AD2025: EnableShadowStack¶
Summary¶
| Property | Value |
|---|---|
| ID | AD2025 |
| Name | EnableShadowStack |
| Category | Security |
| Severity | Warning |
| Applies to | PE (Windows) |
Description¶
Binaries should enable Intel Control-flow Enforcement Technology (CET) Shadow Stack to provide hardware-enforced protection against Return-Oriented Programming (ROP) attacks.
When enabled, the processor maintains a shadow stack that mirrors return addresses, making ROP exploits significantly harder.
How It Works¶
The rule checks for CET compatibility in the PE load configuration directory. CET Shadow Stack works by:
- Hardware maintains a separate "shadow stack" for return addresses
- On function call, return address pushed to both normal and shadow stack
- On function return, addresses are compared
- Mismatch = ROP attack detected = process terminated
Why This Matters¶
Return-Oriented Programming (ROP) has been the dominant exploitation technique for over a decade. Intel CET Shadow Stack provides hardware-enforced protection that makes ROP attacks significantly harderβpotentially obsoleting this entire attack class.
The ROP Problem¶
ROP attacks exploit the gap between /GS cookie checks and the actual return:
Without Shadow Stack:
1. Attacker corrupts return address on stack
2. /GS cookie check happens (passes, cookie intact)
3. Function returns to attacker-controlled address
4. Attacker chains "gadgets" ending in RET
5. Arbitrary computation achieved
ROP works because the CPU can't distinguish legitimate from corrupted return addresses.
How Shadow Stack Works¶
CET Shadow Stack maintains a protected copy of return addresses:
Normal Stack: Shadow Stack:
[Local vars] (hardware protected)
[Cookie]
[Saved RBP]
[Return addr] <-------> [Return addr]
On CALL: Return address pushed to both stacks
On RET: Addresses compared; mismatch = fault
The shadow stack is: - In a separate memory region - Protected by hardware (can't be written by normal instructions) - Managed by the CPU, not software
Attack Prevention¶
With Shadow Stack, ROP fails:
1. Attacker corrupts return address on normal stack
2. Function returns
3. CPU compares normal stack vs shadow stack
4. Mismatch detected!
5. #CP (Control Protection) fault β process terminated
Performance Characteristics¶
Unlike software-only mitigations, CET has minimal overhead:
| Metric | Overhead |
|---|---|
| CALL instruction | +1 cycle (shadow push) |
| RET instruction | +1 cycle (shadow compare) |
| Overall | ~0% measurable in most workloads |
This is because the operations are handled in hardware, in parallel with normal execution.
Hardware Requirements¶
CET Shadow Stack requires specific CPU support:
| Vendor | First Supporting CPU | Date |
|---|---|---|
| Intel | 11th Gen Core (Tiger Lake) | 2020 |
| AMD | Zen 3 (Ryzen 5000) | 2020 |
Software must be compiled with CET support AND run on compatible hardware for protection to be active.
Interaction with Other Mitigations¶
| Mitigation | Protection | CET Adds |
|---|---|---|
| /GS | Stack buffer overflow detection | ROP prevention |
| CFG | Forward-edge CFI | Backward-edge CFI |
| ASLR | Address randomization | Return validation |
CET Shadow Stack provides the critical "backward edge" protection that CFG lacks.
JIT and Shadow Stack¶
JIT compilers require special handling:
- JIT code must use CET-compatible calling conventions
- Shadow stack must be properly managed for dynamic code
- Some JIT patterns may need adaptation
Major browsers and runtimes have added CET support.
Deployment Status¶
| Platform | Status |
|---|---|
| Windows 10 20H1+ | Supported |
| Windows 11 | Enabled by default |
| Linux 6.6+ | Userspace support added |
| Major browsers | Chrome, Edge support CET |
Resolution¶
Enable CET Compatibility¶
Linker flag:
Project Properties¶
- Open Project Properties
- Navigate to Linker β Advanced
- Set "CET Shadow Stack Compatible" to "Yes"
CMake¶
When to Suppress¶
This rule may be suppressed for:
- Older Windows: CET requires Windows 10 20H1 or later
- Older hardware: Requires Intel 11th gen (Tiger Lake) or AMD Zen 3+
- Compatibility issues: Some JIT engines may conflict
- Performance testing: Comparing with/without CET
Caveats¶
- Requires Windows 10 version 2004 (20H1) or later
- Requires hardware support (Intel CET or AMD equivalent)
- JIT compilers need special handling
- All modules in process should be CET-compatible for full protection
Hardware Requirements¶
| Vendor | Minimum CPU |
|---|---|
| Intel | 11th Gen Core (Tiger Lake) |
| AMD | Zen 3 (Ryzen 5000 series) |
Software Requirements¶
| Component | Minimum Version |
|---|---|
| Windows | 10 20H1 (build 19041) |
| Visual Studio | 2019 16.7+ |
| MSVC | 19.27+ |
How CET Shadow Stack Works¶
Normal Stack Shadow Stack
βββββββββββββββ βββββββββββββββ
β Return Addr β ββββ β Return Addr β β CPU compares on RET
βββββββββββββββ€ βββββββββββββββ€
β Local Vars β β Return Addr β
βββββββββββββββ€ βββββββββββββββ
β Return Addr β ββββ (verified)
βββββββββββββββ
ROP Attack:
1. Attacker overwrites return address on normal stack
2. Shadow stack still has original address
3. RET instruction compares: MISMATCH!
4. CPU raises #CP exception β process terminated