BUUCTF | [De1CTF 2019]SSRF Me
解法一字符串拼接:
1.得到签名sign
http://8fa4531c-1164-49b7-a700-70e77e6aacb7.node3.buuoj.cn/geneSign?param=flag.txtread

2.添加Cookie发送请求得到flag
Cookie: action=readscan;sign=cf8d4365c9b27a29b29e025a7ed25fa6

原理:
1.分析源码
#! /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)

2.传入一个param,/geneSign路由会返回的一个sign



3.通过cookie得到一个sign,到时候回传到exec()中去跟getSign()产生的sign校验,所以这里直接传一个getSign()产生的sign。通过cookie传入一个action参数,看后面的Exec()可以知道action="readscan"。根据提示param=flag.txt,所以这个sign应该是md5('xxxflag.txtreadscan'),但是action在geneSign()写死了为"action"。
不妨假设
secert_key是xxx,那么在开始访问/geneSign?param=flag.txt的时候,返回的 md5 就是md5('xxx' + 'flag.txt' + 'scan'),在 python 里面上述表达式就相当于md5(xxxflag.txtscan),这就很有意思了。直接构造访问
/geneSign?param=flag.txtread,拿到的 md5 就是md5('xxx' + 'flag.txtread' + 'scan'),等价于md5('xxxflag.txtreadscan'),这就达到了目标。

解法二文件包含:
1.得到sign
2.得到flag
原理:
Python 2.x - 2.7.16 urllib.fopen支持local_file导致LFI(CVE-2019-9948):https://bugs.python.org/issue35907
这里是使用的 urllib.urlopen(param) 去包含的文件,所以可以直接加上文件路径
flag.txt或./flag.txt去访问,也可以使用类似的file:///app/flag.txt去访问,但是file关键字在黑名单里,可以使用local_file代替。 如果使用 urllib2.urlopen(param) 去包含文件就必须加上file,否则会报ValueError: unknown url type: /path/to/file的错误当不存在协议的时候,默认使用
file协议读取可以使用
local_file:绕过,例如local_file:flag.txt路径就是相对脚本的路径local_file://就必须使用绝对路径(协议一般都是这样)
PS:local-file:///proc/self/cwd/flag.txt也可以读取,因为/proc/self/cwd/代表的是当前路径




解法三:哈希拓展攻击
我们可以在不知道salt的具体内容的情况下,计算出任意的md5(salt+message+padding+append)值
对于本题来说就是 md5(secert_key + 'flag.txt' + 'scan') 的值延拓成 md5(secert_key + 'flag.txt' + 'readscan') 的值
由于我本机的hashpump老是安装失败就不复现了Orz Hash Length Extension Attack
参考:
https://blog.csdn.net/weixin_44255856/article/details/98946266
https://www.cnblogs.com/20175211lyz/p/11440316.html
https://joychou.org/web/hash-length-extension-attack.html
BUUCTF | [De1CTF 2019]SSRF Me的更多相关文章
- 刷题记录:[De1CTF 2019]SSRF Me
目录 刷题记录:[De1CTF 2019]SSRF Me 一.涉及知识点 1.MD5长度扩展攻击 2.Python 2.x - 2.7.16 urllib.fopen支持local_file导致LFI ...
- [De1CTF 2019]SSRF Me
原帖地址 : https://xz.aliyun.com/t/5927 De1CTF 2019 的一个题目总结 题目描述 直接查看页面源代码可以看到正确格式的代码 #! /usr/bin/env py ...
- 刷题[De1CTF 2019]SSRF Me
前置知识 本题框架是flask框架,正好python面向对象和flask框架没怎么学,借着这个好好学一下 这里我直接听mooc上北京大学陈斌老师的内容,因为讲的比较清楚,直接把他的ppt拿过来,看看就 ...
- [De1CTF 2019]SSRF Me-MD5长度扩展攻击&CVE-2019-9948
0x00 打开题目查看源代码,开始审计 这里贴上网上师傅的博客笔记: https://xz.aliyun.com/t/6050 #! /usr/bin/env python #encoding=utf ...
- 刷题记录:[De1CTF 2019]Giftbox && Comment
目录 刷题记录:[De1CTF 2019]Giftbox && Comment 一.知识点 1.sql注入 && totp 2.RCE 3.源码泄露 4.敏感文件读取 ...
- [De1CTF 2019]Giftbox 分析&&TPOP学习
[De1CTF 2019]Giftbox 刚进来我以为是直接给了shell,恐怖如斯. 随便扔了个命令,之后就没然后了,hhh,截包发现可能存在sql注入. 然后我就不会了... what i lea ...
- BUUCTF | [RoarCTF 2019]Easy Calc
看一下页面源码,发现了提示: calc.php?num=encodeURIComponent($("#content").val()) $("#content" ...
- [BUUCTF]REVERSE——[2019红帽杯]easyRE
[2019红帽杯]easyRE 附件 步骤: ida载入,没有main函数,就先检索了程序里的字符串 发现了base64加密的特征字符串,双击you found me跟进,找到了调用它的函数,函数很长 ...
- BUUCTF | [SUCTF 2019]CheckIn
感觉这题师傅们已经写得很详细了,我就做一个思路梳理吧,顺道学一波.user.ini 步骤: 1.上传一个“.user.ini”文件 2.上传自己的马“a.jpg” 3.菜刀连接 "http: ...
随机推荐
- python 设置开机启动脚本
1.创建python_auto.bat的快捷方式,放入启动项: C:\Users\Administrator\AppData\Roaming\Microsoft\Windows\Start Menu\ ...
- k8s创建资源
一.创建方式分类: 命令 vs 配置文件 Kubernetes 支持两种方式创建资源: 1.用 kubectl 命令直接创建(适用于少数的pod创建) kubectl run httpd- ...
- 解决gson解析long自动转为科学计数的问题
不废话,直接上代码: public class GsonUtils { public static Gson getMapGson(){ Gson gson=new GsonBuilder().reg ...
- Junit 3.8源码分析
JUnit背景介绍 JUnit是由Erich Gamma和Kent Beck 编写的一个回归测试框架(regression testing framework).Junit测试是程序员测试,即所谓的白 ...
- JAVA总结--jvm
VM,Virtual Machine 即虚拟机,指通过软件模拟的具有完整硬件系统功能的.运行在一个完全隔离环境中的完整计算机系统. JVM,Java Virtual Machine 即Java虚拟机, ...
- <每日一题> Day8:CodeForces-996A.Hit the Lottery(贪心)
原题链接 因为数据太水,我直接一发暴力过了...... #include <cstdio> using namespace std; ] = {, , , , }; int main() ...
- git的基本使用方法
git的基本使用方法:https://blog.csdn.net/qq_33316091/article/details/82414389
- P2933 [USACO09JAN]气象测量The Baric Bovine
传送门 挺显然的 $dp$ ,然鹅一开始想的是 $dfs$ 乱剪剪枝搞了 $70$ 分... 设 $f[i][j]$ 表示切了 $i$ 次,当前切的位置为 $j$ 的最小误差 那么转移显然枚举上一个切 ...
- 详解 HiveUDF 函数
更多精彩原创内容请关注:JavaInterview,欢迎 star,支持鼓励以下作者,万分感谢. Hive 函数 相信大家对 Hive 都不陌生,那么大家肯定用过 Hive 里面各种各样的函数.可能大 ...
- Log4Net 之将日志记录到数据库的配置 (一)
原文:Log4Net 之将日志记录到数据库的配置 (一) 前段时间我一直想做一个通用一点的日志记录系统,可以便于不同的业务组调用进行日志记录及分析.本来打算着自己下手写一个,后面发现各业务组可能会需要 ...