OWASP TOP10 ---注入(二)
SQL注入
作者:CatG0d
一、SQL注入的原理
SQL注入,就是通过把SQL命令插入到Web表单递交或输入域名或页面请求的查询字符串,但Web应用程序没有对用户输入的数据进行过滤和对数据合法性的判断,从而导致前端传入的参数可以被攻击者利用。攻击者可以lion给恶意的SQL查询语句或添加语句进行数据库的攻击。SQL注入带来的危害非常大,比如猜解后台数据库来盗取网站的敏感信息、绕过认证来绕过验证登录的网站后台、借助数据库的存储过程进行提权等操作。
二、SQL注入的类型
1、按照注入点分类
-
- 数字型注入
- 字符型注入
- 搜索型注入
2、按照执行效果分类
-
- 布尔盲注
- 时间盲注
- 报错注入
- 联合注入
- 堆叠注入
- 二次注入
- 宽字节注入
3、按照提交方式分类
-
- GET注入
- POST注入
- Cookie注入
- HTTP注入
三、SQL注入详解
1、数字型注入
在注入点输入参数为数字时存在注入漏洞就称其为数字型注入,数字型注入点一般出现在弱类型的语言中,因为弱类型语言会自动推导变量类型。观察下图URL:http://127.0.0.1/sqli/Less-1/?id=-1

2、字符型注入
当输入的参数为字符串时存在SQL注入,称为字符型注入。字符型注入不同于数字型注入的是:字符串一般需要通过单引号来进行闭合,而数字型不需要单引号闭合。观察下图最后的查询语句即可发现。

3、搜索型注入
搜索型注入是一种特殊的注入类型。这类注入主要是指在进行数据搜索时没有过滤搜索参数,一般在链接地址中有“keyword=关键字”有的不显示在链接地址里面,而是直接通过搜索框表单提交。即可分为POST注入和GET注入。这类注入点提交的SQL语句,大致为:select * from 表名 where 字段 like ‘%关键字%’

4、布尔盲注
盲注查询不需要返回结果,仅需判断查询语句是否正常执行即可,所以返回页面可以看到一个布尔值,正常显示为true,报错或者其他不正常回显为false。盲注一般适用于页面回显极少甚至没有的情况。盲注一般都会用二分法进行猜解数据库。
sql语句:
id=1’ and length(database()) =8 --+
id=1’ and substr(database(),1,1)=‘s’ --+
id=i’ and ascii(substr((select table_name from information_schema.tables where table_schema=’security’ limit 0,1)1,1))=117 --+

5、时间盲注
时间盲注一般现象,当检测是否存在SQL注入漏洞时,页面回显的信息是固定的,没有出现查询的信息和报错信息,但在回显的过程中出现时间差,这时可以大概推测出存在时间盲注,再利用相关工具进行测试。通过构造SQL语句查看页面响应时间来判断,if(条件,A,B) –如果条件成立,执行A,否则执行B。
sql语句:
id=1’ and if ((ascii(substr(database(),1,1))>50),sleep(3),1) --+


6、报错注入
报错注入又可细分为updatexml报错注入、extractvalue报错注入、floor报错注入。
updatexml报错注入
updatexml()报错注入函数在SQL中负责更新xml文档攻击者通常在xml文档路径的位置写入子查询,然后在输入特殊字符,这时候就会因不符合输入规则然后报错,但在报错前,它已经执行完子查询语句,这就导致了SQL注入的产生。
sql语句:
id=1’ and updatexml(0x7e,concat(0x7e,database()),0x7e) --+
id=1’ and updatexml(0x7e,concat(0x7e,(select count(table_name) from information_schema.tables where table_schema=‘security’), 0x7e),1) --+
extractvalue报错注入
extractvalue()函数在SQL语法中是为了从目标xml中返回包含u哦查询值的字符串,格式为extractvalue(xml_document,xpath_string),xml_document是string格式,为xml文档对象的名称;xpath_string是xpath格式的字符串。
sql语句:
id=1’ and extractvalue(1,concat(0x7e,database())) --+
id=1’ and extractvalue(1,concat(0x7e, (select count(table_name) from information_schema.tables where table_schema=database()) )) --+
Floor报错注入
floor报错注入是利用count()、rand()、floor()、group by 这几个特定的函数结合在一起产生的注入漏洞。准确来说是因为floor()、count()、group by 冲突导致的报错,该报错是因为数据库表主键不能重复的原理,使用group by分组,产生主键冗余,导致的报错。
sql语句:
id=1’ union select count(*),1,concat((select database()),floor(rand(0)*2)) as a from information_schema.tables group by a --+
7、联合注入
Union在SQL语法中用于合并两个或多个select语句,利用这个特性就可以向数据库查询更多信息,这就导致了SQL注入漏洞的产生。Union联合查询的使用前提:页面必须要有显示位,即回显。sql语句示例:select * from table union select * from column where cat


8、堆叠注入
堆叠查询注入,和union查询原理大同小异,其就是再union查询的基础上,可以多条SQL语句一起执行。与union查询不同的是union或者union all 执行的语句类型是有限的,union注入可以执行查询语句,而堆叠诸恶u可以执行任意语句。
sql语句:
id=1’ ;insert into users(id,username,password) values (‘38’,’less38’,’ruoli’) --+



9、二次注入
二次注入是指已存储(数据库、文件)的用户输入内容被读取后再次进入到SQL查询语句中导致的注入。二次注入的原理:在第一次进行数据库插入数据的时候,仅仅只是使用了addslashes或者是借助get_magic_quotes_gpc对其中的特殊字符进行了转义,在写入数据库的时候还是保留了原来的数据,但是数据本身是有害数据。再将数据存入到数据库之中,开发者就认为数据是可信的。在下一次进行需要进行查询的时候,直接从数据库中取出有害数据,没有进行进一步的检验和处理,这样就会造成SQL的二次注入。
10、宽字节注入
宽字节注入就是利用mysql特性进行的,在使用GBK编码时将/进行转义。宽字节注入带来的安全问题主要是吃ASCII字符(一字节)的现象。

11、GET注入
GET是HTTP协议的传输方式。它的特点就是可以直接以URL的形式传输数据,GET型注入漏洞就是利用这一特点,对数据库进行注入测试。

12、POST注入
在HTTP常用方法中,POST方法提交的实体不存储在URL中,而是存储在HTTP协议实体内容中,我们无法通过重构URL的方式去实现注入。因此,我们需要借助代理工具Burp Suite,将我们提交的报文进行拦截,并对报文实体内容进行重构。POST注入的检测方式和注入方式和GET注入一样,但POST注入和GET注入的区别在POST注入的SQL语句的重构是在BurpSuite中进行的。

13、Cookie注入
在防注入系统中,程序会对GET和POST中的数据进行过滤,但并没有对Cookie中的数据作检测,所以就会导致Cookie注入的产生。

14、HTTP注入
XFF注入
XFF(全称X-Forwarded-For)代表客户端,是HTTP的请求端的真实IP,通常一些网站的防注入功能会记录请求端真实IP地址并写入数据库或者某文件。【通过修改XFF头实现伪造IP】
除此之外,还有UA(user-Agent注入)、Referer注入,这些和POST注入方式一样,需要利用BurpSuite进行抓包,再进行修改、注入、重放。
四、SQL注入的检测
工具检测
Sqlmap,Netsparker,SQLIer
逻辑检测
1、先在注入点加单引号’ 、双引号“ 等看是否报错,如果报错就可能存在SQL注入漏洞
2、在注入点URL后面加and 1=1、and 1=2看页面显示是否一样,如果不一样,就存在SQL注入漏洞
3、时间盲注(timing attack)测试。在MYSQL中,有一个benchmark()函数,它是用来测试性能的。benchmark(count,expr)是将表达式expr执行count次。利用benchmark()函数,可以让一个函数执行若干次,使得结果返回的时间比平时要长,通过时间长短的变化,可以判断诸如语句是否执行成功
五、Bypass
混淆/编码Bypass
大小写
URL编码
Unicode编码
HTML实体编码
混合编码
双重URL编码
通配符绕过
动态payload生成
垃圾字符
插入换行符
未定义变量
Tab键和换行符
闭合SQL注入
其他格式的混淆
正则表达式
过滤关键词 绕过
and,or,union 1 || (select user from users where userid=1) = ‘admin’
and,or,union,where 1 || (select user from users limit 1) = ‘admin’
and,or,union,where,limit 1 || (select user from users group by userid having userid=1) = ‘admin’
and,or,union,where,limit,group by 1 || (select substr(group_concat(userid),1,1) user from users) =1
and,or,union,where,limit,group by,select 1 || 1 =1 into outfile ‘result.txt’ 或者 1|| subtr(user,1,1) = ‘a’
and,or,union,where,limit,group by,select,’ 1 || userid is not null 或者 1 || substr(user,1,1) = 0x61 或者 1 || substr(user,1,1) = unhex(61)
%00(00截断)
注释符绕过
中间件特性绕过
关键字替换绕过
脏数据绕过
全局替换绕过
空白符绕过
白名单绕过
嵌套剥离绕过
http协议绕过
特殊Bypass
伪装绕过(请求头欺骗)
伪装成本地
伪装成爬虫
其他Bypass
Sleep函数过滤绕过
if函数过滤绕过
substr函数过滤绕过
过滤and、or绕过
过滤括号绕过
过滤比较符号(=、<、>)绕过
盲注函数过滤绕过
过滤引号绕过
过滤逗号绕过
过滤information_schema绕过与无列名注入

SQL注入的原理、类型、详解、检测以及一些Bypass方式



浙公网安备 33010602011771号