ZeroLogon
ZeroLogon(CVE-2020-1472)从零到域控 — 实战记录
前言
Zerologon 是我接触内网渗透后打的第一个真正意义上的”不用密码就能拿域控”的漏洞。它的爆点在于——不需要知道任何密码、不需要用户交互、不需要钓鱼,只要域控没打补丁,一把梭就提权到域管。
什么是 Zerologon
Zerologon 是 Netlogon 远程协议(MS-NRPC)的一个特权提升漏洞,编号 CVE-2020-1472。
Netlogon 是 Windows 域环境里机器账户认证用的协议——每台加域的计算机启动时,都要通过 Netlogon 向域控证明”我是我”。这个协议跑在 SMB 命名管道(\pipe\netlogon)上。
漏洞出在它使用了 AES-CFB8 加密模式,但初始化向量(IV)被固定为全零。攻击者只需要不断发送全零密文作为凭证,每次有 1/256 的概率被域控接受为合法认证。平均 256 次尝试就能拿到域控的机器账户身份。
环境说明
| 角色 | 主机名 | IP |
|---|---|---|
| 域控(DC) | masterpc | 192.168.111.100 |
| 攻击机 | Kali / Windows + Python | 192.168.111.25 |
| 域名 | myd.com |
域控是 Windows Server 2016(Build 14393),未安装 KB4565349 补丁。
攻击流程
Step 1:漏洞检测
使用 SecuraBV 的 zerologon_tester 脚本检查目标是否存在漏洞:
1 | |
脚本会向域控发送 2000 次全零认证请求,每次返回 = 号表示失败。如果某次返回 Success,说明漏洞存在。
也可以使用 Impacket 自己写检测逻辑,核心就两步:
- NetrServerReqChallenge — 发送全零挑战
- NetrServerAuthenticate3 — 发送全零凭证认证
Step 2:置空机器账户密码
确认存在漏洞后,执行 VoidSec 的 exploit 脚本:
1 | |
脚本爆破成功后,会询问是否继续修改密码——输入 Y,将 masterpc$ 的密码置为空。这一步操作的就是 AD 数据库 ntds.dit 中机器账户的凭据。
Step 3:导出域哈希
密码置空后,用空密码冒充 masterpc$ 登录域控,导出所有用户的哈希:
1 | |
拿到 Administrator 的 NTLM hash:
1 | |
Step 4:PTH 攻击拿到 Shell
有了哈希就不用解密码,Windows NTLM 认证协议只看哈希对不对得上:
1 | |
拿到域控的 SYSTEM 权限 shell:
1 | |
踩坑记录
坑1:Windows Defender 杀 impacket
运行 exploit 时一直报 WinError 10053 — 你的主机中的软件中止了一个已建立的连接。
查了半天发现是 Windows Defender 把 impacket 的几个关键文件(nrpc.py、epm.py、__init__.py)标记为”潜在垃圾软件”并阻断读写。解决方案是把 Python 目录加到 Defender 排除列表。
修复后还有更坑的: ping 命令被 impacket 自带的 ping.py 劫持了。因为 Python Scripts 目录在 PATH 里的优先级比 C:\Windows\System32 高,导致 ping 实际上在跑 ping.py。删掉 ping.py 解决。
坑2:impacket 版本不兼容
原版 exploit 写于 2020 年,用的是 impacket==0.9.23。而我本地装的是 impacket==0.13.1,新版改了多个 API:
nrpc.MSRPC_UUID_NRPC的值在新版中损坏NETLOGON_NEG_SUPPORTS_AES等常量在新版中不存在- 结构体字段名有变化
降级到 pip install impacket==0.9.23 解决。
坑3:PrimaryName 参数问题
通过 SMB 命名管道连接 Netlogon 服务时,PrimaryName 参数必须传空字符串 \x00,不能传 \\masterpc\x00,否则域控返回 STATUS_INVALID_COMPUTER_NAME。
坑4:杀毒软件拦截
即使加了排除目录,发送 Zerologon 攻击包时杀毒软件的实时网络防护仍会拦截。需要临时关闭实时防护或在攻击机上用 -codec gbk 解决中文乱码。
为什么恢复哈希很重要
攻击完成后,masterpc$ 在 AD 数据库(ntds.dit) 中的密码被置空了。但域控本地的注册表和 lsass 进程中存的还是原始密码。这就导致了:
1 | |
域控重启时拿着注册表的原始密码去 AD 认证,但 AD 里的密码是空的——两边对不上,域控会脱域甚至开不了机。
恢复方法:
1 | |
一些思考
关于哈希加密的意义
刚接触的时候觉得挺矛盾的——破解不了的 hash,结果直接拿去登录了,那加密的意义在哪?
后来想明白了:哈希的目的是防止密码被反向获取,而不是防止被重用。 NTLM 协议设计时就没想过”哈希会泄露”的场景——它假设只有域控才能拿到哈希。ZeroLogon 打破了这个假设。
关于域渗透的学习路径
从一个漏洞切入整个 Windows 域体系,比直接背命令效果好得多。打完 ZeroLogon,我对以下概念建立了具象理解:
- 域控 ≠ 域管(一个是服务器,一个是账号)
- NTLM 认证的 hash 可以直接登录(PTH 的本质)
- 机器账户
masterpc$和普通账户的区别 - Kerberos 票据是”通行证”,黄金票据伪造 KDC,白银票据伪造服务
- SMB 命名管道作为 RPC 传输通道的工作方式