This article demonstrates using Microsoft WinDbg Time Travel Debugging (TTD) to accelerate dynamic analysis of an obfuscated multi-stage .NET dropper that performs classic process hollowing, allowing analysts to quickly locate CreateProcess* and WriteProcessMemory calls and extract an injected PE. The case study shows extracting an AgentTesla payload and configuration from memory by querying the debugger data model and using LINQ filters plus low-level commands like !tt, !dh, and .writemem. #AgentTesla #WinDbg
Keypoints
- Time Travel Debugging (TTD) records deterministic, replayable execution traces for user-mode processes, enabling rewindable analysis and shareable trace files.
- TTD paired with WinDbgâs Debugger Data Model and LINQ queries lets analysts rapidly search for specific API calls (e.g., CreateProcess*, WriteProcessMemory*) to triage behavior without manual stepping.
- The examined .NET dropper used P/Invoke to call native Windows APIs and performed classic process hollowing by creating InstallUtil.exe suspended, unmapping, writing a PE, and resuming the thread.
- Practical TTD triage steps shown: record trace with ttd.exe, use dx to inspect Debugger objects, query @$cursession.TTD.Calls for suspicious APIs, navigate to a time position with !tt, and inspect stack/parameters.
- TTDâs limitations include user-mode-only traces, proprietary trace format tied to WinDbg, and inability to alter past execution (a new trace is required to observe different outcomes).
- Memory writes identified (WriteProcessMemory) matched PE header and section sizes, allowing extraction of the injected .NET PE via .writemem and confirmation with !dh; the payload was AgentTesla.
- Recording child processes requires the -children flag; traces produce .run, .idx, and .out files, and FLARE-VM provides a convenient environment for WinDbg/TTD analysis.
MITRE Techniques
- [T1055 ] Process Injection â The dropper used process hollowing by creating a suspended InstallUtil.exe, unmapping original sections, writing a malicious PE into the target process memory, modifying thread context, and resuming the thread; quoted: âCreateProcess (with the CREATE_SUSPENDED flag)⌠ZwUnmapViewOfSection or NtUnmapViewOfSection⌠VirtualAllocEx and WriteProcessMemory⌠GetThreadContext⌠SetThreadContext⌠ResumeThread.â
- [T1106 ] Execution through API â The malware invoked native Windows APIs from managed .NET code via P/Invoke to perform hollowing and memory writes; quoted: âmanaged .NET code direct access to the unmanaged Windows API, allowing authors to port⌠process hollowing into their code.â
- [T1012 ] Query Registry (Startup Persistence) â The sample contained configuration values indicating startup persistence names and registry entries (e.g., StartupRegName = âeXCXESâ), suggesting registry-based persistence; quoted: âpublic static string StartupRegName = âeXCXESââ.
- [T1055.002 ] Process Hollowing (sub-technique) â The classic hollowing steps (suspend, unmap, write PE, set thread context, resume) were explicitly observed and triaged via TTD; quoted: âThe classic process hollowing steps are as follows: CreateProcess⌠ZwUnmapViewOfSection⌠WriteProcessMemory⌠GetThreadContext⌠SetThreadContext⌠ResumeThread.â
Indicators of Compromise
- [File name ] Suspicious child process â InstallUtil.exe (launched from %windir%Microsoft.NETFrameworkInstallUtil.exe) observed as a child of the sample.
- [File hash ] sample used for trace recording â 0b631f91f02ca9cffd66e7c64ee11a4b.bin (trace file named 0b631f91f02ca9cffd66e7c64ee11a4b02.run).
- [Strings / Configuration ] extracted config values â StartupInstallationName: âeXCXES.exeâ, StartupRegName: âeXCXESâ, SmtpServer and SmtpSender present (redacted in article).
- [Memory offsets / addresses ] Write targets â example write addresses observed in trace: 0x400000 (PE base), 0x402000, 0x43e000, 0x440000 related to WriteProcessMemory calls.
- [PE header signature ] in-memory PE evidence â MZ header found at memory 0x9810af0 confirming an injected PE image; additional extracted sections written to disk via .writemem (headers.bin, text.bin, rsrc.bin).