Ntlm Rleay簡介
Ntlm Rleay翻譯過來就是Ntlm 中繼的意思,也肯定是跟Ntlm協議是相關的,既然要中繼,那么攻擊者扮演的就是一個中間人的角色,類似于ARP欺騙,ARP欺騙就是在一個廣播域中發送一些廣播,然后大聲問這個IP地址的MAC地址是多少啊???如果有不懷好意的人回答了,那么就造成了ARP欺騙,好似一個中間人攻擊。
就比如說有一個客戶端和一個服務端,客戶端請求服務端的某個服務,需要身份驗證,客戶端提供身份驗證,服務端響應,這原本是一次很正常的流程,但是如果加入了攻擊者這個角色,那么就變成了攻擊者發送同樣的消息給服務端,服務端進行響應,然后交給攻擊者,攻擊者返還給客戶端。
那么我們可以想象其實攻擊者就是充當了一個代理轉發點。
看一下如下圖:
攻擊者在客戶端和服務端的中間,也就是說你客戶端發送的無論是質詢,響應,認證,我攻擊者都是可以收到的,為什么會收到?,因為客戶端以為攻擊者是服務端,而正好相反,服務端以為攻擊者是客戶端,這就造成了,客戶端將數據給攻擊者,攻擊者再將數據發送給服務端,同樣服務端返回數據給攻擊者,攻擊者也返回數據給客戶端,那么這中間如果攻擊者對數據進行了修改,或者說發送給其他人了,并沒有發送給原來的客戶端,那么就可能造成了安全問題。

Ntlm Relay測試分析
這里的測試環境:
域:relaysec.com
user-win7 10.211.1.2
dc 10.211.1.210
kali 10.211.1.45
這里我們使用ntlmrelay.py
ntlmrelay.py可以將獲取到Ntlm中繼到內網的其他機器。
這里表示的意思就是,如果我獲取到了其他機器的SMB憑據,我中繼給1.2這臺機器。

緊接著我們到DC上面去請求一下攻擊者這臺機器。
去dir \10.211.1.45\addwadwa 只需要訪問到攻擊者的SMB服務即可。
我們這里wireshark抓包,我們需要著重注意紅框中的6個包。

他們分別代表著 協商,質詢,認證。

我們先來簡單看一下這個包,會發現其實攻擊者一直在做一個轉發的事情,攻擊者就是一個代理轉發點,一直轉發著客戶端和服務端的數據。
我們先來看第二組包,也就是DC給攻擊者發送質詢包的時候。

我們直接來看質詢值,會發現客戶端發送給攻擊者的質詢值和攻擊者發送給DC的質詢值是沒有改變的。這兩個包其實是一樣的。


也就是說當攻擊者收到這個請求的時候,他會原封不動的將包發送給210。
我們可以看到攻擊者只是在轉發東西,它只是將信息從客戶端傳遞到服務端,只是最后服務端以為攻擊者身份驗證成功,所以攻擊者可以代表DC去WIN7這臺機器上操作。
這里中間還有SSPI和NTLM SSP這里當作了解即可,可以看之前的NTLM協議那篇文章。
會話簽名
簽名其實就是一個校驗數據在發送期間有沒有被更改的方法,比如說張三給李四發送了一個hello world的文檔,并且對這個文檔進行了數字簽名,那么任何收到該文檔并且和他簽名(張三)的人都可以驗證編輯它的人是張三,并且可以確定他寫了這句話。因為簽名保證文檔沒有被修改,只要協議支持,簽名原則可以應用于任何協議,例如SMB協議,Ldap協議,HTTP等等,但是在實際情況中,HTTP前面很少實現。

簽名的意義就是當客戶端想要訪問服務的時候,由于攻擊者可以處在中間人的位置并且中繼身份信息,因此他可以在于服務器交互的時候冒充客戶端。這就是簽名發揮作用的時候。
在Ntlm中繼中,攻擊者想要偽造客戶端,但是他不知道的客戶端的密鑰,因此他就無法替客戶端做任何事情。由于攻擊者無法對任何數據包進行簽名,因此接收到數據包的服務端查看有沒有簽名或者說這個簽名對不對,如果不對或者沒有簽名的話,服務端直接拒絕攻擊者的請求。

所以說數據包必須在認證后進行簽名,那么攻擊者就攻擊不了了,因為他不知道客戶端的密鑰。
認證之后代表的是這個包: 協商->質詢->認證

但是客戶端和服務端如何才能達成一致的呢,就比如說我客戶端想要簽名,你服務端不知道我客戶端想要簽名,所以服務端如果不簽名的話,又是什么情況呢?
所以來到了NTLM的協商階段,也就是協商包唄。
NTLM 協商
這個協商包,我們之前已經再NTLM協議中了解過了這里直接來看他的標志位。
這里的有很多的協商標記,這里我在Ntlm協議哪里已經詳細解釋過了,我們這里主要看NEGOTIATE SIGN
這個協商標記設置的是1,他表示客戶端支持簽名,但是這并不代表服務端一定會簽署客戶端的數據包,只是客戶端有這個能力。
同樣當服務端回復的時候,如果支持簽名的話,這個標記位也是1。
所以說,這種協商只是客戶端向服務端表示我支持簽名,同樣服務端向客戶端表示我支持簽名,但是這并不意味著數據包就會被簽名,就比如說HTTP協議,即使客戶端和服務端都支持簽名,其實實際上也會很少簽名。

微軟提供了標記位,用于確定SMB數據包是否基于客戶端和服務端的設置來進行簽名,而對于SMBV2的版本是必須處理簽名的。
我們可以在HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\LanmanServer\Parameters注冊表中更改EnableSecuritySignature鍵和RequireSecuritySignature鍵,這兩個的值需要改成1。
注意:這里你不能只更改一臺機器為SMBV2,否則還是不簽名。
win7:

DC:

緊接著我們使用ntlmrelay.py工具進行攻擊。
可以發現已經明顯不行了。

我們來抓包看下:
首先這里我們不用kali來去做這個中繼,我們直接訪問1.2

然后進行抓包。
主要查看這兩個包。

可以看到10.211.1.210去訪問10.211.1.2的時候,簽名狀態。
這兩個值其實就是我們上面在注冊表中設置的值,我這里給10.211.1.210設置為了EnableSecuritySignature為1,RequireSecuritySignature為0。EnableSecuritySignature設置為1表示10.211.1.210支持簽名,RequireSecuritySignature設置為0表示我不用簽名。說的簡單點就是雖然我支持簽名,但是協商不簽名。但是如果服務端需要簽名的話,服務端可以處理我的簽名。
我們再來看服務端也就是10.211.1.2。
這里它表示我不僅支持簽名,我還需要簽名。

那么在協商階段的時候,客戶端和服務端將NEGOTIATE_SIGN標志設置為1,因為他們都支持簽名。完成身份驗證之后,會話繼續。

那么我們來測試一下,如果客戶端沒有設置簽名,但是服務端設置了簽名并且要求簽名,能不能中繼成功?(如下測試是對于SMBV1的)
顯然是不行的。

那么如果服務單沒有設置簽名,客戶端設置了簽名,能不能中繼成功?
我們發現是可以的。

wireshark如下抓包:

那么如果服務端支持簽名,但是不需要簽名,我們發現還是可以中繼成功的。
那么也就是說服務端需要既支持簽名又需要簽名,客戶端無論需不需要,都要簽名。
如上的測試只需要改注冊表的值即可,就是RequireSecuritySignature和EnableSecuritySignature這兩個值改為0或1。
Ldap簽名
Ldap簽名有3個級別。
- 禁用: 這意味著不支持數據包簽名。
- Negotiated Signing:此選項表示協商簽名,如果與他通信的機器也協商簽名,那么數據包就會被簽名。
- 必須簽名:這代表不僅支持簽名,而且必須對數據包進行簽名才能使會話繼續。
在域控中Ldap簽名是在HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\NTDS\Parameters/注冊表中的ldapserverintegrity選項,他的值可以為0,1,2分別代表著Ldap簽名的級別。默認他的值為1。

那么對于客戶端來說,Ldap簽名設置是在HKEY_LOCAL_MACHINE\System\CurrentControlSet\Services\ldap注冊表中。他的默認值也是1。

所以說服務端協商簽名,客戶端也協商簽名,所以,所有的Ldap數據包都會被簽名。(這里說的是Ldap的級別1)
那么如果一方需要簽名,而另一方不支持簽名,那么需要簽名的一方會忽略未簽名的數據包。(這里說的是Ldap級別2)
那么如果我們需要使用Ldap將身份驗證中繼到服務器,那么必須滿足兩個要求。
- 服務端不能設置為需要簽名,也就是Ldap的級別為2,默認情況下所有的機器都是協商簽名,而不是必須簽名。
- 客戶端不能設置NEGOTIATE_SIGN(SMB簽名)為1,如果設置了那么客戶端就希望簽名,因為攻擊者不知道客戶端的密鑰,所以就無法簽署數據包。
關于第二點,那么客戶端如果不設置此標記的話,那么是不是就可以中繼了呢?Windows SMB客戶端設置了它,默認情況下,我們無法將SMB身份驗證中繼到LDAP。
MIC簽名
這里目前有一個環境,就是說我這臺1.2機器上也就是服務端不僅支持簽名而且需要簽名,那么攻擊者就無法通過SMB進行中繼。
如下圖:

我們使用ntlmrelay.py進行中繼。可以看到是無法中繼的。

所以我們在想,既然不能中繼到SMB協議上,那么能不能中繼到其他協議?比如Ldaps協議。
Ldaps對應的端口是636。
我們都知道NEGOTIATE_SIGN標記是用于客戶端和服務端是否支持簽名的,但是在某些情況下,LDAP/LDAPS會考慮這個標記。
對于LDAPS來說,服務端也會考慮這個標志,如果服務端看到客戶端的NEGOTIATE_SIGN標記設置為1,那么服務端直接拒絕身份驗證,這是因為LDAPS也是基于TLS的LDAP,他是會處理數據包簽名的TLS層。
那么現在來說我們中繼的客戶端需要通過SMB進行身份驗證,但是它支持數據包簽名,它將NEGOTIATE_SIGN標志設置為了1,但是如果我們通過LDAPS來中繼身份驗證,但是LDAPS服務端也會看到這個標記,并且終止身份驗證。
也就是說無論是SMB還是LDAP/LDAPS,看到這個NEGOTIATE_SIGN標記位設置為了1,那么就會終止會話,因為攻擊者無法對數據包簽名,攻擊者不知道客戶端的密鑰。
那么我們能不能將這個標記給它干掉呢?就比如說給他刪掉,這鳥標記太煩人了。
但是這個標記我們干不掉,因為在它的上面還有一個NTLM級別的簽名,那么就是MIC簽名。
MIC簽名是如下計算的。
HMAC_MD5(Session key, NEGOTIATE_MESSAGE + CHALLENGE_MESSAGE + AUTHENTICATE_MESSAGE)
最重要的是會話密鑰是用客戶端的密鑰進行加密的,所以攻擊者無法計算MIC值。

所以說啊,如果把將NTLM消息這部分改了,那么MIC就不會生效了,所以我們無法更改NEGOTIATE_SIGN標記。
那么我們能不能將MIC給它干掉呢?這是可以的,因為MIC是可選的。
那么它通過什么來可選的呢?
它是通過msAvFlags值來進行可選的,如果他的值為0x00000002那么它就會告訴服務器必須存在MIC,如果不存在的話,就會直接終止身份驗證。
那么如果我們將msAvFlags的值設置為0,然后移除MIC,是不是可以呢?
這樣是不行的,因為當客戶端請求服務端質詢的時候,服務端返回NTLMV2 Hash,這個Hash它不僅僅考慮了質詢,而且還考慮了所有標志的HASH,所以說MIC存在的標志也是響應的一部分。
也就是說更改或者刪除MIC標記會使NTLMV2Hash無效。因為數據被修改之后它是這樣子的。

MIC保護了協商,質詢,認證這三條消息的完整性,而msAvFlags保護的是MIC的存在,NTLMv2 哈希保護標志的存在,因為攻擊者不知道客戶端的密鑰,所以不能計算這個Hash值。
所以這種情況下我們是不能攻擊的。
但是老外發現了一個相關的漏洞,CVE-2019-1040,它可以繞過NTLM MIC(消息完整性檢查)保護。
已經集成到了ntlmrelayx.py --remove-mic
我們來使用一下:
可以看到這里成功將user4用戶添加到企業管理組里面了,這里是通過SMB協議進行觸發的,中繼到了Ldap協議。這里中繼的是ldap,ldaps也是可以的,這里的ip是210,因為只有域控有Ldap服務。

如下圖可以看到user4已經是企業管理組的成員了。

CVE-2019-1040的漏洞范圍是:
Windows 7 sp1 至Windows 10 1903
Windows Server 2008 至Windows Server 2019
那么你如果使用Ldaps去中繼的時候會出現這樣的問題。
這是因為你沒有安裝證書服務導致的,所以在AD控制面板哪里添加功能,選擇證書服務。

如下圖: 可以百度搜索安裝ADCS證書服務。 這里可以參考:https://lework.github.io/2019/07/24/ad-install/#%E5%90%AF%E7%94%A8ldaps

之后我們使用LDP.exe連接Ldaps服務。
記得勾選上SSL即可。

緊接著我們再來Ldaps中繼,可以發現成功了。

通道綁定
那么通道綁定是干什么的呢?就如我們上面看到的,我們可以通過跨協議中繼,通道綁定就是為了解決這個問題。
其實就是將身份驗證和正在使用的協議綁定在一起,攻擊者就無法修改,如果客戶端希望對服務器進行身份驗證以及使用特定的服務,例如cifs等等,則將該標識性的信息添加到NTLM響應中,由于服務名稱在NTLM響應中,所以因此它受到NtProofStr響應的保護,該響應是此信息以及其實和MIC計算的那個msAvFlags值是差不多的,都是使用客戶端的密鑰進行計算的。
就比如說客戶端去請求服務端,客戶端已經在他的NTLM響應中指明了他要訪問的服務,并且由于攻擊者無法修改它,當攻擊者將請求中繼給服務端的時候,將攻擊者請求的SMB服務,和 NTLM響應中的HTTP服務進行對比,發現是不同的服務,所以直接拒絕連接。
如下圖,客戶端在NTLM響應中加了要訪問的服務,攻擊者如果中繼給服務端是其他服務的話,那么服務端就會直接拒絕連接。

具體來說所謂服務其實就是SPN,之前的文檔里面講過。
可以看到它使用的是CIFS服務,也就是SMB協議,,不僅有服務名稱 (CIFS),還有目標名稱或 IP 地址。這意味著如果攻擊者將此消息中繼到服務器,服務器也會檢查目標部分,并會拒絕連接,因為在 SPN 中找到的 IP 地址與他的 IP 地址不匹配。因此,如果所有客戶端和所有服務器都支持這種保護,并且每臺服務器都需要這種保護,那么它可以減少所有中繼嘗試。

那么怎么設置呢???
默認win2012是沒有這個東西,網上資料顯示是win10才新加的策略。
參考:https://learn.microsoft.com/zh-cn/windows/security/threat-protection/security-policy-settings/domain-controller-ldap-server-channel-binding-token-requirements
那些協議可以中繼
NEGOTIATE_SIGN如果不需要簽名,則任何未設置標記的客戶端都可以中繼到Ldap。

NTLMV1的危害
在NTLMV2中,NTLMV2哈希考慮了msAvFlags標記位,MIC字段,還有NetBios名稱的字段等等,但是NTLMV2的哈希是沒有任何附加信息的,例如沒有MIC,目標名稱,SPN等等。因此如果服務端允許NTLMV1身份驗證的話,攻擊者可以直接移除MIC字段,從而將身份驗證中繼到Ldap或Ldaps。
但更重要的是,他可以發出 NetLogon 請求以檢索會話密鑰。確實,域控制器沒有辦法檢查他是否有權這樣做。而且由于它不會阻止不是完全最新的生產網絡,它會出于“復古兼容性原因”將其提供給攻擊者。
這一點可以在ZeroLogon這個漏洞中進行體現。
總結
SMB V1中繼到SMBV1 服務端如果沒有設置簽名,也就是RequireSecuritySignature和EnableSecuritySignature這兩個值。那么就可以中繼成功,無論客戶端是否支持簽名還是需要簽名,是可以中繼成功的。
SMBV2默認需要簽名。
跨協議中繼,SMBV2中繼到Ldap服務,這是利用了CVE-2019-1040這個漏洞,這個漏洞可以繞過MIC簽名。
SMBV2中繼到Ldaps服務,需要安裝ADCS證書服務。
通道綁定可以解決跨協議中繼的問題,將服務的標識放在了NTLM響應中,從而和服務端的服務進行對比。
Andrew
Anna艷娜
安全俠
Andrew
Anna艷娜
虹科網絡安全
安全俠
RacentYY
FreeBuf
X0_0X