Is there any way to convert NetNTLMv2 to ntlm hashes? For instance ntlm value of the 123 is
3DBDE697D71690A769204BEB12283678
Same password for user "try" in computer "PC" which has private ip address 192.168.73.130 NetNTLMv2 value is
try::PC:d158262017948de9:91642a8388d64d40f6c31b694e79363e:010100000000000058b2da67cbe0d001c575cfa48d38bec50000000002001600450047004900540049004d002d00500043003100340001001600450047004900540049004d002d00500043003100340004001600650067006900740069006d002d00500043003100340003001600650067006900740069006d002d0050004300310034000700080058b2da67cbe0d0010600040002000000080030003000000000000000000000000030000065d85a4000a167cdbbf6eff657941f52bc9ee2745e11f10c61bb24db541165800a001000000000000000000000000000000000000900240063006900660073002f003100390032002e003100360038002e0031002e00310030003700000000000000000000000000
Can we convert this NetNTLMv2 to NTLM (3DBDE697D71690A769204BEB12283678
) without knowing any credentials?
There is no answer :) But it is ok, because I did a little research and found the answer. For now, there is no way to convert NetNTLMv2 to NTLM. Actually NTLM hash is the first key to generate NetNTLMv2. I decided to explain how it works.
To calculate and compare NTLMv2 you should first calculate the NTLM value of the password which is 123
in this case. To demonstrate it, I'll use python 2.7. Before starting you should import those modules hashlib, binascii, hmac
.
NTLM value of 123
calculated with python like this:
_ntlm = hashlib.new("md4", "123".encode("utf-16-le")).digest()
ntlm = binascii.hexlify(_ntlm)
The result is 3dbde697d71690a769204beb12283678
and this value will be used as key for the first HMAC_MD5 calculation.
To do that we should concatenate the user name and domain name. If you don't work on the domain, you'll use your computer name. In this case, my username is try
and my computer name is PC
.
When we concatenate it, it'll become tryPC
. Then this value is converted into unicode uppercase in little-endian format. We'll generate HMAC_MD5 hash of this value with using NTLM of 123
as a key.
"tryPC"==> "TRYPC" ==> '54005200590050004300' (UTF-16-le in hexadecimal)
We calculate this in Python like:
"tryPC".upper().encode("utf-16-le").encode("hex")
Then we calculate HMAC_MD5(54005200590050004300) with key 3dbde697d71690a769204beb12283678
In python it is calculated like this:
firstHMAC = hmac.new("3dbde697d71690a769204beb12283678".decode("hex"),"54005200590050004300".decode("hex"),hashlib.md5).hexdigest()
firstHMAC ==> 2381ca3f5e9c4534722cd511f6a4c983
After that we'll use firstHMAC as a key to calculate the HMAC_MD5 value of the Type2 challenge.
Type2 challenge is combined with server challenge and blob.
Network response for NetNTLMv2 is like this:
try::PC:d158262017948de9:91642a8388d64d40f6c31b694e79363e:010100000000000058b2da67cbe0d001c575cfa48d38bec50000000002001600450047004900540049004d002d00500043003100340001001600450047004900540049004d002d00500043003100340004001600650067006900740069006d002d00500043003100340003001600650067006900740069006d002d0050004300310034000700080058b2da67cbe0d0010600040002000000080030003000000000000000000000000030000065d85a4000a167cdbbf6eff657941f52bc9ee2745e11f10c61bb24db541165800a001000000000000000000000000000000000000900240063006900660073002f003100390032002e003100360038002e0031002e00310030003700000000000000000000000000
When we split this response according to :
index 3 is the server challenge which is d158262017948de9
Index 5 which starts like "01010000..."
indicates the blob value. Blob value also consists of blob signature, reserved fields, timestamp, random client nonce and target information. I don't give detail about the blob.
To calculate NTLMv2 we should concatenate the server challenge and the blob to calculate the HMAC_MD5 value of this by using firstHMAC
as a key.
In Python we do that like this:
firstHMAC = "2381ca3f5e9c4534722cd511f6a4c983"
type2Challange = "d158262017948de9010100000000000058b2da67cbe0d001c575cfa48d38bec50000000002001600450047004900540049004d002d00500043003100340001001600450047004900540049004d002d00500043003100340004001600650067006900740069006d002d00500043003100340003001600650067006900740069006d002d0050004300310034000700080058b2da67cbe0d0010600040002000000080030003000000000000000000000000030000065d85a4000a167cdbbf6eff657941f52bc9ee2745e11f10c61bb24db541165800a001000000000000000000000000000000000000900240063006900660073002f003100390032002e003100360038002e0031002e00310030003700000000000000000000000000"
ntlmv2 = hmac.new(firstHMAC.decode("hex"),type2Challange.decode("hex"),hashlib.md5).hexdigest()
ntlmv2 ==> 91642a8388d64d40f6c31b694e79363e
If this value is equal to the 4th index of the NetNTLMv2 response, you'll be verified. In this case, the 4th index is equal to 91642a8388d64d40f6c31b694e79363e
and that means you have the correct password.
According to server challenge and blob value, you'll always get the different NTLMv2 value and you only can calculate this if you have the correct password.
In other words, we can produce NetNTLMv2 with NTLM. However, we cannot convert back NetNTLMv2 to NTLM because [cryptographic] hash functions are one-way functions.