本文仅限技术研究与讨论,严禁用于非法用途,否则产生的一切后果自行承担。
前言
这篇文章记述了又又一次的CTF拉练,node.js的白盒审计题,跟上次的记又一次CTF拉练-Node.js基本逻辑一样,感觉是得到了很多非预期解进一步限制条件~
sourceCode1源码
1 | process.on('uncaughtException', function (err) { |
思路解析
首先分析代码, 先是引入一些模块,定义网站根路径加载源码,定义了package.json,Version页面提供一些版本信息,中间用isProtectUrl进行判断url中是否有相关字符等及session[‘username’]是否定义来处理请求,不包含相关字符或者未定义seesion[‘username’]则 跳转到网站根路径;定义了一个login页面,可以post验证用户名及密码,如果用户密码对了则session 赋值;定义了一个getflag1,getflag2,getflag3页面,3个页面加载flag显示。 题目主要请求访问/getflag1,/getflag2,/getflag3来查看flag文件。基本逻辑跟上次的记又一次CTF拉练-Node.js一致~~,感觉是上一次得到很多非预期解(猜的…),进一步限制了条件,上一次的升级版。
初步想法
绕过isProtectUrl(req.originalUrl, req.query)
本题考点
req.query 包含在路由中每个查询字符串参数属性的对象。如果没有,默认为{};
1、不能获取原型链的属性
2、如果没有query string,它就是一个空对象,属性的值为{}。
3、不能获取数组[]后面=前面的值(如:[]123
不能获取到123)
…
解题步骤
getflag1对url中存在__proto__
及存在]*
进行了判断,根据相关特性我们可以构造getflag1?=/login
getflag1?1=1&=/login
getflag1?&%5b%5d/login
getflag1?[][/login
等进行绕过
1 | https://xxx.xxx.xxx.com/getflag1?=/login |
sourceCode2源码
1 | var fs = require('fs'); |
getflag2也对url中存在__proto__
及存在]*
看是否等于]=
的判断,根据特性我们可以构造getflag1?=/login
getflag1?1=1&=/login
getflag1?&%5b%5d/login
等进行绕过
1 | https://xxx.xxx.xxx.xxx.com/getflag2?=/login |
sourceCode3源码
1 | var config = require('./config'); |
getflag3 对url存在__proto__
?=
&=
并匹配如果输入有]*
看是否等于]=
进行了判断。这里采用将[]
、__proto__
进行url编码绕过。
本地环境调试
getflag3?&%5b%5d/login
getflag3?%5f%5f%70%72%6f%74%6f%5f%5f=/login
1 | https://xxx.xxx.xxx.xxx.com/getflag3?&%5b%5d/login |
最后
仅供参考~