What You'll Learn
- Explain why memory forensics is essential for detecting fileless malware, injected code, and encryption keys that never touch disk
- Describe the major memory acquisition methods for Windows (winpmem, DumpIt, FTK Imager) and Linux (LiME)
- Explain Volatility 3's architecture including the framework, plugin system, and symbol table requirements
- Use
windows.pslistandwindows.pstreeto enumerate processes and identify suspicious parent-child relationships - Use
windows.netscanto extract active and recently closed network connections from memory - Use
windows.cmdlineto recover the full command-line arguments of every running process - Use
windows.malfindto detect injected code in process memory regions with executable, non-backed pages - Use
windows.filescanandwindows.dlllistto enumerate file handles and loaded DLLs - Apply a systematic memory analysis workflow to move from initial triage to definitive findings
- Identify common process injection techniques and their memory forensic signatures
Why Memory Forensics Matters
Every investigation technique you have learned so far examines artifacts on disk — log files, registry hives, filesystem timestamps, bash_history. But modern attackers increasingly operate in a space that disk forensics cannot reach: memory.
Fileless malware, process injection, living-off-the-land binaries, and in-memory-only payloads leave no files to find and no hashes to match. The encryption keys that protect an attacker's C2 channel exist only in RAM. The network connections that were active during the breach are recorded in memory structures, not log files. The injected shellcode that gave the attacker their foothold may have been loaded directly into a legitimate process — never written to disk.
| Evidence Type | Available on Disk? | Available in Memory? |
|---|---|---|
| Fileless malware payloads | No | Yes — injected into process address space |
| Active network connections | Partially (netstat logs if enabled) | Yes — full connection table with PIDs |
| Encryption keys (TLS, BitLocker, VeraCrypt) | No | Yes — keys are held in RAM during use |
| Process command-line arguments | Partially (event logs if auditing enabled) | Yes — stored in PEB for every process |
| Injected DLLs and shellcode | No (if reflectively loaded) | Yes — detectable via memory region analysis |
| Running rootkit components | No (hidden from disk tools) | Yes — memory structures reveal hidden processes |
| Clipboard contents | No | Yes — current clipboard data in memory |
| Recently typed passwords | No | Yes — often in cleartext in process memory |
Memory evidence is the most volatile evidence you will encounter. Once a system is powered off or rebooted, RAM contents are gone permanently. There is no "recycle bin" for memory. In a live incident, memory acquisition should happen BEFORE disk imaging — you can always image the disk later, but you cannot recover what was in RAM once power is lost.
Memory Acquisition Methods
Before you can analyze memory, you need to capture it. Memory acquisition creates a binary dump of the system's physical RAM — typically a file between 4 GB and 128 GB depending on the system.
Windows Acquisition Tools
| Tool | Type | Advantages | Considerations |
|---|---|---|---|
| winpmem | Open-source, command-line | Free, scriptable, supports raw and AFF4 formats | Requires admin privileges; some EDR may block the driver |
| DumpIt | Free (Comae/Magnet) | Single executable, no installation, one-click capture | Writes to current directory — ensure sufficient disk space |
| FTK Imager | Free (Exterro) | GUI-based, can capture memory + pagefile simultaneously | Larger footprint; installs a driver |
| Belkasoft RAM Capturer | Free | Minimal footprint, works on locked screens | Limited format options |
C:\> winpmem_mini_x64.exe memory.raw
C:\> DumpIt.exe
Linux Acquisition with LiME
LiME (Linux Memory Extractor) is a loadable kernel module that captures memory from a running Linux system:
sudo insmod lime-$(uname -r).ko "path=/evidence/memory.lime format=lime"
Compile LiME for the target kernel version BEFORE the incident. LiME must be compiled against the exact kernel headers of the system you are capturing. Having pre-compiled LiME modules for your standard server images in your forensic toolkit is essential — you will not have time to compile during an active incident.
Acquisition Best Practices
- Capture memory before disk — memory is more volatile
- Write the dump to an external drive — avoid overwriting evidence on the target system
- Hash the dump immediately —
sha256sum memory.raw > memory.raw.sha256for chain of custody - Document the time and method — note the exact UTC time and tool used
- Capture the pagefile too —
C:\pagefile.sysandC:\swapfile.sysmay contain swapped-out memory pages
Volatility 3 Architecture
Volatility is the industry-standard framework for memory forensic analysis. Volatility 3 (the current version) is a complete rewrite of the original Volatility 2, with significant architectural improvements.
Key Differences from Volatility 2
| Feature | Volatility 2 | Volatility 3 |
|---|---|---|
| Profile system | Required exact OS profile selection | Uses symbol tables (ISF) — auto-detects OS |
| Plugin naming | pslist | windows.pslist, linux.pslist (namespaced) |
| Performance | Slower, Python 2 | Faster, Python 3, better caching |
| Output formats | Text-based | JSON, CSV, text — pipeline-friendly |
| Symbol tables | Bundled profiles | Downloaded on-demand from symbol servers |
Running Volatility 3
python3 vol.py -f memory.raw windows.pslist
python3 vol.py -f memory.raw windows.pstree
python3 vol.py -f memory.raw windows.netscan
The basic syntax is always: vol.py -f <memory_dump> <plugin_name>
Symbol Tables
Volatility 3 needs symbol tables to understand the internal data structures of the operating system. For Windows, these are automatically downloaded from Microsoft's symbol server the first time you analyze a dump. For Linux, you may need to generate them from the target system's kernel debug symbols using dwarf2json.
Essential Plugins: Process Analysis
Process analysis is the foundation of memory forensics. Attackers must run code to accomplish their objectives, and that code runs as (or inside) a process.
windows.pslist — Process Listing
python3 vol.py -f memory.raw windows.pslist
PID PPID ImageFileName Offset Threads Handles SessionId
4 0 System 0x... 164 - N/A
88 4 Registry 0x... 4 - N/A
348 4 smss.exe 0x... 2 - N/A
444 436 csrss.exe 0x... 10 - 0
508 436 wininit.exe 0x... 3 - 0
528 500 csrss.exe 0x... 12 - 1
588 500 winlogon.exe 0x... 5 - 1
672 508 services.exe 0x... 8 - 0
684 508 lsass.exe 0x... 9 - 0
3284 672 svchost.exe 0x... 15 - 0
7420 3284 cmd.exe 0x... 1 - 0
7488 7420 powershell.exe 0x... 8 - 0
Key things to look for:
- Unexpected parent-child relationships —
cmd.exespawned bysvchost.exeis suspicious;powershell.exespawned bywinword.exeis almost certainly malicious - Processes with unusual names — misspellings like
scvhost.exeorlssas.exe - Multiple instances of singleton processes — there should be exactly one
lsass.exe, oneservices.exe, onewininit.exe - Processes running from unexpected paths — legitimate
svchost.exeruns fromC:\Windows\System32\, notC:\Users\Public\
windows.pstree — Process Tree
python3 vol.py -f memory.raw windows.pstree
This displays processes in a hierarchical tree format, making parent-child relationships immediately visible. Attackers who inject into legitimate processes or spawn suspicious child processes are much easier to spot in the tree view.
Know the normal Windows process tree. To identify abnormal, you must first know normal. System (PID 4) → smss.exe → csrss.exe + wininit.exe. wininit.exe → services.exe → svchost.exe (multiple). wininit.exe → lsass.exe. Any deviation from this hierarchy warrants investigation.
Essential Plugins: Network Analysis
windows.netscan — Network Connections
python3 vol.py -f memory.raw windows.netscan
Offset Proto LocalAddr LocalPort ForeignAddr ForeignPort State PID Owner
0x... TCPv4 10.0.1.50 49753 185.141.63.12 443 ESTABLISHED 7488 powershell.exe
0x... TCPv4 10.0.1.50 445 10.0.2.30 52891 ESTABLISHED 4 System
0x... TCPv4 10.0.1.50 80 0.0.0.0 0 LISTENING 1204 httpd.exe
0x... TCPv4 10.0.1.50 49771 10.0.2.15 4444 CLOSED 7420 cmd.exe
This is extraordinarily valuable forensic evidence:
- ESTABLISHED connections show what was actively communicating at the time of capture —
powershell.execonnecting outbound to185.141.63.12:443is a strong C2 indicator - CLOSED connections show recent connections that have ended —
cmd.execonnecting to port 4444 (Metasploit default) confirms exploitation - LISTENING ports reveal backdoors — unexpected services listening on unusual ports
- PID correlation links network activity to specific processes, which you can then investigate further
Essential Plugins: Command Lines and Code
windows.cmdline — Process Command Lines
python3 vol.py -f memory.raw windows.cmdline
PID Process Args
7420 cmd.exe cmd.exe /c whoami && net user /domain
7488 powershell.exe powershell.exe -nop -w hidden -enc SQBFAFgAIAAoA...
3284 svchost.exe C:\Windows\System32\svchost.exe -k netsvcs -p
The -enc flag in PowerShell with a Base64 string is one of the most common attack indicators. Decode it:
echo "SQBFAFgAIAAoA..." | base64 -d
windows.malfind — Injected Code Detection
python3 vol.py -f memory.raw windows.malfind
PID Process Start VPN End VPN Tag Protection Hexdump / Disasm
3284 svchost.exe 0x2a40000 0x2a41fff VadS PAGE_EXECUTE_READWRITE
4d 5a 90 00 03 00 00 00 MZ......
04 00 00 00 ff ff 00 00 ........
malfind identifies memory regions that are:
- Executable — marked with execute permissions (PAGE_EXECUTE_READWRITE or PAGE_EXECUTE_READ)
- Not backed by a file on disk — no corresponding DLL or EXE mapped from the filesystem
- Contain code patterns — the plugin shows the first bytes, often revealing PE headers (MZ) or shellcode
A PAGE_EXECUTE_READWRITE region containing an MZ header inside a legitimate process like svchost.exe is a near-certain indicator of process injection.
Dump injected code for further analysis. When malfind identifies suspicious memory regions, dump them with windows.malfind --dump and analyze the extracted binary with YARA rules (Module 7) or submit to a sandbox. This bridges memory forensics with malware analysis.
windows.filescan — File Handles
python3 vol.py -f memory.raw windows.filescan
This scans memory for FILE_OBJECT structures, revealing every file handle open at the time of capture — including files that may have been deleted from disk but were still open in memory.
windows.dlllist — Loaded DLLs
python3 vol.py -f memory.raw windows.dlllist --pid 7488
Lists every DLL loaded into a process. Compare against known-good DLL lists for that process. An unfamiliar DLL loaded from an unusual path (e.g., C:\Users\Public\malware.dll loaded into svchost.exe) indicates DLL injection or sideloading.
Process Injection Detection
Process injection is the technique of executing code within the address space of another process. Attackers use it to evade detection — the malicious code runs under the identity of a trusted process like svchost.exe or explorer.exe.
Common Injection Techniques and Their Memory Signatures
| Technique | How It Works | Memory Forensic Indicator |
|---|---|---|
| Classic DLL Injection | CreateRemoteThread + LoadLibrary to load a DLL into another process | Unexpected DLL in dlllist from a non-standard path |
| Reflective DLL Injection | DLL loaded directly from memory without touching disk | malfind: PE header (MZ) in RWX memory region with no file backing |
| Process Hollowing | Legitimate process created in suspended state, code replaced | pslist shows process with correct name but wrong image path or size |
| APC Injection | Asynchronous Procedure Call used to execute code in target thread | malfind: executable non-backed region in a thread's context |
| Shellcode Injection | Raw position-independent code written to allocated memory | malfind: small RWX regions without PE headers, often starting with \xfc\xe8 |
The Memory Analysis Workflow
A structured approach prevents you from missing critical artifacts:
Phase 1 — Process Triage
- Run
windows.pslistto get the full process listing - Run
windows.pstreeto visualize parent-child relationships - Identify suspicious processes: wrong parents, unusual names, wrong session IDs
Phase 2 — Network Triage
4. Run windows.netscan to map all network connections
5. Correlate PIDs from suspicious connections back to processes identified in Phase 1
6. Look for connections to known-bad IPs, unusual ports, or unexpected outbound traffic
Phase 3 — Deep Dive
7. Run windows.cmdline on suspicious PIDs to see their command-line arguments
8. Run windows.malfind to detect injected code
9. Run windows.dlllist on suspicious processes to check loaded modules
10. Run windows.filescan to find file handles of interest
Phase 4 — Extraction
11. Dump suspicious memory regions (--dump flag) for offline analysis
12. Extract injected code for YARA scanning or sandbox submission
13. Document all IOCs found: IPs, domains, file hashes, mutexes
Not every malfind hit is malicious. Some legitimate software (antivirus, DRM, game anti-cheat) uses executable memory regions that malfind will flag. The key is context: a RWX region containing an MZ header in svchost.exe is suspicious; a similar region in chrome.exe related to JIT compilation may be benign. Always correlate malfind results with other plugins before concluding injection.
Finding Hidden Processes
Sophisticated malware may attempt to hide processes from standard listing tools by unlinking them from the kernel's process list (Direct Kernel Object Manipulation — DKOM). Volatility can detect this:
python3 vol.py -f memory.raw windows.pslist
python3 vol.py -f memory.raw windows.psscan
windows.pslist walks the kernel's linked list of active processes — what the OS "sees." windows.psscan scans all of physical memory for process structures regardless of whether they are linked. Processes that appear in psscan but not pslist are either terminated processes whose structures have not been overwritten, or actively hidden processes using DKOM.
Memory IOC Extraction
Memory dumps are rich sources of indicators of compromise:
| IOC Type | How to Extract | Plugin |
|---|---|---|
| C2 IP addresses | Network connections in netscan output | windows.netscan |
| C2 domains | Strings in process memory | windows.strings + grep |
| Malware hashes | Dump injected regions, hash the output | windows.malfind --dump + sha256sum |
| Encryption keys | Specialized plugins for specific crypto | windows.hashdump, third-party plugins |
| Mutex names | Kernel object scan | windows.mutantscan |
| Registry artifacts | In-memory registry hives | windows.registry.printkey |
Key Takeaways
- Memory forensics reveals evidence that disk forensics cannot — fileless malware, injected code, encryption keys, and active network connections
- Acquire memory BEFORE disk — RAM evidence is the most volatile and cannot be recovered after power loss
- Volatility 3 uses symbol tables (not profiles), namespaced plugins (
windows.pslistnotpslist), and Python 3 windows.pslist+windows.pstreeexpose process relationships — know the normal Windows process tree to spot anomalieswindows.netscanreveals network connections tied to specific PIDs — critical for identifying C2 communicationwindows.cmdlinerecovers full command-line arguments including Base64-encoded PowerShell payloadswindows.malfinddetects injected code by finding executable, non-file-backed memory regions — MZ headers in RWX regions are near-certain injection indicators- Compare
pslistvspsscanto detect hidden processes using DKOM rootkit techniques - Follow the four-phase workflow: process triage → network triage → deep dive → extraction
- Dump suspicious memory regions for YARA analysis and sandbox submission — bridging memory forensics with malware analysis
What's Next
You can now investigate what happened on disk (Lesson 9.4) and in memory (this lesson). But a real investigation requires combining all artifacts into a single chronological view. Lesson 9.6 introduces building a forensic timeline — using tools like Plaso/log2timeline to merge filesystem timestamps, memory artifacts, log entries, and SIEM alerts into one unified super timeline that tells the complete story of an incident from initial compromise through data exfiltration.
Knowledge Check: Memory Forensics with Volatility 3
10 questions · 70% to pass
Why should memory acquisition be performed BEFORE disk imaging during a live incident?
What tool is used to acquire memory from a live Linux system?
How does Volatility 3 differ from Volatility 2 in identifying the operating system of a memory dump?
In Lab 9.5, you find powershell.exe (PID 7488) with an ESTABLISHED connection to 185.141.63.12:443. Which Volatility 3 plugin revealed this connection?
What does the windows.malfind plugin specifically look for in process memory?
You run windows.malfind and find a PAGE_EXECUTE_READWRITE region in svchost.exe starting with bytes '4d 5a 90 00'. What do these bytes indicate?
How can you detect a process hidden using Direct Kernel Object Manipulation (DKOM)?
During Lab 9.5 analysis, you find powershell.exe with the argument '-enc SQBFAFgA...'. What should your next investigative step be?
Which type of forensic evidence is available ONLY in memory and cannot be found through disk analysis?
What is the correct four-phase memory analysis workflow sequence?
0/10 answered