Windows身份认证

admin 2022年10月1日20:51:09评论138 views字数 16603阅读55分20秒阅读模式

本文来自宽字节安全第一期学员Demia投稿。第二期线下培训预计十一月底开班,欢迎咨询。

这里的叙述,从一个用户开机并使用账号密码登录开始。

启动Windows操作系统。用户张三使用其账号密码code/code登录Windows 10操作系统。

登录之后,打开浏览器下载进程查看工具(Time:2021.8.24

https://processhacker.sourceforge.io/downloads.php

https://github.com/processhacker/processhacker/releases/download/v2.39/processhacker-2.39-bin.zip

Windows身份认证

打开之后的界面如下(默认双击打开是普通用户权限):

  • name:各个进程的名称
  • PID:进程的PID
  • User Name:进程是以什么权限启动的
Windows身份认证

针对以上过程:

  • 用户张三登录
  • 用户打开浏览器下载文件
  • 运行下载的文件
  • 查看process

需要明白Windows如何进行身份认证的,这里就需要接触Windows认证的一些概念。

sam

安全帐户管理器(SAM,Security Account Manager) 是运行 Windows 操作系统的计算机上的数据库,用于存储本地计算机上的用户的用户帐户和安全描述符。每个用户帐户均与两个密码相关联:LAN Manager 的兼容密码和 Windows 密码。

C:WindowsSystem32configsam

SAM主要包含的内容

  • SAM_ALIAS:本地组
  • SAM_GROUP:不是本地组的组
  • SAM_USER:用户帐户
  • SAM_DOMAIN:域
  • SAM_SERVER:计算机帐户

回看张三使用账号密码登录时候,操作系统首先接受到账号密码后,通过加密的得到的Hash对比sam总Hash对比,如果Hash一致则登录成功。那么需要看下是如何加密明文得到Hash的?

将明文加密成Hash

这里需要知道两个东西:LM HashNT Hash

LM Hash

LM Hash:windwos Lan管理器Hash

注意⚠:在早期的Windows操作系统,使用了LM Hash,这种密码生成规则要求用户的密码最多仅能为14个字符。

LAN 管理器兼容的密码与 LAN 管理器使用的密码兼容。此密码基于原始设备制造商 (OEM) 字符集。此密码不区分大小写,并且最多为 14 个字符。此密码的 OWF 版本也称为 LAN 管理器 OWF 或 ESTD 版本。此密码是使用 DES  加密通过纯文本密码对常量进行加密来计算的。LAN 管理器 OWF 密码长 16 字节。清除文本密码的前 7 个字节用于计算 LAN 管理器  OWF 密码前 8 个字节。清除文本密码的第二个 7 个字节用于计算 LAN 管理器 OWF 密码的第二个 8 个字节。

🈚:高版本的Windows默认不存储LAN管理器Hash

Windows身份认证

先看下默认的加密流程:

  1. 将明文口令转换为其大写形式
  2. 将大写字符串转换为16进制字符串
  3. 密码不足14字节要求用0补全(二进制层面)
  4. 十六进制分割2组8字节的编码
  5. 从左到右按照每7bit一组罗列,接下来在每7bits一组的末尾添0,再将其转换成16进制
  6. 得到的两组8字节编码,分别作为DES加密key为魔术字符串KGS!@#$%进行加密
  7. 两组DES加密后的编码拼接,得到最终LM-Hash值

既然默认不存储,那么我们启用该选项并重新更改密码,然后通过Mimikatz抓取Hash(不设置的话,以下操作抓不到该Hash,其他抓Hash方式再说)

Windows身份认证

首先转储sam,然后利用mimikatz读取Hash

reg save HKLMSYSTEM system.hiv
reg save HKLMSAM sam.hiv
reg save hklmsecurity security.hiv

mimikatz # lsadump::sam /system:system.hiv /sam:sam.hiv
Windows身份认证

Hash LM  : 6f0c960c447706471aa818381e4e281b Hash NTLM: 7ac777be44beae80b2ca783edd7f8df5

手工转换一下,然后对比是否一样?

  1. code.123转换大小写:CODE.123
  2. 字符串转16进制:434F44452E313233
  3. 密码不足14字节要求用0补全434F44452E313233434F44452E313233000000000000
  4. 每一组7字节的十六进制转换为二进制,每7bit一组末尾加0,再转换成十六进制组成得到2组8字节的编码:434F44452E313233000000000000
  5. 从左到右按照每7bit一组罗列,接下来在每7bits一组的末尾添0,再将其转换成16进制
Windows身份认证
将以上的BIN,二进制数据以每7BIT罗列,最后在每组后添加一个0
0100001 -> 01000010
1010011 -> 10100110
1101000 -> 11010000
1000100 -> 10001000
0101001 -> 01010010
0111000 -> 01110000
1100010 -> 11000100
0110010 -> 01100100
得到:0100001010100110110100001000100001010010011100001100010001100100 ---> 42A6D0885270C464

同理,第二组的得到:
 0011001010000000000000000000000000000000000000000000000000000000 ---> 3280000000000000
  1. 得到的两组8字节编码,分别作为DES加密key为魔术字符串KGS!@#$%进行加密,得到:
6f0c960c44770647
1aa818381e4e281b
拼接得到最后的LM HASH : 6f0c960c447706471aa818381e4e281b
Windows身份认证
Windows身份认证

手工的完毕了,借用大佬的脚本也可。

#coding=utf-8
import re
import binascii
from pyDes import *
def DesEncrypt(str, Des_Key):
    k = des(binascii.a2b_hex(Des_Key), ECB, pad=None)
    EncryptStr = k.encrypt(str)
    return binascii.b2a_hex(EncryptStr)

def group_just(length,text):
    # text 00110001001100100011001100110100001101010011011000000000
    text_area = re.findall(r'.{%d}' % int(length), text) # ['0011000', '1001100', '1000110', '0110011', '0100001', '1010100', '1101100', '0000000']
    text_area_padding = [i + '0' for i in text_area] #['00110000', '10011000', '10001100', '01100110', '01000010', '10101000', '11011000', '00000000']
    hex_str = ''.join(text_area_padding) # 0011000010011000100011000110011001000010101010001101100000000000
    hex_int = hex(int(hex_str, 2))[2:].rstrip("L"#30988c6642a8d800
    if hex_int == '0':
        hex_int = '0000000000000000'
    return hex_int

def lm_hash(password):
    # 1. 用户的密码转换为大写,密码转换为16进制字符串,不足14字节将会用0来再后面补全。
    pass_hex = password.upper().encode("hex").ljust(28,'0'#3132333435360000000000000000
    print(pass_hex) 
    # 2. 密码的16进制字符串被分成两个7byte部分。每部分转换成比特流,并且长度位56bit,长度不足使用0在左边补齐长度
    left_str = pass_hex[:14#31323334353600
    right_str = pass_hex[14:] #00000000000000
    left_stream = bin(int(left_str, 16)).lstrip('0b').rjust(56'0'# 00110001001100100011001100110100001101010011011000000000
    right_stream = bin(int(right_str, 16)).lstrip('0b').rjust(56'0'# 00000000000000000000000000000000000000000000000000000000
    # 3. 再分7bit为一组,每组末尾加0,再组成一组
    left_stream = group_just(7,left_stream) # 30988c6642a8d800
    right_stream = group_just(7,right_stream) # 0000000000000000
    # 4. 上步骤得到的二组,分别作为key 为 "KGS!@#$%"进行DES加密。
    left_lm = DesEncrypt('KGS!@#$%',left_stream) #44efce164ab921ca
    right_lm = DesEncrypt('KGS!@#$%',right_stream) # aad3b435b51404ee
    # 5. 将加密后的两组拼接在一起,得到最终LM HASH值。
    return left_lm + right_lm

if __name__ == '__main__':
    hash = lm_hash("123456")

NT Hash

本次测试默认的NT HASH

code.123   -->  7ac777be44beae80b2ca783edd7f8df5

  1. 先将用户密码转换为十六进制格式。

  2. 将十六进制格式的密码进行Unicode编码。

  3. 使用MD4摘要算法对Unicode编码数据进行Hash计算

import hashlib
import binascii

print(binascii.hexlify(hashlib.new("md4""code.123".encode("utf-16le")).digest()))
Windows身份认证

知道了Windows Hash生成方式之后,这里继续回看,张三账号密码登录操作系统之后,操作系统将用户输入的明文进行加密,然后与SAM中的Hash比对,如果登录成功则进入桌面,否则提示账号密码错误。

这里牵涉到另外一个问题,上述只是说明了Hash对比,但是windows是如何判断用身份的,在操作系统曾面如何进行?

LSA 用户登录身份验证

LSA 处理本地计算机上的用户登录和身份验证。LSA 提供对 (Ssp) 的安全支持提供程序的身份验证包的访问。执行以下两种类型的身份验证之一:

  • 交互式身份验证
  • 非交互身份验证

交互式身份验证

当提示用户提供登录信息时,身份验证是交互式的。本地安全机构 (LSA) 在用户通过 GINA用户界面登录时执行交互式身份验证。

Windows身份认证
  1. 用户输入账号密码,Winlogon 接收 SAS 并调用 GINA,以显示用户界面并获取用户的登录数据(Winlogon、GINA和网络提供程序是交互式登录模型的各个部分。 交互式登录过程通常由 Winlogon、MSGina.dll和网络提供程序控制。若要更改交互式登录过程,MSGina.dll自定义 GINA DLL 替换该登录过程。)
  2. 获取登录数据后,GINA 会调用 LsaLogonUser 函数来对用户进行身份验证,并指定必须使用哪种身份验证包来评估登录数据。
  3. LSA 调用指定的身份验证包,并向其传递登录数据。身份验证包检查数据并确定身份验证是否成功。身份验证结果将从 lsa 返回到 GINA。
  4. GINA 显示用户身份验证是成功还是失败,并将身份验证结果返回给 Winlogon。如果身份验证成功,用户的登录会话将开始,并保存一组登录凭据(Hash)以供将来参考。

Winlogon

Winlogon维护GINA用于确定所需的身份验证操作所使用的工作站状态。

在任意时间点,Winlogon 处于以下三种状态之一:

  • 已注销状态
  • 登录状态
  • 工作站锁定状态
Windows身份认证

Logged-Off状态

当 Winlogon 的状态为"已注销"时,系统会提示用户标识自己并提供身份验证信息。 如果用户提供正确的用户帐户信息,并且没有任何限制阻止此信息,则用户将登录,并且 shell 程序 (例如 Windows Explorer)  在应用程序桌面中执行。Winlogon 将更改到登录状态。

Logged-On状态

当 Winlogon 为登录状态时,用户可以与 shell 交互、激活其他应用程序并完成其工作。 从登录状态开始,用户可以停止所有工作并注销,或锁定其工作站 (使所有工作都) 。如果用户决定注销,Winlogon  将终止与该登录会话关联的所有进程,工作站将可供其他用户使用。如果用户决定锁定工作站,Winlogon 将改为工作站锁定状态。

Workstation-Locked状态

当 Winlogon  为工作站锁定状态时,会显示一个安全的桌面,直到用户通过提供与最初登录的用户相同的标识和身份验证信息来解锁工作站,或者直到管理员强制注销。 如果工作站已解锁,则会显示应用程序桌面,并且可以继续工作。但是,如果管理员通过提供管理员帐户) 的标识和身份验证信息解锁工作站  (,则已登录用户的进程将终止,Winlogon 将更改到已注销状态。

非交互式身份验证

非交互式身份验证只能在交互式身份验证发生后使用。在非交互式身份验证期间,用户不会输入登录数据 ,而是使用以前建立的凭据(Hash)。

当应用程序使用安全支持提供程序接口 (SSPI) 和安全包建立安全网络连接时,将执行非交互式身份验证

非交互式身份验证是当用户连接到网络上的多台计算机而无需重新输入每台计算机的登录信息时的工作机制。

Windows身份认证

如果应用程序需要在远程计算机上打开安全文件夹,并且应用程序用户已经以交互式登录到远程计算机,则应用程序不需要用户再次提供登录数据。相反,应用程序可以使用 SSPI 请求非交互式身份验证,以将以前建立的安全信息传递给安全包。

上图:客户端应用程序启动对 SSPI 的调用,以请求经过身份验证的网络连接。SSPI 将客户端的请求传递给安全包进行处理。安全包通过调用本地安全机构 ( LSA) 并指定身份验证包并提供用户的现有凭据来对用户进行身份验证。

身份验证包

本地安全机构(LSA) 使用注册表中存储的配置信息加载身份验证包

登录过程使用身份验证包分析登录数据,通过添加GINA来收集所需的登录数据,并通过添加新的身份验证包来分析数据,从而将新的登录进程添加到系统中。

身份验证包负责以下任务:

  • 分析登录数据,以确定是否允许安全主体登录到系统。
  • 建立新的登录会话并为成功通过身份验证的主体创建唯一的登录标识符(LUID)。
  • 为主体的安全令牌将安全信息传递到 LSA。

登录会话

登录会话是一种计算会话,在用户身份验证成功时开始,并在用户注销系统时结束。

用户成功通过身份验证后,身份验证包将创建一个登录会话,并将信息返回给本地安全机构(LSA) 用于为新用户创建令牌 。此令牌包括登录会话 (LUID) 的 本地唯一标识符 ,称为 登录 Id。

创建令牌后,登录会话的引用计数将递增。 如果为进程创建、模拟或其他使用创建了令牌的副本,则还会递增引用计数。由于令牌使用已完成,并且删除了令牌的副本,因此将减少登录会话的引用计数。当引用计数达到零时,将删除登录会话。

登录标识符

标识登录会话的LUID。登录ID有效,直到用户注销。当计算机正在运行时,登录 ID 是唯一的, 但是,当计算机启动时,登录ID会重置。若要从访问令牌中检索登录 ID。

当用户尝试交互式登录时,LSA 将调用一个身份验证包来确定是否允许用户登录。

例如:MSV1_0 是随 Microsoft Windows 操作系统一起安装的身份验证包。MSV1_0 包接受用户名和哈希密码。它在SAM数据库中查找用户名和哈希密码组合。如果登录数据与存储的凭据匹配,则身份验证包将允许登录成功。

身份验证包负责为主体创建新的 LSA 登录会话,并分配唯一标识该登录会话的登录标识符。身份验证包可能会将凭据信息与登录会话相关联,以便进行后续身份验证请求。例如,  Microsoft 提供的 MSV1_0 authentication package() 将用户帐户名称和用户密码的哈希与每个登录会话相关联。

身份验证包还提供了一组 安全标识符 , (sid) 以及适用于在 LSA 创建的安全令牌中包含的其他信息。此令牌表示主体用于访问 Windows 操作的安全 上下文。

创建登录会话并将其与主体相关联后,代表主体进行的后续身份验证请求的处理方式与初始登录不同。身份验证包不会创建新的登录会话,也不会返回用于创建令牌的信息,当访问请求的资源所需的信息超出了初始登录所建立的凭据时,将获得补充凭据,调用其他的身份验证包 。

上面提到了:exporer的子进程?user用户?SID是什么?权限信息?

  • exporer.exe : 是Windows程序管理器或者文件资源管理器,它用于管理Windows图形壳,包括桌面和文件管理
  • user:当前登录用户code
  • SID:当前用户code身份的标识
  • 权限信息可以看到explorer并非是以完整的Access Token来启用。(Flags: disabled)

这里可以回顾之前的张三的登录操作:

  1. 张三输入账号密码,winlogn 调用GINA接受到账号密码,GINA 会调用LsaLogonUser函数,然后指定身份验证包,并向身份验证包传递登录数据,身份验证包判断登录成功失败,并将身份验证结果将从 lsa 返回到 GINA,GINA将身份验证结果回传给WinLogon。
  2. WinLogon状态从Logged-Off状态转变为Logged-On状态。在启用桌面程序时,系统将创建访问令牌(不完整Token),代表该用户执行的每一个进程都将具有此访问令牌的副本
  3. 操作系统以不完整Token来启用了explorer.exe进程,接着张三进入到Windows桌面,之后张三启用的进程/对象,比如:ProcessHacker或者CMD将会以不完整Token来启用。
Windows身份认证

举个例子来查看Token问题:

  1. 直接打开CMD,执行whoami /all
Windows身份认证
  1. 以管理员权限启用CMD并执行:whoami /all
Windows身份认证
Windows身份认证

对比两个CMD的进程信息:

Windows身份认证

紧接着向下看,以管理员身份认证来运行的CMD,弹窗提示是什么?那么操作系统是如何控制的呢?这里涉及到两个问题:

  1. 访问控制模型(Access-Control-Model)
  2. 用户账户控制(User-Account-Control)

访问控制模型

访问控制模型(Access-Control-Model)

一直提到一个进程查看工具ProcessHacker,得到的进程信息:

  1. explorer.exe进程信息
  2. user:DESKTOP-VCBQ663code
  3. SID:S-1-5-21-4177939220-3106167579-508168540-1003
  4. 权限信息

我们需要理解一下为什么ProcesHacker进程是exporer的子进程?user用户?SID是什么?权限信息?TokenView中某进程的Token是怎么来的?

Windows身份认证
Windows身份认证

这就需要我们知道什么是:访问控制模型(Access-Control-Model)

基本组成

  • 访问令牌 access token

当用户登录系统时,系统会对用户的账户名和密码进行校验,如果登录成功,系统将创建访问令牌,代表该用户执行的每一个进程都将具有此访问令牌的副本。令牌中包含安全标识符,用于标识用户的账户以及该用户所属的任何组账户。令牌还包含用户或用户组用户的权限列表,当进程尝试访问安全对象或执行需要特权的系统任务时,系统使用此令牌来标识关联用户。

  • 安全描述符 Security descriptors

在创建一个安全对象是,系统会为其分配一个安全描述符,其中包含创建者指定的安全信息,如果没有指定安全信息,则为其默认分配安全信息。安全描述符号中,还可以包含访问控制列表(Access Control Lists)

访问令牌 Access token

当线程与安全对象交互或尝试执行需要特权的系统任务时,系统使用访问令牌来标识用户。令牌包含了以下信息:

  • 用户帐户 ( SID) 安全标识符
  • 用户是其中一个成员的组的 ID
  • 标识 当前登录 会话的 登录 SID
  • 用户 或 用户组拥有的权限列表
  • 所有者 SID
  • 主组的 SID
  • 用户创建安全对象而不指定安全描述符时系统 使用的默认 DACL
  • 访问令牌的源
  • 令牌是主 令牌还是模拟令牌
  • 限制 SID 的可选列表
  • 当前模拟级别
  • 其他统计信息

每个进程都有 一个主令牌,用于描述与进程关联的用户帐户的安全上下文(当前生效的安全属性或规则)。默认情况下,当进程的线程与安全对象交互时,系统将使用主令牌。此外,线程可以模拟客户端帐户。模拟允许线程使用客户端的安全上下文与安全对象进行交互。模拟客户端的线程同时具有主令牌和模拟令牌。

安全描述符

安全描述符包含与安全对象关联的安全信息。安全描述符包含安全描述符结构及其关联的安全信息。安全描述符可以包含以下安全信息:

  • 对象的所有者和主要组的 Sid(安全标识符)
  • 用于指定允许或拒绝特定用户或组的访问权限的 DACL 。
  • 指定为对象生成审核记录的访问尝试类型的 SACL 。
  • 一组限制安全描述符或其各个成员的含义的控制位。

安全标识符 SID

SID(安全标识符)是用于标识受信者的可变长度的唯一值。每个帐户都有一个由机构颁发的唯一 SID, 用户每次登录时,系统都将从数据库中检索该用户的 SID,并将其放在该用户的访问令牌 中。系统使用访问令牌中的 SID 来识别与 Windows认证后进行的所有后续交互中的用户。当某个 SID 被用作用户或组的唯一标识符时,它不能再次用于标识其他用户或组。

  • 用于标识对象的所有者和主要组的安全描述符
  • 在 访问控制项中,标识允许、拒绝或审核其访问权限的受信者
  • 在 " 访问令牌" 中,确定用户和用户所属的组

S-1-5-21-4177939220-3106167579-508168540-1003

组成部分:

  • 修订级别为1
  • 标识符颁发机构值为 5 (安全 _ NT _ 颁发机构)
  • 域标识符 (21-4177939220-3106167579-508168540)
  • RID(1003)

访问控制列表 ACL

(ACL) 适用于对象的安全保护列表。 (对象可以是文件、进程、事件或其他具有安全描述符的任何对象。) 访问控制列表 (ACL) 中的条目是访问控制项 (ACE) 。

访问控制表描述用户或系统进程对每个对象的访问控制权限。要确定一个对象的所有访问权限需要搜索整个访问控制表来找出相对应的访问权限

有两种类型的访问控制列表:

  1. 自由访问控制列表(DACL) :用于标识允许或拒绝访问的用户和组
  2. 系统访问控制列表(SACL):用于控制如何审核访问

常见的访问控制列表:

Filesystem ACLs

Active Directory ACLs

Networking ACLs

查看文件的ACL

Get-Acl -Path .mimikatz.exe | format-list

Windows身份认证

访问控制项 ACE

高级权限中的每一项代表的是每一个访问控制项(ACE)

Windows身份认证

DACL

当某个 进程 尝试访问某个安全对象时,系统将在对象的 DACL 中检查 ace,以确定是否授予对该对象的访问权限。

如果该对象没有 DACL,则系统向所有人授予完全访问权限。如果对象的 DACL 没有 Ace,则系统将拒绝所有对对象的尝试,因为 DACL 不允许任何访问权限。如果 DACL 具有允许访问一组有限用户或组的 ACL,则系统会隐式拒绝访问 AES 中未包含的所有受信者。

查看文件的DACL列表

Windows身份认证

如果对象的 DACL 有ACE系统会按顺序检查 Ace,直到找到允许所有请求的访问权限的一个或多个 Ace,或直到拒绝任何请求的访问权限为止。

下图显示了对象的 DACL 如何允许访问一个线程,同时拒绝对另一个线程的访问。

Windows身份认证

对于线程 A,系统读取 ACE 1 并立即拒绝访问,因为访问被拒绝的 ACE 适用于线程的访问令牌中的用户。在这种情况下,系统不检查 Ace 2 和3。对于线程 B,ACE 1 不适用,因此系统继续到 ACE 2 (允许写入访问)和 ACE 3 (允许读取和执行访问)。

如果一个 ACE 向某个组授予读取访问权限,另一个 ACE 向作为该组成员的用户授予写入权限,则该用户可以对该对象同时具有读取和写入访问权限。

Windows身份认证

通过TokenView查看DACL和SACL

Windows身份认证

SACL

SACL 应用于计算机或文件共享上的每个文件和文件夹或注册表项,作为防止未检测到可验证访问的安全措施。

UAC

用户帐户控制 (UAC) 有助于防止恶意软件损坏电脑,并且有助于组织部署易于管理的桌面。借助  UAC,应用和任务将始终在非管理员帐户的安全上下文中运行,除非管理员专门授予管理员级别的访问系统权限。UAC  可阻止自动安装未经授权的应用并防止意外更改系统设置。

UAC 允许所有用户使用标准用户帐户登录到他们的计算机。使用标准用户令牌启动的进程可能会使用授予标准用户的访问权限执行任务。 例如,Windows 资源管理器会自动继承标准用户级别权限。此外,使用 Windows  资源管理器启动(例如,通过双击快捷方式)的任何应用也会使用标准用户权限组运行。许多应用(包括操作系统本身附带的应用)旨在通过此方式正常运行。

每个需要管理员访问令牌的应用都必须提示征得同意。一个例外是父进程和子进程之间的关系。子进程从父进程继承用户的访问令牌。 但是,父进程和子进程必须具有相同的完整性级别。Windows 10标记进程的完整性级别来保护进程。完整性级别是信任的度量。 "高"完整性应用程序是执行修改系统数据的任务(如磁盘分区应用程序)的应用程序,而"低"完整性应用程序是执行可能会损害操作系统的任务(如 Web  浏览器)的应用程序。完整性级别较低的应用无法修改完整性级别较高的应用程序中的数据。当标准用户尝试运行需要管理员访问令牌的应用时,UAC  要求用户提供有效的管理员凭据。

这里就是区分了高完整性Token和低完整性Token

下面显示了管理员的登录过程与标准用户的登录过程的区别:

回顾之前,就是张三以code用户登录电脑后,以非管理员和管理员启动cmd.exe时的区别(是否触发UAC)。

Windows身份认证

这里需要知道管理员与非管理员的区别,以及500特权用户。

这里系统中存在三个用户

  • admin(普通用户)
  • administrator(操作系统默认管理员,500特权用户)
  • code(管理员用户)

非管理员

当非管理员用户尝试执行需要用户管理访问令牌的任务时,将显示凭据提示。要求提供管理员其凭据。

这里添加一个新用户admin,不授予其管理员权限。net user admin admin@123 /add

  • 如果以管理员身份启用CMD程序的话,需要提供管理员的账号密码才可以。
Windows身份认证

管理员

管理员登录后,会为用户创建两个单独的访问令牌:标准用户访问令牌和管理员访问令牌。 标准用户访问令牌包含与管理员访问令牌相同的用户特定信息,Windows权限和 SID。标准用户访问令牌用于启动在标准用户应用中不 (管理) 。然后,使用标准用户访问令牌显示桌面 (explorer.exe) 。Explorer.exe是所有其他用户启动的进程从其继承其访问令牌的父进程。 因此,除非用户同意或凭据批准应用使用完整的管理访问令牌,否则所有应用均以标准用户身份运行。

非500管理员登陆后,默认分配的时低完整Token(标准用户),如果需要以管理员身份启用CMD则需要UAC认证。

Windows身份认证

500特权用户

在Windwos中,默认的管理员RID为500的是administrator。那么为什么500的用户比较特殊呢?

在登陆系统后,RID为500的用户,默认分配的是完整的Token,不会触发UAC认证

比如:直接以管理员启用CMD,将会直接打开,不会提示用户账户控制弹窗。如果以张三登录的用户code来右键以管理员身份启用CMD,则会提示用户账户控制弹窗。

Windows身份认证

查看系统中的SID信息wmic useraccount where name="administrator" list full /format:list

Windows身份认证

UAC体系结构

Windows身份认证

在UAC认证体系同我们需要知道的时UAC的四个级别:高-->低

  1. 始终通知
  • 当程序尝试安装软件或对计算机进行更改时通知你。
  • 当您对自定义设置进行更改时Windows通知。
  • 冻结其他任务,直到做出响应。
  1. 仅在程序尝试更改我的计算机时通知
  • 当程序尝试安装软件或对计算机进行更改时通知你。
  • 对设置进行更改时不Windows通知。
  • 冻结其他任务,直到做出响应。
  1. 仅在程序尝试更改计算机时通知我 (我的桌面设备)  将:
  • 当程序尝试安装软件或对计算机进行更改时通知你。
  • 对设置进行更改时不Windows通知。
  • 在响应之前,不要冻结其他任务。
  1. 从不通知 (禁用 UAC 提示)  将:
  • 当程序尝试安装软件或对计算机进行更改时不通知你。
  • 对设置进行更改时不Windows通知。
  • 在响应之前,不要冻结其他任务。

默认情况下为第三个等级(低到高,1,2,3,4):仅在程序尝试更改我的计算机时通知

Windows身份认证

为了更好地了解UAC认证体系每个组件,请查看下表:

组件 描述
用户
用户执行需要特权的操作 如果操作更改文件系统或注册表,则调用 Virtualization。所有其他操作都调用 ShellExecute。
ShellExecute ShellExecute 调用 CreateProcess。ShellExecute 从 CreateProcess  ERROR_ELEVATION_REQUIRED错误。如果收到错误,则 ShellExecute  将调用应用程序信息服务以尝试执行请求的任务,同时显示提升的提示。
CreateProcess 如果应用程序需要提升,CreateProcess 将拒绝调用,ERROR_ELEVATION_REQUIRED。
系统
应用程序信息服务 一种系统服务,可帮助启动需要一个或多个提升的权限或用户权限来运行的应用,例如本地管理任务以及需要更高完整性级别的应用。 应用程序信息服务通过为具有管理用户'的完全访问令牌(如果需要提升)和 ((具体取决于组策略)的应用程序创建一个新进程来帮助启动此类应用程序)  用户同意这样做。
提升安装ActiveX安装 如果未ActiveX,系统将检查 UAC 滑块级别。如果ActiveX,将选中用户帐户控制:提示提升组策略设置    切换到安全桌面。
检查 UAC 滑块级别 UAC 具有从四个通知级别中选择的滑块。始终通知  将:当程序尝试安装软件或对计算机进行更改时通知你。当您对自定义设置进行更改时Windows通知。冻结其他任务,直到做出响应。建议经常安装新软件或访问不熟悉的网站。 仅在程序尝试更改我的计算机时通知  我:当程序尝试安装软件或对计算机进行更改时通知你。对设置进行更改时不Windows通知。 冻结其他任务,直到做出响应。建议不要经常安装应用或访问不熟悉的网站。 仅在程序尝试更改计算机时通知我 (我的桌面设备)  将:当程序尝试安装软件或对计算机进行更改时通知你。对设置进行更改时不Windows通知。 在响应之前,不要冻结其他任务。不建议使用。仅在需要很长时间才能将桌面上的桌面变暗时,才选择此选项。 从不通知 (禁用 UAC 提示)  将:当程序尝试安装软件或对计算机进行更改时不通知你。对设置进行更改时不Windows通知。 在响应之前,不要冻结其他任务。由于安全问题,不建议这样做。
启用安全桌面 选中  用户帐户控制:在提示提升策略设置时  切换到安全桌面:  如果启用安全桌面,则所有提升请求将转到安全桌面,而不考虑管理员和标准用户的提示行为策略设置。 如果未启用安全桌面,所有提升请求将转到交互式用户'桌面,并且使用管理员和标准用户每用户设置。
CreateProcess CreateProcess 调用 AppCompat、Fusion 和 Installer 检测,以评估应用是否要求提升。 然后检查该文件以确定其请求的执行级别,该执行级别存储在文件的应用程序清单中。 如果清单中指定的请求执行级别与访问令牌不匹配,CreateProcess 将失败,并且向 ShellExecute  (ERROR_ELEVATION_REQUIRED) 错误。
AppCompat AppCompat 数据库将信息存储在应用程序的应用程序兼容性修复条目中。
Fusion Fusion 数据库存储应用程序清单中描述应用程序的信息。清单架构已更新,以添加新的请求执行级别字段。
安装程序检测 安装程序检测可检测安装程序文件,这有助于防止在用户不知情'的情况下运行安装。
内核
虚拟化 虚拟化技术可确保不合规的应用不会以无法确定原因的方式以静默方式运行或失败。UAC 还为写入受保护区域的应用程序提供文件和注册表虚拟化以及日志记录。
文件系统和注册表 每用户文件和注册表虚拟化将每计算机注册表和文件写入请求重定向到等效每用户位置。读取请求首先重定向到虚拟化每用户位置,然后重定向到每计算机位置。

如果张三想通过命令行登录别的机器呢?

wmic /node:ip os get name

wmic /node:ip /user:administrator /password:admin@123 os get name

NTLM 身份验证

高版本的Windows使用的都是NTLM Hash,那么通过CMD登录别的机器是如何认证的呢?

NTLM身份验证是一种Challenge/Response 验证机制,由三种消息组成:通常称为type 1(协商),类型type 2(质询)和type 3(身份验证)。

该过程总共三个包

  • wmic /node:ip os get name
Windows身份认证

这里可以看到,如果按照上述的命令来执行,默认第三个包(type3携带的是当前用户的身份信息)

wmic /node:ip /user:administrator /password:admin@123 os get name

Windows身份认证

如果指定了账号密码则type3携带的是指定的账号密码信息。

身份验证过程

  1. (type 1)客户端向服务器发送type 1(协商)消息,它主要包含客户端支持和服务器请求的功能列表。
Windows身份认证
  1. (type 2)服务器用type 2消息(质询)进行响应,这包含服务器支持和同意的功能列表。但是,最重要的是,它包含服务器产生的Challenge。
Windows身份认证
  1. (type 3)客户端用type  3消息(身份验证)回复质询。用户接收到type2中的challenge之后,使用用户hash与challenge进行加密运算得到response,将response,username,challeng发给服务器。消息中的response是最关键的部分,因为它们向服务器证明客户端用户已经知道帐户密码。
Windows身份认证

Net-NTLM-Hash

在第二步中获取到challenge,Challenge/Response验证机制里面type3 response里面包含Net-ntlm  hash,NTLM v1响应和NTLMv2响应对应的就是Net-ntlm hash分为Net-ntlm hash v1和Net-ntlm  hash v2。

Net-ntlm hash v1的格式为:

username::hostname:LM response:NTLM response:challenge

Net-ntlm hash v2的格式为:

username::domain:challenge:HMAC-MD5:blob
  • v2是16位的Challenge,而v1是8位的Challenge
  • v1是将 16字节的NTLM hash空填充为21个字节,然后分成三组,每组7比特,作为3DES加密算法的三组密钥,加密Server发来的Challenge。将这三个密文值连接起来得到response。

v2是的加密算法:

  1. 将Unicode后的大写用户名与Unicode后的身份验证目标(在Type  3消息的"TargetName"字段中指定的域或服务器名称)拼在一起。请注意,用户名将转换为大写,而身份验证目标区分大小写,并且必须与“TargetName”字段中显示的大小写匹配。使用16字节NTLM哈希作为密钥,得到一个值。
  2. 构建一个blob信息
Windows身份认证
  1. 使用16字节NTLMv2哈希作为密钥,将HMAC-MD5消息认证代码算法加密一个值(来自type 2的Challenge与Blob拼接在一起)。得到一个16字节的NTProofStr
  2. 将NTProofStr与Blob拼接起来形成得到response。

至于选择哪个版本的响应由LmCompatibilityLevel决定。

通过组合usernamedomainchallengeNTProofStrNTMLv2 response得到最终的Net-NTML-Hash

  • challenge为第二步响应中:ntlmssp.ntlmserverchallenge
  • NTProofStr为:ntlmssp.ntlmv2_response
  • NTMLv2 response为:这里并非全部的NTMLv2 response,需要去掉NTProofStr部分。

username::domain:challenge:HMAC-MD5:blob

code::DESKTOP-VCBQ663::0dc777436569ba02::8b40cef49d75eb381e0e839c9d67bf33:01010000000000007ee5f5e88999d701da61be980d5ef0120000000002001e00570049004e002d00390035004c004400330037004d004c0034004100390001001e00570049004e002d00390035004c004400330037004d004c0034004100390004001e00570049004e002d00390035004c004400330037004d004c0034004100390003001e00570049004e002d00390035004c004400330037004d004c00340041003900070008007ee5f5e88999d70106000400020000000800300030000000000000000100000000200000646d9a6112ce450b82af68bbb2676ad7e6b2b63e9014ffcad271bbe2d443cd2d0a0010000000000000000000000000000000000009002a00520050004300530053002f003100390032002e003100360038002e003100300031002e003100370030000000000000000000

参考:

https://docs.microsoft.com/zh-CN/troubleshoot/windows-server/windows-security/ntlm-user-authentication

https://docs.microsoft.com/zh-cn/windows/win32/secauthn/microsoft-ntlm

https://docs.microsoft.com/zh-cn/windows/win32/secauthn/lsa-authentication

https://docs.microsoft.com/zh-cn/windows/security/identity-protection/access-control/security-identifiers

https://daiker.gitbook.io/windows-protocol/ntlm-pian/4

https://docs.microsoft.com/zh-cn/windows/win32/secauthn/msv1-0-authentication-package


本文始发于微信公众号(宽字节安全):Windows身份认证

  • 左青龙
  • 微信扫一扫
  • weinxin
  • 右白虎
  • 微信扫一扫
  • weinxin
admin
  • 本文由 发表于 2022年10月1日20:51:09
  • 转载请保留本文链接(CN-SEC中文网:感谢原作者辛苦付出):
                   Windows身份认证https://cn-sec.com/archives/536786.html

发表评论

匿名网友 填写信息