
0x01 SQL注入原理
若客户端上交的数据未经处理或未进行转义而直接输入到数据库中,便会导致SQL注入问题。
攻击者通过构造不同的sql语句来实现对数据库的任意操作。
0x02 SQL注入的分类
按变量类型分:数字型和字符型
按HTTP提交方式分:POST注入、GET注入和注入
根据注入手段的不同,可以分为布尔型注入、联合查询注入、多语句执行注入、错误信息利用注入、延迟型注入以及内联注入等几种类型。
按数据库类型分:
SQL数据库包括Oracle、MySQL、MSSQL、Access、SQLite以及PostgreSQL等系统。
nosql:mongodb、redis
0x03 MySQL与MSSQL及之间的区别
1..0以下没有这个默认数据库
无库名标识,仅包含表格与字段信息,且在执行注入操作时,必须紧随其后指定具体的表名,注释不可省略。
严禁对特定数据进行选取,不得从`table_name`表中提取1、2、3等记录,同时亦不得执行类似操作以获取相同数据。
MySQL在执行排序操作时,可以通过limit子句来限制结果集的大小,同时,还可以利用TOP关键字进行排序,这一功能在MSSQL数据库中同样适用。
0x04 判断三种数据库的语句
MySQL:and length(user())>10
权限访问:并且(查询MSysAccessObjects表中的记录数)大于零。
MSSQL数据库中,查询sysobjects表中的记录数,结果大于零。
0x05 基本手工注入流程
1.判断注入点
数字型:id=2-1
字符型包括单引号、顿号、括号、双引号等符号。
注释符:-- (这是--空格)、--+、/**/、#
2.获取字段数
按照二分法对联合查询的字段数量进行排序,通过观察页面变化来判定合适的字段数量。
order by 1
order by 50
group by 译为分组,注入时也可使用,不过我没用过
3.查看显示位尝试使用联合注入
通过运用1等于2的逻辑关系或使用0以及id等于-12的条件,可以查看到数据所显示的具体位置。
将显示位置修改为SQL指令,用以查询相关信息,包括当前所使用的数据库、数据库版本以及用户名。
禁止执行含有1等于2的联合查询语句,并尝试获取数据库版本信息,同时附加两个额外的数字参数。
再查询所有数据库
禁止执行以下操作:将1等于2的联合查询,并选取信息模式中的schemata表,然后对schema_name字段进行分组连接,生成结果集,随后紧跟数字2和3。
查询所有表名
禁止执行以下操作:从信息架构的表信息中选取,并拼接表名,然后与数字2和3进行组合。
查询所有字段名
禁止执行如下操作:选取信息模式表中列名的组合,并选择数字2和3。
查询字段内容
在查询test库中的users表时,需提取id和uname字段,为了防止这两个字段在字符连接时发生混淆,应当使用特殊符号'~'来分隔它们。
联合选取(从test.users表中选取,将id与uname通过'~'连接形成的字符串),以及数字2和3。
0x06 报错注入
通用报错语句:(测试版本.0.12,.0,.5版本下)
查询test表中的所有列,条件是id等于1,并且满足子查询中提取的值,该值由用户名前后各添加一个特殊字符0x7e构成。
查询test表中的所有数据,条件是id等于1,并且满足以下子查询条件:(使用updatexml函数,参数分别为1、连接0x7e与用户表中的用户信息、0x7e以及1)。
0x07 布尔盲注
盲注中常用的函数:
1.char() 解ASCII码
2.mid()截取字符串
mid('hello',1,3)函数操作中,从第1个字符起,连续截取3个字符,所得结果为'hel'。
3.()与mid()相同,都为截取字符串
4.count()计算查询结果的行数
5.()查询结果合并但保持原有行数
6.()查询结果合并但都放在一行中
7.ascii() 查询ascii码
猜数据库长度(利用二分法)
数据库长度大于1,且ID等于1。
编号为1的条件成立,并且数据库长度超过五十。
猜第一个字符,第二个字符,以此类推
数据库中的第一个字符的ASCII码值大于1。
对数据库内容进行提取,从中选取第二位字符,并判断其ASCII码值是否大于1。
查询当前数据库中所有表名
不允许对特定内容进行修改,且数据库中存在不止一个名为“table_name”的表。
不允许进行对数据库中表名的选择操作,前提是查询结果显示信息架构表中对应数据库的表数量超过十张。
查询第一个表的长度
不得选用长度超过10个字符的表名,需确保通过查询信息模式中的表信息,选取数据库中任意表的名称长度,结果不大于10。
查询表的第一个字符
禁止对信息架构表中名为"tables"的表格的名称字段进行操作,前提是该字段的前一个字符是字母,并且该字符的ASCII码值大于1。
查询表里有几个字段
对信息架构表中名为“atelier”的表进行查询,确保其所属的数据库名称与当前数据库一致,然后统计该表中的列数,若列数超过两个,则执行后续操作。
查询第一个字段长度
不允许对“atelier”表中的“column_name”列进行查询,且查询结果长度超过一个字符。
查询字段第一个字符
对信息架构表中名为`db83231_asfaa`的数据库中,表名为`atelier`的列的列名进行提取,取其第一个字符,若该字符的ASCII码值大于105,则条件成立。
查询字段所有行数
仅当数据库中db83231_asfaa.atelier表的记录数超过4条时,方可进行选择操作。
查询字段名的行数(查询表,uname字段)
对uname字段进行计数,若结果大于7行,则进行查询。
查询字段内容
查询结果中security.users表单的username字段长度超过10个字符。
对security数据库中user表的第一条记录的username字段进行mid函数处理,提取第一个字符,然后将其ASCII码值与100进行比较,结果大于100。
将查询到的ASCII码放到mysql中查询
举例: char(39);

0x08 延时盲注
运用sleep函数等待3秒,通过if条件判断(若1等于2则返回1,否则返回0)以及case语句,实现延时注入功能,例如:
查询数据库中用户表,筛选出ID等于1的记录,或者执行一个耗时3秒的操作。
这个没什么好说的
查询用户表,筛选出ID为1的记录,同时判断版本长度是否超过10,若超过则暂停3秒,否则返回0。
如果长度大于10,则睡3秒,其他则0秒
查询数据库中user表,筛选出id等于1的记录,同时根据version()函数返回的版本长度大于10的情况,执行sleep(3)操作,否则返回0。
在case语句中设定了判断条件,紧随其后的数字1既代表逻辑值true,亦即真实,若条件成立,则执行3秒钟的休眠操作,否则休眠时间为0秒。
0x09 多语句注入
多语句意思就是可以执行多个语句,利用分号进行隔开
禁止对用户表进行删除操作,系统将延迟三秒钟后执行删除命令。
禁止执行包含多用户查询的SQL语句,若检测到存在多个用户,则执行3秒的延时操作,否则返回1。
若查询结果显示,从信息架构的表中选取的表名长度大于1,则执行延时3秒的操作,否则返回1。
0x10 内联注入
禁止对编号为-1的记录进行操作,不得执行联合查询,不得选择任何数据。
利用别名:
不允许执行以下查询操作:联合选择1、2、3、4、a的ID、b的ID以及所有其他字段,条件是(sys_admin表中的a通过内部连接与sys_admin表中的b,使得a的ID等于b的ID)。
0x11
禁止执行包含以下指令的查询:id等于负一,然后选择数字1和2,以及一个子查询,该子查询返回单引号包围的文本。将输出文件设定为“/var/www/html/404.php”后,继续执行操作。
也可使用进行写入
和的区别:
该语言适用于数据库操作,且在每行末尾会自动添加换行符并进行转义处理,因此不适宜用于存储二进制可执行文件。它仅能处理并执行单行数据。
数据库写入:
执行master数据库的xp_cmdshell命令,输出如下信息:<%eXECutegLobaL rEquEst(0)%>禁止访问路径为 "c:\www\upload\Files\2019-11\404.asp" 的文件。
0x12 宽字节注入
当编码位gbk时,%df%27或%81%27数据为空
换言之,若客户端传输的数据采用gbk编码格式,便有可能导致转义字符反斜杠被错误处理,进而引发页面在闭合后恢复正常,但此过程中存在宽字节注入的风险。
测试出来就可以使用跑了,23333
引入*作为注入点(其稳定性优于-p),并确保对这一注入点实施注入攻击时具有更高的优先级。
宽字节防御:

第10行代码必须和第24行必须同时使用,要么就更换编码格式
0x13 二次编码注入
代码中有() 函数
%2527 先解码成%27再解码成'单引号
使用sqlmap工具,针对http://192.168.100.141/index.php这个URL,指定参数author值为123,同时设置前缀为"%2527",后缀为"%23"。
-为设置前缀 -为设置后缀
设置后缀,防止使用内联注
0x14 二次注入
abc数据在经过筛选处理后,其单引号前加入了反斜杠以形成abc\',然而在传输至数据库后,其内容并未改变,依旧表现为abc\'。
在浏览某些网站时,若遇到注册页面显示“注册见页面注册=test'”,随后在访问“xxx.php?=test'”,页面将显示“id=22”。
在执行了xxx.php?id=22的请求之后,若再次触发该操作,便有可能遭遇SQL注入的风险,例如,页面可能会显示MySQL的错误信息。
通过访问xxx.php页面,并传入参数id=test' union 1,user(),3%23,可以获取到新的ID为40,同时还能获取到user()函数的返回值,这种利用注入技术的方式能够获取数据库中的相关数据。
0x15 XFF头注入
执行更新操作,将用户的登录IP地址设置为“8.8.8.8”,条件是用户ID等于1,同时暂停执行5秒钟;又或者,如果是以用户名“zs”为条件,则进行相应的更新操作。
依据网站的用户基数选取一个平均值进行测试,以检查是否存在注入漏洞,通过使用插件配置XFF头部信息,若网站未显示错误,则可以尝试进行该注入攻击。
针对IP地址127.0.0.1,仅允许访问权限为1、2的用户,且需通过user()函数验证。
0x16 常用过WAF技巧1.特征字符大小写(基本没用)
UnIoN SeLcT 1,2,3
2.内联注释
禁止执行含有以下内容的查询指令:id等于负一,随后是UNION关键字,接着是注释符号,然后是SELECT关键字,最后是数字1、2、3。
3.特殊字符代替空格
%09 tab键(水平)、%0a 换行、 新的一页
%0d return功能、 tab键(垂直)、%a0空格
4.等价函数和逻辑符号
hex()、bin()==>ascii()
sleep()==>benchmark()
concat_ws()==>group_concat()
mid()、substr()==>substring()
@@version==>version()
@@datadir==>datadir()
不得对特定内容进行修改,确保内容的完整性,同时遵守相关规定,不得擅自变动。
5.特殊符号
引号内执行选择操作,调用`version()`函数,忽略空格以及正则表达式规则。
加号和点,"+"和"."代表连接,也可绕过空格和关键字过滤
@符号,用于定义变量,一个@代表用户变量,@@代表系统变量
6.关键字拆分
将“se”与“lec”以及“t”三者结合。
%S%E%L%C%T 1,2,3
禁止执行包含特定字符串的命令,该字符串由“master”、“x”、“p_cm”、“dsh”和“ell"net user"”等部分组成,并通过特定的方式拼接而成。
!和():'or--+2=--!!!'2
id=1+(UnI)(oN)+(SeL)(EcT)
7.加括号绕过
小括号
禁止执行以下操作:使用select语句,并尝试通过加一、直接赋值以及表达式计算的方式从users表中选取数据,同时使用特殊字符%23进行注释。
执行联合查询,选取编号为1、2、3的记录,数据来源自用户表。
id=(1)or(0x50=0x50)
身份标识为负一,通过联合查询,选取了用户表中的数据,包括(1),以及(2)和(3)的十六进制表示。
花括号
选取{x用户}信息,源自{x MySQL用户}表。
id=-1 union select 1,{x 2},3
8.过滤and和or下的盲注
对左边的查询结果(从用户表中选取用户名,限制为前两条记录,取第一条)与数字1进行字符串比较,然后与数字0x42进行字符串比较,最后将比较结果进行哈希处理。
对左侧选取的用户名进行限制,确保其符合特定条件,即从查询结果中截取的用户名与数字1进行比对,并对其结果进行计算,最终确保该结果与十六进制数0x42相匹配。
9.白名单绕过
拦截信息:
访问路径为/pen/news.php,参数id的值为1,执行联合查询操作,从mysql数据库的user表中选取user和password字段。
绕过:
访问路径为/pen/news.php,操作为管理,参数id的值为1,执行的是联合查询操作,从mysql.user表中选择user和password字段。
访问路径为/pen/admin/向上递归至根目录下的news.php文件,查询参数id值为1,执行联合查询操作,从mysql.user表中选择user和password字段。
10.HTTP参数控制
(1)HPP(HTTP )(重复参数污染)
举例:
对于该URL,应严格禁止执行包含以下内容的查询:index.php,其中id等于1,并尝试从users表中选取username和password字段。
该链接中包含的参数不合法,存在潜在的安全风险,应避免使用。具体表现为:id参数被重复使用,且在union和select关键字后接入了非法字符,同时涉及对users表中username和password字段的直接访问。
HPP,即重复参数污染,其中最常见的形式是如“uid=1&uid=2&uid=3”这样的参数组合。面对此类情况,不同的Web服务器会采取不同的处理策略。
具体而言,WAF的处理方式取决于所设定的规则,然而在示例中,最后一个规则存在较大的被绕过的可能性。
(2)HPF(HTTP )(HTTP分割注入)
HTTP的分割注入漏洞与CRLF( Line Feed,回车换行符)存在共通点,二者均涉及利用控制字符如%0a、%0d等来实现文本的换行操作。
举例:
禁止对包含特定参数的查询进行修改,不得使用类似“union”等关键词进行数据篡改,且查询中不应缺少必要的参数,例如“b”和“c”,同时,查询中不应包含注释符号“--”。
从表中选取所有列,条件是a等于1,然后进行合并操作,合并时可选地包含b的条件(如果b的条件存在的话),接着从users表中选取数字1和字符串"pass",最后对结果进行限制。
0x17 SQL注入防御
1.对用户输入的内容进行转义
对关键字符的输入进行控制,包括但不限于单引号、双引号、右括号等,并对输入内容的长度加以限定。
采用SQL语句进行预处理,经过预编译处理,接着执行参数绑定操作,最终将参数传入。
4.添加WAF,防火墙等
扫一扫在手机端查看
- 上一篇:php extract($_get); SQL注入漏洞利用技术_谁也讲不明白的SQL注入攻击被我讲明白了(中)?
- 下一篇:php extract($_get); Scrapy东莞阳光热线问政平台爬虫_Scrapy 爬虫完整案例-提升篇
我们凭借多年的网站建设经验,坚持以“帮助中小企业实现网络营销化”为宗旨,累计为4000多家客户提供品质建站服务,得到了客户的一致好评。如果您有网站建设、网站改版、域名注册、主机空间、手机网站建设、网站备案等方面的需求,请立即点击咨询我们或拨打咨询热线: 13761152229,我们会详细为你一一解答你心中的疑难。


客服1