在域渗透测试里,黄金票据就像是一把万能钥匙——只要拿到了krbtgt账户的哈希,你就能为任意用户伪造一张永不过期的访问凭证。我第一次在Windows Server 2008域环境中实操黄金票据时,踩了不少坑,所以这篇进阶版实战笔记,既是给刚接触Kerberos攻击链的朋友扫盲,也是给已经会基础操作的人提供一些绕过和防御的细节。本文只讨论在合法授权条件下的安全测试与防护验证,请务必在自有环境或取得书面授权的靶场中操作。
如果你手头正好管理着老旧的Windows Server 2008域控,或者正在做内网安全审计,那这篇文章能帮你把黄金票据的原理、伪造步骤、隐蔽技巧和检测防御一次讲透。我会从Kerberos握手说起,一直到Mimikatz的具体命令、SID History隐藏提权、事件日志排查,全程以实测记录为主,尽量让你读完就能照着复现。
1. 从Kerberos握手到黄金票据:底层原理与适用场景
1.1 一句话讲透Kerberos认证流程
要搞懂黄金票据,先要理解Kerberos到底是怎么工作的。域环境里,所有计算机都信任域控制器(DC)上的Kerberos服务,整个认证过程分三步:客户端先向认证服务器(AS)发送身份请求,AS验证通过后返回一张票据授权票据(TGT);客户端接着拿TGT向票据授予服务(TGS)申请服务票据(ST),最后带着ST去访问目标服务。
这就像你去一个高档小区,第一步在门卫处刷身份证拿到临时通行证(TGT),第二步凭临时通行证去物业换某个楼栋的门禁卡(ST),第三步才能刷门禁卡进具体房间。关键在于:门卫(AS)和物业(TGS)都无条件信任一个超级密码本的摘要,这个摘要就是krbtgt账户的密码哈希。一旦你拿到了这个哈希,就等于自己造一本一模一样的密码本,想给谁发通行证就给谁发,想让通行证什么时候到期就什么时候到期。
黄金票据利用的正是这个信任根。攻击者不需要知道域管理员的密码,也不需要控制任何一台域内主机,只要拿到krbtgt哈希,就能自建一张合法的TGT,签名、时间戳、会话密钥全部自己定,域控完全无法分辨真假。
1.2 黄金票据与白银票据的本质区别
经常有人把黄金票据和白银票据混在一起讲,但两者根本不是同一个层级。黄金票据伪造的是TGT,属于认证的“总入口”,一旦成功,你就能访问域内任何服务,包括文件共享、SQL Server、Exchange、域控上的LDAP等等。白银票据伪造的是ST,也就是针对单一服务(比如CIFS或HTTP)的票据,只能访问这一个服务,但好处是不需要跟域控有任何交互,日志记录更少。
我用一个实际测试来对比:在黄金票据场景下,我用伪造的TGT去访问域控的CIFS服务,一条dir \\dc01\c$直接列目录成功;而在白银票据场景下,我只伪造了CIFS的ST,虽然也能列目录,但换个时间同步、换台机器可能就失效。黄金票据的权限维持能力是全局性的,这也是为什么它被红队视为域管后的“保留项目”。
从安全检测角度看,白银票据更容易被服务端的KDC验证拦截,因为服务端会检查票据的签名来源;黄金票据则通过KDC校验,和正常TGT没有任何区别,所以传统的事件日志审计非常难发现。
1.3 为什么说拿到krbtgt哈希等于控制整个域
krbtgt账户是Kerberos分发中心的“根信任”。这个账户的密码由DC在域创建时自动设定,之后极少有人去改它。Windows Server 2008的几个常见版本里,krbtgt密码默认十年都不会轮换一次。如果你通过DCSync或域管权限拿到了krbtgt哈希,就意味着这个域的所有Kerberos票据都能被你合法签发,包括域管理员的。
这意味着:你不需要破解任何密码,不需要抓取任何明文,只需要rdp到一台能访问DC的机器上,执行几条命令,就能获得域内最高权限。更麻烦的是,除非管理员主动重置krbtgt密码两次并清空相关日志,否则就算你把域管密码改了,黄金票据依然有效。这正是我强调“权限维持”优于“瞬时提权”的原因——黄金票据不是一发入魂的弹药,而是一把可以反复使用、跨越多个运维周期的后门钥匙。
2. 环境搭建与前置信息收集:动手前你必须拿到四样东西
2.1 准备一个干净的Windows Server 2008 R2测试域
黄金票据的复现环境要求其实不算高。你只需要一台装好Windows Server 2008 R2的域控制器(同时充当DC和DNS),以及两到三台加入域的Windows 7或Windows 10客户端,虚拟机完全够用。系统镜像请通过正规渠道获取,不建议使用第三方精简版或所谓的“GHO一句话下载”,因为在安全测试中,不可信的镜像本身就是一种污染源,会干扰你对攻击链的完整判断。
域内规划建议用lab.local这种清晰的域名,域功能级别设为“Windows Server 2008”即可。需要注意的是:Windows Server 2008的默认安全策略里,SMBv1是启用的,后续某些Mimikatz操作和历史版本的漏洞利用都依赖它,但这个测试域不需要太多加装的东西,保持干净最有利于出结果。创建域时把第一个域控的netbios名称记好,后面提取SID要用。
2.2 获取域名、SID和krbtgt哈希的三种姿势
伪造黄金票据需要四个关键参数:域名(Domain)、域的SID、目标用户RID(通常设为500,即Administrator)、krbtgt的NTLM哈希。前两个可以直接通过命令拿到:whoami /fqdn和wmic useraccount get sid,或者直接读注册表。krbtgt哈希则必须从DC的NTDS.dit中提取,常见姿势有三种:
- 在DC上以域管身份运行Mimikatz,执行
lsadump::lsa /patch或lsadump::dcsync /domain:lab.local /user:krbtgt。DCSync方式最稳妥,因为它模拟的是DC之间的复制请求,不会产生太多异常日志。 - 如果你只有普通管理员权限,先提权到SYSTEM,然后
lsadump::sam和lsadump::secrets,再配合离线解析NTDS.dit。 - 离线方式:从域控拷贝
C:\Windows\NTDS\ntds.dit和SYSTEM文件,用esentutl或impacket-secretsdump在本机解析。我推荐第三种,因为不会在目标机上留下Mimikatz的进程痕迹,更容易躲避AV的实时扫描。
拿到hash之后,用mimikatz # kerberos::golden之前先核对一下格式,确保是一串32位的十六进制。很多新人在这里翻车,把LM Hash误当NTLM Hash用,导致伪造出来的票据无效。
2.3 关于权限与合规的最后提醒
我必须再啰嗦一遍:黄金票据属于典型的“高权限持久化”技术,它的获取和使用过程都会触发大量安全事件,尤其是lsadump::dcsync这种操作。不要在生产域环境里手痒乱试,更不要在没有书面授权的客户内网里炫技。我见过不止一个安全工程师因为好奇心爆棚,在客户机器上执行了kerberos::golden,结果被SOC当场抓包,合同直接泡汤。
自建测试域时,建议关闭Windows Defender对Mimikatz的实时防护,或者在Mimikatz目录单独加白名单,否则杀软会秒删exe。我这里只是介绍原理和防御视角,实操前请确保你有权做这件事。
3. 黄金票据伪造全流程:从Mimikatz命令到票据注入
3.1 用Mimikatz提取krbtgt哈希的实测记录
我在测试机上用管理员cmd运行Mimikatz,先验证权限:privilege::debug,然后执行lsadump::dcsync /domain:lab.local /user:krbtgt。Mimikatz会自动输出这个用户的两条哈希,一条是LM Hash,另一条是NTLM Hash。黄金票据要的是NTLM Hash,也就是通常以c5ff2fa...开头、32位十六进制的字符串。
注意:在Windows Server 2008的某些补丁版本上,直接执行lsadump::lsa /patch可能会提示“Access is denied”,这是因为内存保护机制和补丁Kb2871997的影响。遇到这种情况,优先改用DCSync,或者先获得SYSTEM令牌再操作。我实测下来,lsadump::dcsync的成功率远高于在线抓取,尤其在打了新补丁的DC上。
如果目标机器上没有Mimikatz,你也可以用Impacket工具包里的secretsdump.py,通过远程RPC从一台普通域机器发起,拿到krbtgt哈希。这种方式对老域控非常友好,而且不需要落地任何二进制文件。
3.2 精确伪造一张永不过期的TGT
拿到那四样参数后,进入伪造环节。Mimikatz的kerberos::golden模块典型命令如下:
kerberos::golden /user:administrator /domain:lab.local /sid:S-1-5-21-123456789 /krbtgt:c5ff2fa... /ptt解释一下参数:/user是你想假冒的用户,通常设为管理员;/domain是域名;/sid是域的SID,注意不要带末尾的-500;/krbtgt就是刚才提的NTLM Hash;/ptt表示直接将生成的票据注入当前会话。如果你不想立即注入,而想保存成.kirbi文件,可以把/ptt换成/ticket:gold.kirbi,方便后续在内网其他机器上离线使用。
我在实测中把/user换成了一个普通域用户,而/sid保持不变,照样能访问域控。因为KDC在验证TGT时只关心签名是否正确,而签名由krbtgt哈希决定,用户名的真实性它根本不检查。如果想更隐蔽,可以把/user设成一个现实中存在的用户,并且把/groups加上500和512组RID,这样连用户组校验都能绕过。
3.3 票据注入与访问验证的实测记录
执行完伪造命令后,当前登录会话里已经有一张TGT。验证方法很简单:先用klist查看票据缓存,能看到一张名为krbtgt/LAB.LOCAL的票据;然后直接访问域控的共享:dir \\dc01\c$。如果一切正常,你会看到C盘文件列表,没有任何权限报错。
我还做过一个更极端的测试:在域内一台Windows 7客户端上,用runas /netonly启动一个进程,然后注入黄金票据后访问其他服务器。所有访问都畅通无阻,而且由于票据签名合法,服务器不会记录任何异常。这里务必注意:注入的票据只对当前用户的登录会话有效,如果你需要跨进程使用,就得重新注入。还有个坑是部分程序(比如某些新旧JDK版本)缓存了Kerberos票据句柄,导致新建的连接不认新票据,需要重启该进程再试。
4. 进阶技巧:提升隐蔽性与攻击效率的五个实操细节
4.1 利用SID History实现跨域提权
SID History本是微软为域迁移设计的兼容性机制,允许用户保留旧域的SID。攻击者可以把自己的TGT里加上目标域的Enterprise Admins SID,从而在域林中获得跨域管理权限。Mimikatz的/sids参数就是干这个用的。
比如当前域SID是S-1-5-21-111...,目标域是S-1-5-21-222...,我伪造时写成:/sids:S-1-5-21-222...-519,这样生成的票据在访问目标域时,会被KDC认为是来自目标域的安全组成员。这个技巧在大型多域林中非常恶心,因为管理员往往只防护当前域,却忽略了对其他子域和信任域的监控。
4.2 票据生命周期与续期机制:如何选择合理的有效时间
黄金票据一个明显的特征是有效时间可以随便设,这也是它和普通TGT的最大区别。默认情况下,域策略规定用户TGT最长24小时,但黄金票据通过直接修改/startoffset和/endin参数,能轻松产生“十年有效”的票据。
然而在实战里,太久反而引人注意。Windows 2008域控的Kerberos策略审计会记录TGT的Ticket End Time,如果看到一张有效期为十年的票据,蓝队一眼就认出来了。我的建议是:把有效时间设定在6到12小时之间,并且跟当前系统时间对齐,避免出现明显的时钟偏差。别小看这个细节,很多测试人员为了方便设了9999小时,结果日志检测一秒锁定。
4.3 结合CIFS和LDAP服务票据最大化横向移动范围
黄金票据伪造的是TGT,但不同的服务需要不同的SPN。我在测试中一般先注入TGT,再配合kerberos::ptt访问域控的CIFS、LDAP、HTTP和WINRM服务,这样把域控的SYSVOL共享、组策略文件和计划任务管理全部拿下。
尤其推荐通过LDAP服务做DCSync。普通管理员想提权必须Invoke-Mimikatz或secretsdump,但在Windows Server 2008下,直接用LDAP的Replication-Get-Changes权限拉取整个域哈希也是可行路径。黄金票据给了你这个权限,自然不会浪费。实操时可以用mimikatz "lsadump::dcsync /domain:lab.local /all /csv"一次性导出所有哈希,再从其中挑出administrator的哈希直接pass-the-hash登录其他服务器。
4.4 绕过程序白名单与AV的加载方式
Mimikatz直接落地会被AV查杀,Windows Server 2008的Defender虽然弱一点,但也不能大意。我实测过几种加载方式:一是利用PowerShell的反射式加载,把Mimikatz的dll读入内存后调用Invoke-Mimikatz,不落地exe文件;二是编译成自删除的小工具,执行完立刻清盘;三是通过计划的批处理脚本间接调用。
不过我要提醒一句:很多“免杀”操作本身就是违规的,尤其是在未授权场景。如果是在授权渗透测试中,请提前向客户说明工具行为,避免引起法律纠纷。我更推荐从防御视角看这个问题——理解加载方式,才能设计出对应的检测规则,比如监控进程命令行里的kerberos::字符串,或者监控lsass.exe的远程读取访问。
5. 防守方视角:如何检测黄金票据并加固域环境
5.1 事件日志与Kerberos证票审计的关键字段
黄金票据虽然能骗过KDC,但也不是完全无痕。在Windows Server 2008上,域控的Kerberos事件日志里会有几个值得关注的ID:
- 事件ID 4769:Kerberos服务票据请求,如果看到大量来自不常见用户名的请求,就要提高警惕。
- 事件ID 4672:为特权用户分配特权,黄金票据注入后会触发这个日志。
- 事件ID 4771:Kerberos预认证失败,但黄金票据通常不会失败,所以它更多用于排查其他问题。
最核心的是检查TGT的Ticket Options和Ticket Encryption Type。正常2008域的TGT加密方式是AES256或RC4,但如果你看到某些用户的TGT加密类型突然从AES变成了RC4,而且Ticket End Time异常长,那基本可以断定有人在伪造票据。我自己的经验是:把DC的audit Kerberos Service Ticket Operations开启,然后定期用PowerShell导出4769事件,统计每个账户的Service Name和IpAddress,比对异常访问。
5.2 微软官方与第三方工具排查清单
排查黄金票据不能只靠眼睛看日志,要借助工具做关联分析。微软官方有Kerberos Configuration Manager,可以扫描异常SPN和委派配置;还有RiskySPN脚本用于发现易受攻击的服务账户。更直接的方法是PingCastle这个免费工具,跑一轮就能给出域的Kerberos安全评分,并明确指出krbtgt过期时间、AdminSDHolder ACL异常等风险点。
我额外推荐一套组合拳:在DC上周期性执行Get-ADUser -Filter * -Properties sidhistory,检查SID History字段是否被篡改;再用Set-ADAccountControl确认关键账户的AccountNotDelegated属性没有被改动。很多黄金票据的持久化操作都会改这些元数据,只改密码反而容易被忽略。
5.3 域控安全基线:让黄金票据不再可行
防御黄金票据最有效的办法是:定期重置krbtgt密码。注意,不是改一次就完事,标准流程是连续修改两次,间隔至少12小时,并且每次修改后观察24小时,确保域内所有机器都同步了新的票据缓存。微软官方KB2871997提供了详细的Set-ADDomain命令,建议做成每180天自动执行的计划任务。
另一个基础但容易被忽视的点是:最小化DCSync权限。默认情况下,域管和域控机器账户才具备Replicating Directory Changes权限,建议你导出域内拥有这个权限的所有主体进行复核,删除不必要的服务账户。我在一次审计里就发现某个备份软件的服务账户带上了DCSync权限,等于给攻击者送了一把免提钥匙。还要重点关注AdminSDHolder对象的ACL,很多提权后门都会通过修改它来实现“最高权限永不消失”。
如果部署了微软AATP或开源工具如Zeek,可以直接对Kerberos流量做检测。黄金票据生成的TGT,其PacInfo中的LogonTime和PasswordLastSet往往不一致,通过流量深度分析很容易识别这种异常。
6. 实操踩坑实录:九个高频问题与排查命令
6.1 注入票据后访问被拒的原因排查
最常见的问题就是dir \\dc01\c$返回“拒绝访问”。我先检查三个点:一是/sid是否写错了,注意要用域的SID而不是用户SID,命令whoami /user看到的是当前用户SID,不是域SID,别拿它充数;二是/krbtgt哈希是否漏了空格或有换行符,把hash写到文件里容易带入隐藏字符;三是票据注入的会话是否和目标访问来自同一个进程,比如你用管理员cmd注入,但又开了一个普通cmd去访问,那就没生效。
还有种情况是目标服务器需要更高等级的身份验证,比如2008的UAC远程限制。如果当前用户不是本地管理员,即使域管身份也会被普通令牌过滤。此时可以加上/user:域管用户名和/groups:512,513来补足组SID,一般就能通过。
6.2 时间同步问题导致的Kerberos错误
Kerberos对时间偏移的容忍度默认是5分钟,Windows Server 2008域里如果DC和客户端时间不同步,你会看到KDC_ERR_PREAUTH_FAILED或KRB_AP_ERR_SKEW。我测试时因为虚拟机暂停恢复时间没调,导致伪造的票据一直失败。
解决办法:在客户端上执行w32tm /resync /force,并确保DC上的W32Time服务正常运行。如果你是离线打的快照,恢复后一定要先跟DC同步时间再注入票据。与此同时,Mimikatz也提供/startoffset参数,直接调整票据的生效时刻,但在生产环境不建议使用,因为日志会暴露时间异常。
6.3 哈希提取报错的常见原因
运行lsadump::dcsync时报“ERROR kuhl_m_lsadump_dcsync”通常有三种原因:当前进程不是高权限,privilege::debug没有执行成功;目标用户不存在或权限不足;域控拒绝来自非DC机器的复制请求。解决办法是先在Mimikatz里执行token::elevate,再重新运行。
还有一个容易忽略的点:如果你在64位系统上用32位Mimikatz,提取结果会不完整。建议务必下载对应架构的最新版,并核对exe的签名。老版本的Mimikatz对2008的支持有些bug,更新到2.2.0以上会更稳定。
6.4 我的实测心得与建议
踩过几次坑之后,我的建议是:每次复现黄金票据都做一份记录文档,把域名、SID、哈希、票据注入时间、结果都写清楚,方便复盘。还有一个习惯是备份原始krbtgt哈希,方便重置测试环境。
做防御验证时,我会专门模拟一次黄金票据攻击,然后在SIEM里写一条检测规则:监控TGT的Ticket End Time超过当前时间12小时的情况,或者监控Logon Process为NtLmSsp但加密类型为RC4的高权限账户。这样的规则误报率很低,却能在第一时间抓住红队那种“图省事”的长时间票据。
最后再分享一个小技巧:在测试域里给krbtgt哈希设置一个固定的测试专用值,然后把它当作“主密钥”来管理。这样每一次复现都能确保从同一把钥匙出发,不会因为随机哈希干扰你对攻击链的因果判断。