- NTLM(New Technology LAN Manager)身份验证协议是微软用于Windows身份验证的主要协议之一。早起SMB协议以明文口令的形式在网络上传输,因此产生了安全性题目。厥后出现了LM(LAN Manager)身份验证协议,它非常简单以至于很容易就被破解。厥后微软提出了NTLM身份验证协议,以及更新的NTLM V2版本。NTLM协议既可以为工作组中的机器提供身份验证,也可以用于域环境身份验证。NTLM协议可以为SMB、HTTP、LDAP、SMTP等上层微软应用提供身份认证。
SSP和SSPI概念
1、SSPI
SSPI(Security Service Provider Interface 或 Security Support Provider
Interface,安全服务提供接口) 是Windows定义的一套接口,该接口定义了与安全有关的功能函数,包括但不限于:
- 身份认证机制
- 为其他协议提供的Session security机制。Session security指的是会话安全,即为通讯提供数据完备性校验以及数据的加解密功能
SSPI接口定义了与安全有关的功能函数,用来获取验证、信息完备性、信息隐私等安全功能,该接口知识定义了一套接口函数,但是并没有实现具体的内容。
2、SSP
SSP(Security Service Provider,安全服务提供者)
是SSPI的实现者,微软自己实现了如下的SSP,用于提供安全功能,包括但不限于:
- NTLM SSP:Windows NT 3.51中引入(msv1_0.dll),为Windows 2000之前的客户端-服务器域和非域身份验证(SMB/CIFS)提供NTLM质询/响应身份验证。
- Kerberos SSP:Windows 2000中引入,Windows vista中更新为支持AES(kerberos.dll),Windows 2000及更高版本中首选的客户端-服务器域相互身份验证。
- Digest SSP:Windows XP中引入(wdigest.dll),在Windows与kerberos不可用的非Windows体系间提供基于HTTP和SASL身份验证的质询/响应。
- Negotiate SSP:Windows 2000 中引入(secur32.dll) ,默认选择 Kerberos,假如不可用则选择 NTLM 协议。Negotiate SSP 提供单点登录 本领,有时称为集成 Windows 身份验证(尤其是用于 IIS 时)。在 Windows 7 及更高版本中,NEGOExts 引入了协商使用客户端和服务器上 支持的已安装定制 SSP 举行身份验证。
- Cred SSP:Windows Vista 中引入,Windows XP SP3 上也可用 (credssp.dll),为远程桌面毗连提供单点登录(SSO)和网络级身份验证。
- Schannel SSP:Windows 2000 中引入(Schannel.dll),Windows Vista 中 更新为支持更强的 AES 加密和 ECC[6]该提供者使用 SSL/TLS 记录来加密 数据有用载荷。
- PKU2U SSP:Windows 7 中引入(pku2u.dll) , 在不隶属域的体系之间提 供使用数字证书的对等身份验证。
由于SSPI中定义了与Session
Security有关的API。所以上层应用使用任何SSP与远程的服务举行了身份验证后,此SSP都会为本次毗连天生一个随机Key。这个随机Key被称为Session
Key。上层应用颠末身份验证后,可以选择性的使用这个Key对之后发往客户端或担当自服务端的数据举行签名或加密。在体系层面,SSP就是一个dll,用来实现身份验证登安全功能。差别的SSP,实现的身份验证机制是不一样的。好比NTLM
SSP实现的就是一种基于质询/响应身份验证机制,而Kerberos
SSP实现的就是基于Ticket票据的身份验证机制。可以自定义编写SSP,然后注册到利用体系中,让利用体系支持自定义的身份验证方法。
LM Hash加密算法
LM(LAN Manager)身份认证是微软推出的一个身份认证协议,其使用的机密算法是LM Hash加密算法。LM Hash本质是DES加密,尽管LM
Hash较容易被破解,但为了保证体系的兼容性,Windows只是将LM Hash禁用了(Windows Vista和Windows Server
2008开始,Windows默认禁用了LM Hash)。LM Hash明文暗码被限定在14位以内,也就是说,假如要停止使用LM
Hash,将用户的暗码设为14位以上即可。
LM Hash的值为:aad3b435b51404eeaad3b435b51404ee,阐明LM Hash为空值或者被禁用了。
LM Hash加密流程:
- 将用户的明文口令转换为大写,并转换为16进制字符串。
- 假如转换后的16进制字符串的长度不敷14字节(长度28),用0补全。
- 将14字节分为两组,每组7字节转换为二进制数据,每组二进制数据长度为56比特位。
- 将每组二进制数据按7比特位为一组,分为8组,每组末尾加0,在转换成16进制,如许每组也就成了8字节长的16进制数据。
- 将上面天生的16进制数据,分别作为DES加密秘钥对字符串“KGS!@#$%”举行加密,然后将加密后的两组密文举行拼接,得到最终的LM Hash值
加密实当代码:
- # coding=utf-8
- import base64
- import binascii
- from pyDes import *
- import hashlib,binascii
- import md5
- def DesEncrypt(str, Des_Key):
- k = des(Des_Key, ECB, pad=None)
- EncryptStr = k.encrypt(str)
- return binascii.b2a_hex(EncryptStr)
- def Zero_padding(str):
- b = []
- l = len(str)
- num = 0
- for n in range(l):
- if (num < 8) and n % 7 == 0:
- b.append(str[n:n + 7] + '0')
- num = num + 1
- return ''.join(b)
- if __name__ == "__main__":
- test_str = raw_input("please input a string: ")
- # 用户的密码转换为大写
- test_str = test_str.upper()
- print('\033[91m'+"转换为大写:"+'\033[0m')
- print(test_str)
- #转换为16进制字符串
- test_str = test_str.encode('hex')
- print('\033[91m'+"转换为16进制字符串:"+'\033[0m')
- print(test_str)
- str_len = len(test_str)
- # 密码不足14字节将会用0来补全
- if str_len < 28:
- test_str = test_str.ljust(28, '0')
- print('\033[91m'+"不足14字节(长度28),用0来补全:"+'\033[0m')
- print(test_str)
- # 固定长度的密码被分成两个7byte部分
- t_1 = test_str[0:len(test_str) / 2]
- t_2 = test_str[len(test_str) / 2:]
- print('\033[91m'+"将14字节分为两组,每组7字节"+'\033[0m')
- print(t_1)
- print(t_2)
- # 每部分转换成比特流,并且长度位56bit,长度不足使用0在左边补齐长度
- t_1 = bin(int(t_1, 16)).lstrip('0b').rjust(56, '0')
- t_2 = bin(int(t_2, 16)).lstrip('0b').rjust(56, '0')
- print('\033[91m'+"转换为二进制数据,每组二进制数据长度为56比特位"+'\033[0m')
- print(t_1)
- print(t_2)
- # 再分7bit为一组末尾加0,组成新的编码
- t_1 = Zero_padding(t_1)
- t_2 = Zero_padding(t_2)
- print('\033[91m'+"将每组二进制数据按7比特位为一组,分为8组,每组末尾加0"+'\033[0m')
- print(t_1)
- print(t_2)
- # print t_1
- t_1 = hex(int(t_1, 2))
- t_2 = hex(int(t_2, 2))
- t_1 = t_1[2:].rstrip('L')
- t_2 = t_2[2:].rstrip('L')
- print('\033[91m'+"两组分别转换为16进制字符串"+'\033[0m')
- print(t_1)
- print(t_2)
- if '0' == t_2:
- t_2 = "0000000000000000"
- t_1 = binascii.a2b_hex(t_1)
- t_2 = binascii.a2b_hex(t_2)
- # 上步骤得到的8byte二组,分别作为DES key为"KGS!@#$%"进行加密。
- LM_1 = DesEncrypt("KGS!@#$%", t_1)
- LM_2 = DesEncrypt("KGS!@#$%", t_2)
- print('\033[91m'+"上步骤得到的8byte二组,分别作为DES key为"KGS!@#$%"进行加密"+'\033[0m')
- print("LM_1:"+LM_1)
- print("LM_1:"+LM_2)
- # 将二组DES加密后的编码拼接,得到最终LM HASH值。
- print('\033[91m'+"将二组DES加密后的编码拼接,得到最终LM HASH值"+'\033[0m')
- LM_Hash = LM_1 + LM_2
- print ("LM_Hash:"+LM_Hash)
复制代码 
NTLM Hash加密算法
为了解决LM Hash加密和身份验证方案中的安全缺点,微软与1993年在Windows NT 3.1中首次引入了NTLM Hash。微软从Windows
Vista和Windows 2008开始,默认禁用了LM Hash,只存储NTLM Hash,而LM Hash的位置则为空。
NTLM Hash算法是微软为了在提高安全性的同时保证兼容性而设计的散列加密算法。NTLM Hash是基于MD4加密算法举行加密的。
1、NTLM加密流程
NTLM Hash是由明文暗码颠末三步加密而成:
NTLM Hash =md4(unicode(hex(password)))
NTLM Hash的加密流程分为三步,具体如下:
- 先将用户暗码转换为16进制格式
- 再将16进制格式的字符串举行ASCII转Unicode编码
- 最后对Unicode编码的16进制字符串举行标准MD4单向哈希加密
实当代码:
- # coding=utf-8
- from Cryptodome.Hash import MD4
- import binascii
- from cprint import cprint
- #转为16进制格式
- def str_to_hex(string):
- return ' '.join([hex(ord(t)).replace('0x', '') for t in string])
- #再将16进制格式的字符串进行ASCII转Unicode编码
- def hex_to_unicode(string):
- return string.replace(" ","00")+"00"
- #最后对Unicode编码的16进制字符串进行标准MD4单向哈希加密
- def unicode_to_md4(string):
- m = MD4.new()
- m.update(binascii.a2b_hex(string))
- return m.hexdigest()
- if __name__ == "__main__":
- string = input("please input a string: ")
- HEX = str_to_hex(string)
- cprint.err("HEX编码:")
- print(HEX)
- Unicode = hex_to_unicode(HEX)
- cprint.err("ASCII转Unicode编码")
- print(Unicode)
- NTLm_Hash = unicode_to_md4(Unicode)
- cprint.err("对Unicode编码的16进制字符串进行标准MD4单向哈希加密得到NTLM Hash")
- print(NTLm_Hash)
复制代码 
或者使用Python命令举行加密
- python3 -c 'import hashlib,binascii; print("NTLM_Hash:"+binascii.hexlify(hashlib.new
- ("md4", "123456".encode("utf-16le")).digest()).decode("utf-8"))'
复制代码 
2、Windows体系存储的NTLM Hash
用户暗码颠末NTLM Hash机密后存储在 %SystemRoot%\system32\config\SAM 文件里。
当用户输入暗码举行本地认证的过程中,所有的利用都是在本地举行的。体系将用户输入的暗码转换为NTLM Hash,然后与SAM文件中的NTLM
Hash举行比较,相同阐明暗码精确,反之错误。当用户注销、重启、锁屏后,利用体系会让winlogon.exe显示登录界面,也就是输入框。当winlogon.exe接收收入后,将暗码交给lsass.exe进程,lsass.exe进程中会存一份明文暗码,将明文暗码加密成NTLM
Hash,与SAM数据库举行比较认证。使用mimikatz就是从lsass.exe进程中抓取明文暗码或暗码Hash。
一样平常抓取到的暗码格式第一部门是用户名,第二部门是用户的SID值,第三部门是LM Hash,第四部门是NTLM Hash,其余部门为空。
NTLM协议认证
NTLM身份认证协议是一种基于Challenge/Response质询响应验证机制,由三种范例消息构成。
- type 1(协商,Negotiate)
- type 2(质询,Challenge)
- type 3(认证,Auth)
NTLM身份认证协议有NTLM v1和NTLM v2两个版本,目前使用最多的是NTLM
v2版本。他们之间最显着的区别就是Challenge质询值与加密算法差别,共同之处就是都是使用NTLM Hash举行加密。
1、工作组环境下的NTLM认证
工作组环境下NTLM认证流程可以分为4个步骤
- 当客户端需要访问服务器的某个服务时,就需要举行身份认证。于是,当客户端输入服务器的用户名和暗码举行验证的时候,客户端就会缓存服务器暗码的NTLM Hash值。然后,客户端会向服务端发送一个请求,该请求使用NTLM SSP天生NTLMSSP_NEGOTIATE消息(被称为Type 1 NEGOTIATE协商消息)
- 服务端接收到客户端发送过来的Type 1消息后,会读取其中的内容并从中选择出自己所能接收的服务内容,加密等级,安全服务等。然后传入NTLMSSP,得到NTLMSSP_CHALLENGE消息(被称为Type 2 Challenge质询消息),并将此Type 2 消息发回客户端。此Type 2消息中包罗了一个由服务端天生的16位随机值,此随机值被称为Challenge质询值,服务端会将该Challenge质询值缓存起来。
- 客户端收到服务端返回的 Type 2 消息后,读取出服务端所支持的内容,并取 出其中的 Challenge 质询值,用缓存的服务器暗码的 NTLM Hash 对其举行加密得 到 Response 消息。最后将 Response 和一些其他信息封装到 NTLMSSP_AUTH 认证消息中(被称为 Type 3 Authenticate 认证消息),发往服务端。
- 服务端在收到 Authenticate 认证消息后,从中取出 Net-NTLM Hash。然后 用自己暗码的 NTLM Hash 对 Challenge 质询值举行一系列加密运算,得到自己 计算的 Net-NTLM Hash。并比较自己计算出的 Net-NTLM Hash 和客户端发送 的 Net-NTLM Hash 是否相等。假如相等,则证明客户端输入的暗码精确,从而 认证乐成,反之则认证失败。
2、域环境下的NTLM认证
域环境下的NTLM认证流程可以分为6个步骤:
- 客户端想要访问服务器的某个服务,需要举行身份认证。于是,在客户端输入 服务器的用户名和暗码举行验证之后,客户端会缓存服务器暗码的 NTLM Hash 值。然后,客户端会向服务端发送一个请求,该请求使用 NTLM SSP 天生 NTLMSSP_NEGOTIATE 消息(被称为 Type 1 NEGOTIATE 协商消息)
- 服务端接收到客户端发送过来的 Type 1 消息,会读取其中的内容,并从中选 择出自己所能担当的服务内容,加密等级,安全服务等。然后传入 NTLM SSP, 得到 NTLMSSP_CHALLENGE 消息(被称为 Type 2 Challenge 质询消息),并 将此 Type 2 消息发回给客户端。此 Type 2 消息中包罗了一个由服务端天生的 16 位随机值,此随机值被称为 Challenge 质询值,服务端将该 Challenge 值缓存起来。
- 客户端收到服务端返回的 Type 2 消息,读取出服务端所支持的内容,并取出 其中的 Challenge 质询值,用缓存的服务器暗码的 NTLM Hash 对其举行加密得到 Response 消息,Response 消息中可以提取出 Net-NTLM Hash。最后将Response 和一些其他信息封装到 NTLMSSP_AUTH 消息中(被称为 Type 3 Authenticate 认证消息),发往服务端。
- 服务端接收到客户端发送来的 NTLMSSP_AUTH 认证消息后,通过 Netlogon 协议与域控创建一个安全通道,将验证消息发给域控。
- 域控收到服务端发来的验证消息后,从中取出 Net-NTLM Hash。然后从数据 库中找到该用户的 NTLM Hash,对 Challenge 举行一系列加密运算,得到自己计 算的 Net-NTLM Hash。并比较自己计算出的 Net-NTLM Hash 和服务端发送的 Net-NTLM Hash 是否相等,假如相等,则证明客户端输入的暗码精确,认证成 功,反之认证失败,域控将验证效果发给服务端。
- 服务端根据 DC 返回的效果,对客户端举行回复。
3、NTLM v1和NTLM v2的区别
NTLM v1 身份认证协议和 NTLM v2 身份认证协议是 NTLM 身份认证协议的差别版本。目前使用最多的是 NTLM v2 版本。NTLM v1 与
NTLM v2 最显着的区别就 是 Challenge 质询值与加密算法差别,共同之处就是都是使用的 NTLM Hash 进 行加密。
Challenge质询值
- NTLM v1 :8字节
- NTLM v2 : 16字节
Net-NTLM Hash使用的加密算法
- NTLM v1:DES加密算法
- NTLM v2:HMAC-MD5加密算法
4、LmCompatibilityLevel
LmCompatibilityLevel 值用来确定网络登录使用的质询/响应身份验证协议。此选
项会影响客户端使用的身份验证协议的等级、协商的会话安全的等级以及服务器接 受的身份验证的等级,如下是 LmCompatibilityLevel
为差别值的含义:
值含义0客户端使用 LM 和 NTLM 身份验证,但从不使用 NTLM v2 会话安全性。域控制器担当 LM、NTLM 和 NTLM v2身份验证。1客户端使用 LM 和 NTLM 身份验证,假如服务器支持 NTLM v2 会话安全性,则使用 NTLM v2 会话安全性。域控制器担当 LM、NTLM和 NTLM v2 身份验证。2客户端仅使用 NTLM 身份验证,假如服务器支持 NTLM v2 会话安全性,则使用 NTLM v2 会话安全性。域控制器担当 LM、NTLM 和NTLM v2 身份验证。3客户端仅使用 NTLM v2 身份验证,假如服务器支持 NTLM v2 会话安全性,则使用 NTLM v2 会话安全性。域控制器担当 LM、NTLM和 NTLM v2 身份验证。4客户端仅使用 NTLM v2 身份验证,假如服务器支持 NTLM v2 会话安全性,则使用 NTLM v2 会话安全性。域控制器拒绝 LM身份验证,但担当 NTLM 和 NTLM v2 身份验证。5客户端仅使用 NTLM v2 身份验证,假如服务器支持 NTLM v2 会话安全性,则使用 NTLM v2 会话安全性。域控制器拒绝 LM 和NTLM 身份验证,但担当 NTLM v2 身份验证。 如何手动举行修改?
打开本地安全策略–》安全设置–》本地策略–》安全选项–》网络安全 AN管理器身份验证级别,默认其值是没有定义的,使用默认值
NTLM协议的安全题目
从上面 NTLM 认证的流程中我们可以看到,在 Type 3 Auth 认证消息中是使用用户暗码的 Hash
计算的。因此当我们没有拿到用户暗码的明文而只拿到 Hash 的环境下,我们可以举行 **Pass The
Hash(PTH)攻击,也就是哈希传递攻击。同样,还是在 Type3 消息中,存在 Net-NTLM Hash,当攻击者得到了 Net- NTLM
Hash 后,可以举行中心人攻击,重放 Net-NTLM Hash,这种攻击手法也就是 NTLM Relay(NTLM 中继)**攻击。并且由于
NTLM v1 版本协议加 密过程存在天然缺陷,可以对 Net-NTLM v1 Hash 举行爆破,得到 NTLM Hash。拿到 NTLM Hash
后即可举行横向移动。
1、Pass The Hash
Pass The Hash(PTH)哈希传递攻击是内网横向移动的一种方式。主要原因是 NTLM 认证过程中使用的是用户暗码的 NTLM Hash
来举行加密。因此当我们获取到了用户暗码的 NTLM Hash 而没有解出明文时,我们可以使用该 NTLM Hash 举行哈希传递攻击,对内网其他机器举行
Hash 碰撞,碰撞到使用相同暗码的机器。然后通过 135 或 445 端口横向移动到使用该暗码的其他机器。
2、NTML Relay
NTLM Relay 其实严格意义上并不能叫 NTLM Relay,而是应该叫 Net-NTLM Relay。它是发生在 NTLM 认证的第三步,在
Response 消息中存在 Net-NTLM Hash,当攻击者得到了 Net-NTLM Hash 后,可以举行中心人攻击,重放 Net- NTLM
Hash,这种攻击手法也就是 NTLM Relay(NTLM 中继)攻击。
3、Net-NTLM v1 Hash破解
由于 NTLM v1 身份认证协议加密过程存在天然缺陷,只要获取到 Net-NTLM v1 Hash,都能破解为 NTLM
hash,这与暗码强度无关。在域环境中这更有用,由于域中使用 hash 即可远程毗连目的机器。假如域控答应发送 NTLM v1 响应的话,
我们就可以通过与域控机器举行 NTLM 认证,然后抓取域控的 Net-NTLM v1 Hash,破解为 NTLM
Hash。使用域控的机器账号和哈希即可导出域内所有用户哈希。
最后
从期间发展的角度看,网络安全的知识是学不完的,而且以后要学的会更多,同砚们要摆正心态,既然选择入门网络安全,就不能仅仅只是入门水平而已,本领越强机会才越多。
由于入门学习阶段知识点比较杂,所以我讲得比较笼统,大家假如有不懂的地方可以找我咨询,我保证知无不言言无不尽,需要相干资料也可以找我要,我的网盘里一大堆资料都在吃灰呢。
干货主要有:
①1000+CTF历届题库(主流和经典的应该都有了)
②CTF技能文档(最全中文版)
③项目源码(四五十个风趣且经典的练手项目及源码)
④ CTF大赛、web安全、渗出测试方面的视频(得当小白学习)
⑤ 网络安全学习路线图(告别不入流的学习)
⑥ CTF/渗出测试工具镜像文件大全
⑦ 2023暗码学/隐身术/PWN技能手册大全
假如你对网络安全入门感兴趣,那么你需要的话可以点击这里 |