Active Directory 手動列舉之擴展
Active Directory 手動列舉之擴展
列舉作業系統
環境說明 : 在 AD 相關的章節中,主要都是依據下列的 LAB 環境,IP 可能不同,但角色相同
攻擊機 192.168.45.248
靶機
- 192.168.203.70 DC
- 192.168.203.72 web04
- 192.168.203.73 files04
- 192.168.203.74 client74
- 192.168.203.75 client75
- 192.168.203.76 client76
已知一般使用者帳號密碼 stephanie / LegmanTeamBenzoin!!
網域名稱 corp.com
採用工具 PowerView,存放路徑 C:\Tools,匯入指令 Import-Module .\PowerView.ps1
kali 有內建位置在 /usr/share/windows-resources/powersploit/Recon/PowerView.ps1
第一步 RDP 進入到某一台 client,注意密碼因為有驚嘆號,所以要加上單引號
xfreerdp /u:stephanie /p:'LegmanTeamBenzoin!!' /d:corp.com /v:192.168.203.75
匯入 PowerView,記得要先 powershell -ep bypass
獲取網域電腦資訊 Get-NetComputer
LAB 很新,DC 都已經是 Windows Server 2022 Standard 版本
之前有提過 Powershell 的輸出可以使用跟資料庫一樣的 select 語法
若要列舉作業系統跟主機名可以使用 Get-NetComputer | select operatingsystem,dnshostname
如下圖列出現有網域的所有電腦作業系統與主機名稱,符合一開始的 LAB 環境定義
練習 1
DistinguishedName for the WEB04
語法 Get-NetComputer | select operatingsystem,dnshostname,distinguishedname
答案 : CN=web04,CN=Computers,DC=corp,DC=com
練習 2
FILES04 的確切作業系統版本是什麼?
指令 Get-NetComputer | select operatingsystem,dnshostname,operatingsystemversion
答案 10.0 (20348)
練習 3
使用 PowerView 枚舉修改後的 corp.com 網域中的作業系統 以取得標誌
指令 Get-NetComputer | select operatingsystem,dnshostname
這樣也可以 Get-NetComputer | findstr "OS{"
如果輸出在 Terminal 介面過長不好查看,可以透過輸出到檔案之後進行搜尋與查看
Powershell 結果輸出要檔案的指令範例 Get-NetComputer | Out-File -FilePath .\123.txt
枚舉權限和登入用戶
當使用者登入網域時,他們的憑證(credentials )將快取在他們登入的電腦的記憶體中
PowerView 的 Find-LocalAdminAccess 指令掃描網絡,嘗試確定目前使用者是否具有網域中任何電腦的管理權限。此命令依賴 OpenServiceW 函數,該函數將連接到目標電腦上的服務控制管理器(SCM)。SCM 基本上維護 Windows 電腦上已安裝服務和驅動程式的資料庫。PowerView 將嘗試使用 SC_MANAGER_ALL_ACCESS 存取權限開啟此資料庫,這需要管理權限,如果連線成功,PowerView 將認為目前的使用者在目標電腦上具有管理權限
下圖中可以看到目前登入的網域帳號是 corp\stephanie 與電腦為 client75
掃描結果顯示當前使用者對於 client74 也擁有管理權限
兩個最可靠的 Windows API 是
- NetWkstaUserEnum 需要管理者權限
- NetSessionEnum 不需要管理者權限
PowerView 的 Get-NetSession 指令在底層使用 NetWkstaUserEnum 和 NetSessionEnum API
指令需要指定要列舉的目標電腦名稱或 IP
指令 Get-NetSession -ComputerName files04 or Get-NetSession -ComputerName web04
如下圖沒有任何結果輸出,有可能真的沒有任何登入 Session 或是沒有權限查詢
此時可以加上參數 -Verbose 將會告知我們結果,同樣指令加上參數再來一次
如下圖可以明確得知是沒有權限
接著讓我們對本機採用相同的命令查詢,可以發現透過簡名或是網域完整名稱都沒有結果
但是透過 127.0.0.1 或是 192.168.203.75 則可以正常查詢
這是因為 LAB 環境中預設名稱的解析皆以 IPv6 來解析所造成
但 LAB 對其他機器預設是走 IPv4,這一點在探訪本機時要特別注意
測試另外一台 Client74 可以發現是走 IPv4
剛剛前面一開始跑 Find-LocalAdminAccess 有列舉出 Client74 有權限
所以這一次讓我們直接針對 Client74 進行 NetSession 列舉
指令 Get-NetSession -ComputerName client74
注意 CNAME 顯示的 IP 是我們用來查詢的 Client75,這表示顯示的該 Session 就是我們用來查詢 Get-NetSession 使用的 Session
根據 NetSessionEnum 的文檔有五種可能的查詢等級:0,1,2,10,502。等級 0 僅傳回建立會話的電腦的名稱。等級 1 和等級 2 傳回更多信息,但需要管理權限。
留下了 10 和 502 級。兩者都應該返回諸如電腦名稱和建立連接的用戶名稱之類的資訊。預設情況下,PowerView 使用 NetSessionEnum 的查詢等級 10
使用 NetSessionEnum 列舉工作階段所需的權限在 SrvsvcSessionInfo 登錄項目中定義
此登錄項目位於 HKEY_LOCAL_MACHINE\SYSTEM\CurrentControlSet\Services\LanmanServer\DefaultSecurity
有 fl 表示一條一條列出,沒有的話將無法透過 Terminal 介面閱讀,如下範例
其中有一條 [ BUILTIN\Users Allow ReadKey ] 這表示所有使用者都可以讀取該設定
即便有許多其他群組可以讀取與擁有控制權,但不包含遠端讀取
根據微軟的文檔,輸出末尾的長字串是 a Capability SID。事實上,文檔引用了我們輸出中的確切 SID。
功能 SID 是不可偽造的授權令牌,它授予 Windows 元件或通用 Windows 應用程式對各種資源的存取權。但是,它不會讓我們遠端存取感興趣的註冊表項。
在舊版 Windows 版本中(Microsoft 未指定), 經過驗證的使用者可以存取註冊表設定單元並從SrvsvcSessionInfo項目取得資訊。但是,遵循最小權限原則,常規網域使用者應該無法在網域內獲取此信息,這也可能是註冊表配置單元的權限發生變更的部分原因。在這種情況下,由於權限的原因,我們可以確定 NetSessionEnum 在預設的 Windows 11 上將無法取得此類資訊。
幸運的是,我們還可以使用其他工具,例如 SysInternals Suite 中的 PsLoggedOn 應用程式。文件指出,PsLoggedOn 將列舉 HKEY_USERS 下的註冊表項,以檢索 登入使用者的安全識別碼(SID) 並將 SID 轉換為使用者名稱。PsLoggedOn 也會使用 NetSessionEnum API 來查看誰透過資源共享登入電腦。
然而一個限制是 PsLoggedOn 依賴遠端註冊表服務來掃描關聯的金鑰。自 Windows 8 以來,Windows 工作站上預設未啟用遠端登錄服務,但係統管理員可以啟用它來執行各種管理任務、向後相容或安裝監視、部署工具、腳本、代理程式等。
在較高版本的 Windows Server 作業系統(例如 Server 2012 R2、2016 (1607)、2019 (1809) 和 Server 2022 (21H2))上,它也預設為啟用。如果啟用,該服務將在十分鐘不活動後停止以節省資源,但一旦我們與 PsLoggedOn 連接,它將重新啟用(使用自動觸發器)。
現在理論已經完成,讓我們嘗試對我們之前嘗試枚舉的計算機(從 FILES04 和 WEB04 開始)運行 PsLoggedOn。
該工具包含在微軟提供的好用 Powershell 工具包 PSTools 中,可以透過下列網址下載
https://learn.microsoft.com/zh-tw/sysinternals/downloads/pstools
直接使用 PsLoggedon.exe 針對 files04、web04 進行列舉
files04 有一個登入的 Session 帳號名稱是 CORP\jeff
web04 沒有顯示任何登入的 Session,記得上述理論也有可能是遠端註冊表服務沒有運行
接著重新列舉 client74,發現除了我們的帳號外還有一個 jeffadmin
但時間顯示 <unknown time> 表示該 Session 可能已經中斷但憑證(credentials )仍舊在
也發現另外一件事是 PsLoggedon 可以列舉出 Get-NetSession 無法列舉的使用者 Session
練習
以 stephanie 身分登入 CLIENT75 。找出 Stephanie 在哪台新電腦上具有管理權限,然後登入該電腦並從管理員桌面取得標誌
登入 75 後 Find-LocalAdminAccess 看一下結果有 web04 & client74 有權限
使用相同帳號密碼 RDP 進入到 web04 在 Administrator 使用者桌面找到 proof.txt
透過服務主體名稱進行枚舉
攻擊機 IP 更換為 192.168.45.172
靶機第三碼換為 250
SPN 全名 : Service Principal Name 服務主體名稱
所有網域中的 SPN 都會註冊到 AD,故可以直接查詢 AD 詢問所有 SPN
指令 setspn -L iis_service
IP 已改變換成登入到 192.168.250.74 RDP
└─$ xfreerdp /u:stephanie /p:'LegmanTeamBenzoin!!' /d:corp.com /v:192.168.250.74
因為之前有 web04 所以我們直接列舉 IIS 服務帳號,指令 setspn -L iis_service
另一種列舉 SPN 帳號的方式是先列舉出所有網域帳號,然後用 select 輸出帳號與 SPN 欄位
指令 Get-NetUser -SPN | select samaccountname,serviceprincipalname
可以看到 iis_service 綁在了 HHTP/web04 上
練習
用於關聯到 Active Directory 中特定服務的唯一服務識別碼的名稱是什麼?
Ans : SPN
枚舉物件權限
ACE 全名 : Access Control Entries 存取控制條目
ACL 全名 : Access Control List 存取控制清單
ACL 由 ACE 所構成,每個 ACE 定義是否允許或拒絕對特定物件的存取
相關權限的描述清單
GenericAll: Full permissions on object
GenericWrite: Edit certain attributes on the object
WriteOwner: Change ownership of the object
WriteDACL: Edit ACE's applied to object
AllExtendedRights: Change password, reset password, etc.
ForceChangePassword: Password change for object
Self (Self-Membership): Add ourselves to for example a group
最強大的 ACL 為第一個 GenericAll
可以使用 Get-ObjectAcl 來列舉 ACE (PS: Get-ObjectAcl 隸屬 PowerView)
先看看自己的帳號擁有那些 ACE,指令 Get-ObjectAcl -Identity stephanie
可以存取的物件是以 SID 的方式顯示,這個雖然是 AD 物件唯一值但卻不易閱讀
一樣透過 PowerView 中的 Convert-SidToName 來顯示成易閱讀的值
例如 : Convert-SidToName S-1-5-21-1987370270-658905905-1781884369-1104
一般我們感興趣的值是 ActiveDirectoryRights 和 SecurityIdentifier 這兩個
下圖為例,RAS and IAS Servers 對使用者物件 stephanie 擁有 ReadProperty 權限
接著讓我們針對群組 "Management Department" 查看誰擁有最大權限 GenericAll
指令 Get-ObjectAcl -Identity "Management Department" | ? {$_.ActiveDirectoryRights -eq "GenericAll"} | select SecurityIdentifier,ActiveDirectoryRights
並將條列出的 SID 一一做 convert 成 name
在轉換 SID to Name 時可以一個一個轉換或是一次輸入所有的 SID 進行轉換
指令 "S-1-5-21-1987370270-658905905-1781884369-512","S-1-5-21-1987370270-658905905-1781884369-1104","S-1-5-32-548","S-1-5-18","S-1-5-21-1987370270-658905905-1781884369-519" | Convert-SidToName
上圖中可以看到我們目前的使用者 stephanie 對管理部門群組擁有 GerericAll 權限,這個在一般網域管理中不常見,因為一般使用者帳號不會對 AD 相關物件擁有過大的權限,會出現如此的權限一般是設定錯誤或是擁有特殊的含意,這個就是在枚舉階段的精隨發現
接著查看該群組的成員 Get-NetGroup "Management Department" | select member
發現僅有一個網域使用者 jen 隸屬該群組
但既然現在的使用者帳號 stephanie 對該群組有最大權限,接著就是將自己的帳號加入該群組
指令 net group "Management Department" stephanie /add /domain
再列舉一次群組 member,現有帳號已隸屬該群組了
要清除帳號使用指令 net group "Management Department" stephanie /del /domain
再列舉一次群組成員,確認剩下 jen 一個帳號,確認現有帳號對該群組擁有權限
練習 1 : ACL 由哪些條目組成?
Ans : ACE
練習 2 : 對於 Active Directory 中的對象,我們可以擁有的最強大的 ACL 是什麼?
Ans : GerericAll
探索域名共享
一樣使用 PowerView 中的 Find-DomainShare 來尋找網域中的共用
使用 Find-DomainShare 列舉網域中的共享資源時需要一段時間,請耐心等候
練習 1 : 在corp.com網域中共用SYSVOL資料夾的伺服器的主機名稱是什麼 ?
Ans : DC1
SYSVOL 預設是 DC 上的 GPO 與腳本共享資料夾路徑,對應到 DC 上的路徑如下
%SystemRoot%\SYSVOL\Sysvol\domain-name,預設每個帳號都可以存取
所以可以先行查看該分享中的內容,ls \\dc1.corp.com\sysvol\corp.com\
跟預設一樣,一個 GPO 一個腳本資料夾
繼續查看資料夾 ls \\dc1.corp.com\sysvol\corp.com\Policies\
Policies 資料夾中有一個資料夾 oldpolicy,光看名稱就應該懷疑是否是梗,所以接著看
ls \\dc1.corp.com\sysvol\corp.com\Policies\oldpolicy,裡面有個 old-policy-backup.xml 檔案
查看一下內容 cat \\dc1.corp.com\sysvol\corp.com\Policies\oldpolicy\old-policy-backup.xml
看到有個 password = "+bsY0V3d4/KgX3VJdO/vyepPfAN1zMFTiQDApgR92JE"
帳號是 Administrator,看來是修改 Client 本機管理員密碼的一個腳本
從密碼來看是一個雜湊值,讓我們使用 kali 內建的 gpp-decrypt 來解密
指令 gpp-decrypt "+bsY0V3d4/KgX3VJdO/vyepPfAN1zMFTiQDApgR92JE"
密碼是 P@$$w0rd
gpp-decrypt 指令說明 https://www.kali.org/tools/gpp-decrypt/
一個簡單的 ruby 腳本,用於解密給定的 GPP 加密字串。
GPP 全名 : Group Policy Preferences 群組原則首選項
該密碼通常可以在名為 groups.xml 的檔案中找到
該檔案通常位於 SMB 共享資源的目錄中,名為SYSVOL,如果您找到該目錄並且您對其具有讀取權限,請利用它,並尋找名為 groups.xml 的檔案
在檔案內部,我們唯一感興趣的是名為 cpassword 的參數中存在的雜湊值
至於 GPP 怎麼加密密碼的呢,微軟有發布在此 https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-gppref/2c15cbf0-f086-4c74-8b70-1f2fa45dd4be?source=post_page-----4edb9a1663c4-------------------------------- 直接告訴你怎麼加密的
在 payload all the thing 中也有提到如何解密 AD Group Policy 的密碼
另一個透過 Powershell 尋找 AD GPO 中的密碼好用指令
findstr /S /I cpassword \\<FQDN>\sysvol\<FQDN>\policies\*.xml
本例中 FQDN 就是 "corp.com"
findstr /S /I cpassword \\dc1.corp.com\sysvol\corp.com\policies\*.xml
回到一開始列舉的 docshare ,發現在 files04 的共享有一個名稱為 docshare
只要是非 Windows 預設 Share 的名稱建議都可以查看 ls \\FILES04.corp.com\docshare
有個資料夾叫 docs
繼續 ls \\FILES04.corp.com\docshare\docs
檔案 environment.txt 內容看來僅是說明,沒有甚麼幫助
查看另一個有趣的資料夾 do-not-share,裡面有個 start-email.txt 文件
查看內容後拿到了帳號密碼 jeff / HenchmanPutridBonbon11
練習 : 使用 PowerView 找到修改後的 corp.com 網域中的共用並列舉它們以取得標誌
看到 files04 有一個叫做 Important Files 資料夾裡面有個 proof.txt,cat 後就發現 flag
留言
張貼留言