第二章-Windows认证机制和协议

<1> Windows认证

(1) Windows认证基础

windows的认证包括三个部分:

  • 本地认证:用户直接操作计算机登录账户
  • 网络认证:远程连接到工作组中的某个设备
  • 域认证:登录到域环境中的某个设备

windows认证和密码的抓取可以说是内网渗透的第一步

(2) windows本地认证

电脑上存储着自己的账号密码,无论电脑是否联网、通外网,只要能开机,就可以输入账号密码登录到电脑中,工作组就是采用本地认证

Windows的登陆密码是储存在系统本地的SAM文件中的,在登陆Windows的时候,系统会将用户输入的密码与 SAM文件中的密码进行对比,如果相同,则认证成功

SAM文件是位于 %SystemRoot%\system32\config\ 目录下的,用于储存本地所有用户的凭证信息

image-20230925161844633

Windows本地认证流程

image-20230926160137492

其中:

  • Windows Logon Process(即winlogon.exe):是Windows NT 用户登陆程序,用于管理用户登陆和退出

    image-20230925181215606

  • LSASS:一个系统进程,用于微软Windows系统的安全机制,它用于本地安全和登陆策略

用户注销、重启、锁屏后,操作系统会让winlogon.exe 显示开机登陆界面,接收用户的输入信息后,将密码交给lsass进程,这个过程中会存一份明文密码,将明文密码加密成NTLM Hash,对SAM数据库进行比较认证

(3) SAM文件和lsass.exe进程详解

SAM文件是Windows的用户账户数据库,所有用户的登录名及口令等相关信息都会保存在这个文件里,格式如下:

用户名称:LM-HASH值:NTLM-HASH值

注:SAM文件中的密码并不是以明文的形式存在,他是加密后存储在SAM文件中

Lsass.exe的进程作用非常重要,它主要负责管理本地安全策略和认证机制。这些策略包括 密码策略、账户策略、用户权限、域策略等等。同时,它还负责对用户进行身份认证,以确保只有授权的用户才能访问系统资源

  1. 将 winlogon.exe 传过来的明文账号密码进行加密,然后和SAM文件中的密文账号密码作比对。比对成功则登录成功
  2. 将收到的明文账号密码在本地内存中保留一份备用 (因此可以在内存抓明文密码)

image-20230925181148045

(4) 有什么方式读取SAM文件

  1. 在线读取(如果有杀软,读取工具可能会被杀,需要绕杀软)

    1
    2
    # 使用mimikatz在线读
    mimikatz.exe "privilege::debug" "token::elevate" "lsadump::sam" exit

    image-20230927092605911

  2. 离线读取(文件复制到你的电脑上,不需要绕过杀软)

    1
    2
    3
    4
    5
    6
    7
    reg save hklm\sam sam.hive
    reg save hklm\system system.hive

    mimikatz.exe "lsadump::sam /sam:sam.hive /system:system.hive"

    # nishang的copy-vss进行复制 如果脚本运行在DC上,ntds.dit和SYSTEM hive也能被dump出来
    copy-vss # 文件会直接保存在当前路径下

    弊端:有的文件过大,传输过程容易中断

    image-20230927093307265

实际上,能不能离线破解出来这个明文密码都一样 拿到NTLM Hash值即可 因为Windows上的认证都是对这个值认证的,后面的 PTH 哈希传递攻击时会提到。administrator是肯定可以利用进行PTH的。

(5) 有什么方式读取lsass进程

  • 在线读取 lsass进程

    从 lsass进程中提取 passwords、keys、pin、tickets等信息

    1
    2
    3
    4
    5
    6
    7
    8
    privilege::debug
    sekurlsa::msv # 获取HASHLMNTLM
    sekurlsa::wdigest # 通过可逆的方式去内存中读取明文密码
    sekurlsa::kerberos # 如果域管理员登录了我们电脑,可以以此来获取域管的明文密码
    sekurlsa::tspkg # 通过tspkg来获取明文密码
    sekurlsa::livessp # 通过livessp 读取明文密码啊
    sekurlsa::ssp # 通过ssp读取明文密码
    sekurlsa::logonPasswords # 通过上述各种方式读取明文密码

    image-20230927100145327

  • 离线读取 lsass进程

    lsass.exe系统进程 在任务管理器中可以看到。 实际上我们可以 右键-> 创建存储文件

    image-20230927100548564

    image-20230927100902536

    也可以用工具 procedump

    1
    procdump64.exe -accepteula -ma lsass.exe lsass.dmp

    复制出来本地使用mimikatz 读取 lsass.dmp文件

    1
    mimikatz.exe "sekurlsa::minidump lsass.dmp" "sekurlsa::logonPasswords full"

上面两种方式都可以看到,读取了 NTLM的值,但是明文密码那却是 (null)

为什么会这样呢?

高版本弃用了LM,同时也不再往内存里写入明文密码

<2> Windows LM和NTLM哈希加密过程

(1) LM HASH值介绍

Windows操作系统通常使用两种方法对用户明文密码进行加密处理。一部分为 LM-Hash,另一部分为NTLM-Hash。 在域环境中,用户信息存储在ntds.dit中,加密后为散列值

Hash结构:username:RID:LM-HASH:NT-HASH

LM Hash 全名为 “LAN Manager Hash” ,是微软为了提高Windows操作系统的安全性而采用的散列加密算法,其本质是 DES 加密。尽管LM Hash 比较容易破解,但为了保证系统的兼容性,Windows 只是将 LM Hash禁用了(从 Windows vista 和 Windows Server2008版本开始,Windows操作系统默认禁用LM Hash)。

LM Hash明文密码被限定在14位以内,即如果要停止使用 LM Hash,将用户密码设置成14位以上即可。 如果LM Hash被禁用了,攻击者通过工具抓取的LM Hash通常 为 “ad3435b51404eead3b435b51404ee” (表示LM Hash为空值或被禁用)

NTLM Hash是微软为了在提高安全性的同时,保证兼容性而设计的散列加密算法。NTLM Hash是基于 MD4加密算法进行加密的。个人版的Windows vista 以后,服务器版从 Windows Server2003 以后,Windows 操作系统的认证方式均为 NTLM Hash

为了解决加密和身份验证方案中固有的安全弱点,Microsoft 于 1993年在Windows NT 3.1 中引入了NTLM协议。下面是各个版本对 LM Hash和 NTLM Hash的支持

加密类型 2000 XP 2003 Vista Win7 2008 Win8 2012 Win10 2016 Win11
LM-Hash 1 1 1 1
NTLM-Hash 1 1 1 1 1 1 1

(2) LM Hash加密原理

假设我们 administrator的密码为 Admin@123

加密过程如下:

  1. 将明文口令转换为其大写形式

    即 Admin@123 -> ADMIN@123

  2. 将字符串大写后转换为16进制字符串

    41 44 4D 49 4E 40 31 32 33

  3. 密码不足14字节要求用0补全,密码为9个字符,还差5个 补00

    补全后为:41 44 4D 49 4E 40 31 32 33 00 00 00 00 00

  4. 然后将上述编码分成2组7字节

第一组:41 44 4D 49 4E 40 31

第二组:32 33 00 00 00 00 00

  1. 再将每一组7字节的十六进制转换为二进制,每7bit 一组末尾加0,在转换成十六进制组成得到2组8字节的编码

    第一组:0100 0001 0100 0100 0100 1101 0100 1001 0100 1110 0100 0000 0011 0001

    第二组:0011 0010 0011 0011 0000 0000 0000 0000 0000 0000 0000 0000 0000 0000

    七位一组分开 末尾加上0 得到:

    第一组:0100000010100010000100101010100010010100011100100000000001100010

    第二组:0011001000011000110000000000000000000000000000000000000000000000

  2. 再挨个转换成十六进制

    第一组:40A212A894720062

    第二组:3218C00000000000

  3. 将以上步骤得到的两组8字节的编码,分别作为DES加密的key 给魔术字符串”KGS!@#$%” 进行加密

    KGS!@#$%的16进制为 4B47532140232425

    先用第一组当key

    image-20230925211741667

    得到:6F08D7B306B1DAD4

    再用第二组当key

    image-20230925211904137

    得到:B75E0C8D76954A50

最终拼接即可,6F08D7B306B1DAD4B75E0C8D76954A50 即 Admin@123 的 LM-Hash值

(3) NTLM Hash值介绍

NTLM Hash是微软为了在提高安全性的同时,保证兼容性而设计的散列加密算法。NTLM Hash是基于 MD4加密算法进行加密的。个人版的Windows vista 以后,服务器版从 Windows Server2003 以后,Windows 操作系统的认证方式均为 NTLM Hash

(4) NTLM hash与NTLM的关系

注:NTLM Hash值跟 NTLM协议不是一个东西,别混淆了

  • NTLM hash为windows认证中的密码哈希散列,而 NTLM是一种网络认证协议,全称 NT LAN Manager,使用NTLM hash作为认证中的根本凭证
  • LM Hash 即 LM协议所使用的密码hash。NT 和 LM认证机制相同,但加密算法不同,由于 LM Hash比较容易破解,在新一点的版本被淘汰

(5) NTLM Hash加密原理

假设我们 administrator的密码为 Admin@123

加密过程如下:

  1. 将明文口令转换成十六进制的格式

    得到:41646D696E40313233

  2. 将十六进制转换成Unicode格式,即在每个字节后添加0x00

    得到:410064006D0069006E004000310032003300

  3. 对 Unicode字符串 hex转码后作 MD4 加密,生成32位的十六进制字符串

    得到:570a9a65db8fba761c1008a51d4c95ab

image-20230925213249994

cmd5可以爆破出来这个弱口令

image-20230925213615379

所以 我们电脑里SAM文件存放的hash密文即为

administrator:6F08D7B306B1DAD4B75E0C8D76954A50:570a9a65db8fba761c1008a51d4c95ab

如果 LM hash被禁用,那么中间的LM Hash应该就是 “aad3b435b51404eeaad3b435b51404ee”

我们利用 mimikatz 抓密码工具 再来验证一下

1
2
3
mimikatz.exe   # 进入到mimikatz的命令行
privilege::debug # 提到debug权限
sekurlsa::logonPasswords # 通过各种方式抓取密码

image-20230925221821619

一模一样

用python 来进行NTLM加密的话,代码为:

1
2
3
4
5
6
7
import binascii
unicode_str = "Admin@123".encode("utf-16le") # 转unicode格式,每个字节后加00
print(unicode_str)
hex_str = binascii.hexlify(unicode_str)
print(hex_str.decode())
# b'A\x00d\x00m\x00i\x00n\x00@\x001\x002\x003\x00'
# 410064006d0069006e004000310032003300

可以得到第二步对应的 16进制串,然后使用hashcalc加密即可

image-20230927085014846

<3> Windows网络认证

当我们访问同一局域网的一台主机上的SMB共享时提供凭证通过验证才能成功进行访问,这就涉及到windows的网络认证

(1) 网络认证概述

网络认证:Windows网络认证是指在Windows 操作系统中进行网络通信和资源访问时,验证用户身份和授权权限的过程。它确保只有经过身份验证的用户能够访问网络资源,并根据其权限级别进行授权操作。

网络认证有哪些?

(2) NTLM协议

NTLM:NTLM 即 NT LAN Manager,是一种早期的Windows 网络认证协议,它基于 挑战(Challenge)/响应(Response)的方式进行身份认证。尽管Kerberos 已经成为首选的认证协议,NTLM 在某些情况下仍在使用,特别在旧版Windows系统或非Windows系统进行交互操作时

NTLM中继(NTLM Relay):是指在NTLM认证过程中设置中间人对HTLM认证的请求截获并转发的一种攻击行为

(3) NTLM协议认证机制

NTLM在工作组环境的认证

其认证过程大致分为三步:

  1. 协商:解决历史遗留问题,为了能向下兼容,双方会确定一下传输协议的版本等各种信息
  2. 质询: 挑战(Challenge)/响应(Response)认证机制的关键
  3. 验证:对质询的结果进行验证,验证通过后即 允许访问资源。是认证的最后一步

image-20231005162943750

NTLM协议 v1 v2版本区别

协商时会确定传输协议的版本,这里版本分为v1和v2。

NTLMv1与NTLM v2最显著的区别就是

  • 共同点就是加密的原料都是NTLM Hash
  • 不同点是Challenge与加密算法不同,NTLM v1的Challenge有8位,NTLM v2的Challenge为16位;NTLM v1的主要加密算法是DES,NTLM v2的主要加密算法是HMAC-MD5

工作组中认证过程:

  1. 当客户端要访问服务器上某个受保护的服务时,需要输入服务器的用户名和密码进行验证。此时客户端会在本地缓存一份服务器密码的NTLM hash,然后向服务器发送协商消息。
  2. 服务器收到客户端的协商信息后,生成并回复质询消息。该消息中包含了一个由服务端生成的16位随机值challenge,服务器也会在本地缓存该值。
  3. 客户端收到质询消息后,会使用步骤1中缓存的服务器的NTLM hash 与 Challenge进行一系列加密生成 Response,再将 Response 封装到身份验证消息中发往服务器。
  4. 服务器在收到身份验证消息后,用自己密码的NTLM hash与Challenge进行加密生成Response2,并比较Response2与Response是否一致。如果一致,就证明客户端掌握了服务器的密码,认证成功,否则认证失败。

NTLM在域环境下的认证

在域环境中,由于所有域用户的哈希值都存储在 域控的 NTDS.dit 中,服务器本身无法计算Response消息,因此需要与域控建立一个安全通道,并通过域控完成最后的认证流程。前三个步骤同工作组环境的认证

域中认证过程:

  1. 当域用户输入自己的账号和密码登录客户端主机时,客户端会将用户输入的密码转换为NTLM hash并缓存。当用户想访问域内某台服务器上的资源时,客户端会向服务器发送TYPE1 Negotiate消息
  2. 服务器收到客户端的协商信息后,生成并回复质询消息。服务端发送Type2 NTLMSSP_CHALLENGE消息,其中包含16位的随机Challenge值
  3. 客户端收到质询消息后,会使用步骤1中缓存的域用户的NTLM hash 与 Challenge进行一系列加密生成 Response。客户端发送Type3 NTLMSSP_AUTH消息,其中包括Response消息
  4. 服务端收到客户端发来的Type3 NTLMSSP_AUTH消息后,会将消息通过 Netlogon协议转发给域控制器
  5. 域控根据自身计算出的Net-NTLM Hash与服务端发过来的Net-NTLM Hash做比较,然后根据结果对客户端进行相应的回复

image-20231005164440355

(4) NTLM基本概念SSPI/SSP

SSPI是安全服务接口是Windows定义的一套接口,该接口定义了与安全有关的功能函数,包括但不限于:

  1. 身份验证机制
  2. 为其他协议提供会话安全可为通信提供完整性校验以及数据的加密、解密的功能。

SSPI 只是定义了一套接口函数,具体实现有SSP完成。

SSP是SSPI的实现者,微软自己也实现了很多SSP用于提供安全功能

典型的SSP实现:

  1. NTLM SSP:Windows NT 3.5中引入(msv1_0.dll)为Windows 2000之前的客户端提供服务器域和非域身份验证(SMB/CIFS)提供NTLM质询/响应身份验证
  2. Kerberos SSP:Windows 2000 中引入为Windows 2000以及更高的版本中首选客户端-服务器域提供相互身份验证

SSPI中定义了会话安全的API,所以上层应用利用任何SSP与远程的服务进行身份验证后,SSP都会为本次的连接生成一个随机key,这个随机key,称为”session key” ,上层的应用经过身份验证后,可以选择性使用这个session key,往服务端或者接收服务端的数据进行签名或加密,SSP就是一个dll,用来实现身份验证等安全功能,不同的SSP实现身份验证的方式是不一样的,比如NTLM SSP实现的是一种基于质询/响应的身份验证机制,Kerberos SSP实现的是基于Tick票据的身份验证机制。

(5) NTLM认证过程抓包分析

为了学习方便,又搭了一套域环境

  • Win2012 IP:192.168.16.10 即 DC
  • Win2008 IP:192.168.16.20 域内主机

我们打开 wireshark 监听 域环境的那个VMNet

使用访问另一台主机的共享

net use \\192.168.16.10\ipc$ /u:administrator Admin@123

根据抓到的数据包,下面也可以看到,net use 是基于SMB协议

我们 先看前四个数据包,Negotiate Protocol Response,是进行协商的

image-20231005125646174

再往下看 第五个数据包,这个是用户启动身份的验证包 flag里确定了一些相关规则

第六个数据包 包含了challenge值

image-20231005132050370

第七个数据包是 发送Response的数据包,还包含账户名的相关信息

image-20231005131735149

客户端根据获得的信息,进行一系列加密得到Response,即这里的 “NTLMv2 Response” 的值

image-20231005132538220

第八个数据包 即返回结果,用来表示成功 or 失败 失败即ERROR

(6) challenge和Response分析

challenge是随机数,位数取决于 NTLM协议的版本 前面提到了

response是如何组成的

response由 NTProofStr+blob两部分组成

  • NTProofStr:使用 NTLM v2 Hash值作为key 对(challenge+blob) 进行 HMAC-MD5加密
  • NTLM v2 Hash:大写Username+Domain name 进行unicode编码,然后和用户名对应密码的 NTLM HASH值进行HMAC-MD5加密
  • blob是由时间、目标信息、随机填充字符生成

计算公式如下:

  • NTLMv2Hash= HMAC-MD5(unicode(hex(upper(UserName)+DomainName))),NTLM Hash)

  • NTProofStr=HMAC-MD5(challenge+blob,NTLM v2 Hash)

我们平时利用工具攻击时 抓到的往往是 Net-NTLM Hash数据

Net-NTLM-Hash格式介绍及拼接

Net-NTLM-v2-Hash的格式为:username::domain:challenge:HMAC-MD5:blob

含义:

username 要访问服务器的用户名
domain 域信息
challenge 数据包6中的服务器返回的challenge值
HMAC-MD5 数据包7中的NTProofStr
blob 对应数据包7中NTLM v2 Response去掉NTProofStr的后半部分

我们利用中间人攻击 Inveigh工具抓取一下 Net-NTLM-v2-Hash 值

1
2
3
4
5
6
powershell
PS C:\Users\Administrator\Desktop\Inveigh> Import-Module .\Inveigh.ps1
PS C:\Users\Administrator\Desktop\Inveigh> Invoke-Inveigh -ConsoleOutput Y -FileOutput y
# 不能加载的话就执行一下 set-ExecutionPolicy RemoteSigned

net use \\192.168.16.10\ipc$ /u:administrator Admin@123

image-20231005143750719

1
administrator::WIN2008:D5E3F1B5CF0101C8:692B3996DC8BF7F0DA9598E6B59DC63D:010100000000000078C3246656F7D901A0EB39BDD6C96EBA00000000020008004800410043004B000100040044004300040010006800610063006B002E0063006F006D0003001600440043002E006800610063006B002E0063006F006D00050010006800610063006B002E0063006F006D000700080078C3246656F7D90106000400020000000800300030000000000000000000000000300000B2B92C5F984625F199A7B3DA00A7897FD7B57990D2735F2E8E9198F48ADD0A8E0A001000000000000000000000000000000000000900240063006900660073002F003100390032002E003100360038002E00310036002E0031003000000000000000000000000000

image-20231005144135954

image-20231005144317709

可以看到 工具抓取的challenge和NTProofStr跟wireshark的是一样的

1
2
3
4
NTLM HASH:570a9a65db8fba761c1008a51d4c95ab
challenge:D5E3F1B5CF0101C8
NTProofStr:692B3996DC8BF7F0DA9598E6B59DC63D
blob:010100000000000078C3246656F7D901A0EB39BDD6C96EBA00000000020008004800410043004B000100040044004300040010006800610063006B002E0063006F006D0003001600440043002E006800610063006B002E0063006F006D00050010006800610063006B002E0063006F006D000700080078C3246656F7D90106000400020000000800300030000000000000000000000000300000B2B92C5F984625F199A7B3DA00A7897FD7B57990D2735F2E8E9198F48ADD0A8E0A001000000000000000000000000000000000000900240063006900660073002F003100390032002E003100360038002E00310036002E0031003000000000000000000000000000

我们利用获取的信息手动计算一下,体会加密过程

计算NTLM-v2-HASH

  1. 将 administrator转化为大写:ADMINISTRATOR
  2. 然后与域名WIN2008 拼接起来:ADMINISTRATORWIN2008
  3. 转化成16进制:41444d494e4953545241544f5257494e32303038
  4. 转化为unicode格式:410044004d0049004e004900530054005200410054004f005200570049004e003200300030003800
  5. 然后 用NTLM HASH:570a9a65db8fba761c1008a51d4c95ab 作为key 对上述进行HMAC-MD5加密 得到:e864d6b3c317322f934b6df3d5c44ffa 即 NTLM-v2-HASH的值

image-20231005151402590

计算 NTProofStr

  1. 将 NTLM-v2-HASH值 e864d6b3c317322f934b6df3d5c44ffa 作为key
  2. 将 challenge 与 blob 值拼接起来:D5E3F1B5CF0101C8010100000000000078C3246656F7D901A0EB39BDD6C96EBA00000000020008004800410043004B000100040044004300040010006800610063006B002E0063006F006D0003001600440043002E006800610063006B002E0063006F006D00050010006800610063006B002E0063006F006D000700080078C3246656F7D90106000400020000000800300030000000000000000000000000300000B2B92C5F984625F199A7B3DA00A7897FD7B57990D2735F2E8E9198F48ADD0A8E0A001000000000000000000000000000000000000900240063006900660073002F003100390032002E003100360038002E00310036002E0031003000000000000000000000000000
  3. 将 NTLM-v2-hash作为key 对上述数据进行 HMAC-MD5加密,得到:692b3996dc8bf7f0da9598e6b59dc63d 验证一下 一致

image-20231005151813588

使用hashcat破解NET-NTLM hash

hashcat [option]

hashcat 爆破一下我们上面得到的 NET-NTLM-Hash

1
hashcat -m 5600 administrator::WIN2008:D5E3F1B5CF0101C8:692B3996DC8BF7F0DA9598E6B59DC63D:010100000000000078C3246656F7D901A0EB39BDD6C96EBA00000000020008004800410043004B000100040044004300040010006800610063006B002E0063006F006D0003001600440043002E006800610063006B002E0063006F006D00050010006800610063006B002E0063006F006D000700080078C3246656F7D90106000400020000000800300030000000000000000000000000300000B2B92C5F984625F199A7B3DA00A7897FD7B57990D2735F2E8E9198F48ADD0A8E0A001000000000000000000000000000000000000900240063006900660073002F003100390032002E003100360038002E00310036002E0031003000000000000000000000000000 rockyou.txt -o result.txt --force

image-20231005154257959

(7) NTLM协议的安全性问题

  1. Net-NTLM v1 v2 Hash破解:v1 使用DES加密,更容易破解。v2版本的话可以通过碰撞、彩虹表、暴力猜解等方式,获取明文账号密码
  2. NTLM-relay攻击:通过中间人攻击,如果获得了 Net-NTLM Hash值,如果爆破不出密码 可以考虑NTLM-relay攻击,可以重放 进行认证

参考:https://chenchena.blog.csdn.net/article/details/123274876?spm=1001.2014.3001.5502

<4> Kerberos域认证★

传送门:https://1vxyz.github.io/2023/10/05/Kerberos%E8%AE%A4%E8%AF%81%E5%AD%A6%E4%B9%A0/

作者

1vxyz

发布于

2023-09-25

更新于

2023-10-20

许可协议

评论