NtSuspendThread
Erhöht den Suspend-Zähler eines Ziel-Threads und hält dessen Ausführung an.
Prototyp
NTSTATUS NtSuspendThread( HANDLE ThreadHandle, PULONG PreviousSuspendCount );
Argumente
| Name | Type | Dir | Description |
|---|---|---|---|
| ThreadHandle | HANDLE | in | Handle auf den zu suspendierenden Thread. Erfordert THREAD_SUSPEND_RESUME. |
| PreviousSuspendCount | PULONG | out | Optionaler Zeiger, der den vorherigen Suspend-Zähler empfängt. |
Syscall-IDs pro Windows-Version
| Windows-Version | Syscall-ID | Build |
|---|---|---|
| Win10 1507 | 0x1A0 | win10-1507 |
| Win10 1607 | 0x1A9 | win10-1607 |
| Win10 1703 | 0x1AF | win10-1703 |
| Win10 1709 | 0x1B2 | win10-1709 |
| Win10 1803 | 0x1B4 | win10-1803 |
| Win10 1809 | 0x1B5 | win10-1809 |
| Win10 1903 | 0x1B6 | win10-1903 |
| Win10 1909 | 0x1B6 | win10-1909 |
| Win10 2004 | 0x1BC | win10-2004 |
| Win10 20H2 | 0x1BC | win10-20h2 |
| Win10 21H1 | 0x1BC | win10-21h1 |
| Win10 21H2 | 0x1BE | win10-21h2 |
| Win10 22H2 | 0x1BE | win10-22h2 |
| Win11 21H2 | 0x1C8 | win11-21h2 |
| Win11 22H2 | 0x1CC | win11-22h2 |
| Win11 23H2 | 0x1CC | win11-23h2 |
| Win11 24H2 | 0x1CF | win11-24h2 |
| Server 2016 | 0x1A9 | winserver-2016 |
| Server 2019 | 0x1B5 | winserver-2019 |
| Server 2022 | 0x1C4 | winserver-2022 |
| Server 2025 | 0x1CF | winserver-2025 |
Kernel-Modul
Verwandte APIs
Syscall-Stub
4C 8B D1 mov r10, rcx B8 CF 01 00 00 mov eax, 0x1CF F6 04 25 08 03 FE 7F 01 test byte ptr [0x7FFE0308], 1 75 03 jne short +3 0F 05 syscall C3 ret CD 2E int 2Eh C3 ret
Undokumentierte Hinweise
NtSuspendThread ist die Kernel-Primitive hinter SuspendThread / Wow64SuspendThread. Die SSN driftet stark zwischen Builds, weil sie im oberen, alphabetisch sortierten Bereich der System Service Descriptor Table liegt — jeder davor eingefügte neue Syscall verschiebt sie. Jeder erfolgreiche Aufruf erhöht den vom Kernel verfolgten Suspend-Zähler (KTHREAD->SuspendCount); der Thread läuft erst weiter, wenn der Zähler durch passende NtResumeThread-Aufrufe wieder auf null sinkt. Die Routine mündet in KeSuspendThread / PsSuspendThread innerhalb von ntoskrnl.exe.
Häufige Malware-Nutzung
Zwei dominante Missbrauchsmuster. Erstens: Thread Hijacking — bestehenden Thread suspendieren, NtGetContextThread, RIP/RSP auf Shellcode umschreiben, NtSetContextThread, NtResumeThread (T1055.003). Zweitens, zunehmend häufig: EDR/AV-Scan-Threads im selben oder einem Remote-Prozess suspendieren, um eine Race Condition zu gewinnen. Varianten (NanoDump-Stil) suspendieren alle Threads von lsass.exe vor dem Lesen des Speichers, um einen kohärenten Snapshot ohne Thread-Erzeugungs-Telemetrie zu erhalten. Verwendet von Cobalt Strikes `inject`-BOFs, Slivers Process-Hollowing-Payloads und den meisten modernen Doppelganging-/Ghosting-Loadern.
Erkennungsmöglichkeiten
NtSuspendThread auf einem Remote-Thread ist selten und signalstark — legitime Suspender sind Debugger, Profiler, .NET-GC und einige Kompatibilitäts-Shims. Sysmon protokolliert es nicht nativ; per ETW-TI (Microsoft-Windows-Threat-Intelligence: EtwTiLogSuspendThread) oder via Kernel-Callback (ObRegisterCallbacks auf Thread-Handles mit THREAD_SUSPEND_RESUME) erfassen. Cross-Process-Suspends auf Threads von Sicherheitsprodukten (MsMpEng.exe, Sense.exe, cylancesvc.exe) sollten mit hoher Konfidenz alarmiert werden. EDR-User-Mode-Hooks auf ntdll!NtSuspendThread werden üblicherweise per direkten/indirekten Syscalls umgangen — Kernel-Telemetrie ist der verlässliche Weg.
Direkte Syscall-Beispiele
asmx64 direct stub (Win11 24H2)
; SSN 0x1CF on Win11 24H2 — do NOT hardcode across builds.
NtSuspendThread PROC
mov r10, rcx ; ThreadHandle
mov eax, 1CFh
syscall
ret
NtSuspendThread ENDPcSuspend-all before LSASS dump
// Snapshot all threads in target, suspend each, then read memory.
// Mirrors NanoDump / HandleKatz technique.
HANDLE hSnap = CreateToolhelp32Snapshot(TH32CS_SNAPTHREAD, 0);
THREADENTRY32 te = { .dwSize = sizeof(te) };
for (BOOL ok = Thread32First(hSnap, &te); ok; ok = Thread32Next(hSnap, &te)) {
if (te.th32OwnerProcessID != lsassPid) continue;
HANDLE hT = NtOpenThread_direct(THREAD_SUSPEND_RESUME, te.th32ThreadID);
if (hT) { NtSuspendThread_direct(hT, NULL); CloseHandle(hT); }
}rustNaked syscall (windows-sys 0.59)
use std::arch::asm;
#[unsafe(naked)]
unsafe extern "system" fn nt_suspend_thread_stub() {
asm!(
"mov r10, rcx",
"mov eax, 0x1CF", // Win11 24H2 only
"syscall",
"ret",
options(noreturn),
);
}MITRE ATT&CK-Mappings
Last verified: 2026-05-20