In this module

MF1.3 Linux Acquisition with LiME and AVML

6 hours · Module 1 · Free
What you already know

From MF1.2 you know how WinPmem captures Windows memory: a signed driver loads into the kernel, reads physical pages, and writes a raw image. Linux acquisition uses the same physical-memory-read approach but with a fundamentally different delivery mechanism — a loadable kernel module (LiME) or a userspace tool that avoids the module requirement entirely (AVML). Both have constraints Windows practitioners don't expect.

Operational Objective

Linux memory acquisition is harder than Windows memory acquisition for one reason: kernel module version coupling. WinPmem ships a single binary that works across Windows 10 and 11 builds because the driver interface is stable. LiME is a loadable kernel module (LKM) that must be compiled against the exact kernel headers for the target system's running kernel. A module built for 5.15.0-91-generic will not load on 5.15.0-92-generic. One patch-level difference and the module refuses to insert.

This version-coupling means you can't carry a single LiME binary the way you carry WinPmem. You either pre-build modules for every kernel version in your environment (feasible for a fleet of identical Ubuntu servers, nightmarish for a heterogeneous estate), build on the target at acquisition time (requires build-essential and kernel headers on a system you're trying to not modify), or use AVML — Microsoft's acquisition tool that reads /proc/kcore from userspace and avoids the kernel module requirement entirely.

This sub covers both tools: LiME for when you can match the kernel version (which includes the course's Target-Linux VM, where you control the kernel), and AVML for when you can't. By the end, you'll have captured memory from your Target-Linux VM and verified it parses in Volatility 3.

Deliverable: Ability to capture Linux memory using LiME (compile, load, capture, verify) and AVML (download, execute, verify), understand when each is appropriate, troubleshoot kernel-version mismatch errors, and produce a verified Linux memory image from your Target-Linux VM.

Estimated completion: 45 minutes
LINUX MEMORY ACQUISITION — TWO PATHS LiME (Loadable Kernel Module) 1. Compile against target kernel headers 2. insmod lime.ko "path=/evidence/mem.lime" 3. Module reads physical memory via kernel API 4. Writes LiME format or raw padded format Constraint: exact kernel version match Constraint: root access required Advantage: highest fidelity kernel-level read Advantage: network capture (TCP output) AVML (Userspace) 1. Download single static binary 2. ./avml output.lime 3. Reads /proc/kcore (userspace access) 4. Writes LiME-compatible format Advantage: no kernel module compilation Advantage: works across kernel versions Constraint: /proc/kcore must be accessible Constraint: slightly higher smear (userspace)
Figure 1.3.1 — LiME operates at the kernel level with exact version coupling; AVML operates from userspace with broad compatibility. The course lab uses LiME (you control the kernel); production incidents may force AVML.

LiME — kernel module acquisition

This section covers the tool the course uses for Linux captures. The kernel-module architecture is LiME's strength and its constraint — understand both before you compile.

LiME (Linux Memory Extractor) is a loadable kernel module that reads physical memory through the kernel's internal page-mapping interface. Because it runs inside the kernel, it has the same level of access as the kernel itself — no page is off-limits, no mapping is restricted. This gives LiME the highest-fidelity read possible on a Linux system.

The cost is version coupling. Linux kernel modules are compiled against specific kernel headers, and the resulting .ko file contains a vermagic string that must exactly match the running kernel's version. insmod checks this string before loading the module and rejects mismatches. There is no cross-version compatibility, no "close enough" — the version must be identical down to the patch level and any distribution-specific suffix.

For the course's Target-Linux VM (Ubuntu 22.04 with a kernel you control), this isn't a problem. You install the kernel headers for your running kernel, compile LiME, and the module loads.

For production incident response against a server whose kernel version you didn't prepare for, this is a significant constraint. The options are: pre-build LiME modules for every kernel version in your fleet and carry them on your IR toolkit USB drive, compile on the target (which requires build-essential and headers, adding forensic footprint), or use AVML instead.

LiME supports three output modes. Disk output writes to a local file in LiME's own format, which Volatility 3 reads natively:

sudo insmod lime.ko "path=/evidence/mem.lime format=lime"

Raw padded output writes a raw image with zero-filled gaps for non-addressable physical ranges — similar to WinPmem's raw output but for Linux:

sudo insmod lime.ko "path=/evidence/mem.raw format=padded"

Network output streams the memory image over a TCP socket to a remote listener, avoiding any disk writes on the target:

# On analysis workstation (listener):
nc -l -p 4444 > target.lime

# On target (sender):
sudo insmod lime.ko "path=tcp:4444 format=lime"

Network capture is LiME's killer feature for minimal-footprint acquisition: the module loads, reads memory, streams the data to your analysis workstation, and unloads without ever writing to the target's filesystem.

AVML — userspace acquisition without kernel module constraints

This section covers the alternative when LiME's kernel-version coupling makes it infeasible. AVML trades slightly higher smear for dramatically broader compatibility.

AVML (Acquire Volatile Memory for Linux) is Microsoft's open-source Linux memory acquisition tool. Unlike LiME, AVML runs entirely in userspace — it reads memory through /proc/kcore, a pseudo-file the kernel exposes that represents physical memory as a virtual file.

Because AVML doesn't load a kernel module, it doesn't have a version-coupling constraint. The same AVML binary works on any Linux kernel that exposes /proc/kcore, which is most standard distributions.

The tradeoff is fidelity. A userspace read through /proc/kcore goes through the kernel's page-fault handler and mapping infrastructure rather than reading physical pages directly. AVML's capture is subject to slightly more smear than LiME's kernel-level read, because the userspace read path is longer and involves more kernel scheduling points.

In practice, the difference is small on systems with reasonable load — both tools produce images with comparable analysis results. The difference matters most on heavily loaded servers where the extra scheduling overhead produces measurably more torn structures.

AVML's constraint is that /proc/kcore must be accessible. Some hardened distributions restrict access (setting it to mode 0400 or disabling it via CONFIG_PROC_KCORE=n). Containerised environments and minimal kernel configurations may not expose it at all. When /proc/kcore isn't available, you're back to LiME or hypervisor-based acquisition.

The command is straightforward — download the static binary, make it executable, run with root:

sudo ./avml /evidence/target-linux.lime

AVML writes LiME-format output by default, which Volatility 3 reads natively. No compilation step, no kernel headers, no version matching. Hash the output immediately after capture.

Extended context — /proc/kcore internals and hardened-distribution restrictions

/proc/kcore is a pseudo-file that presents the kernel's view of physical memory as an ELF core dump. It's not a real file — reads from it trigger kernel code that maps the requested physical pages into the reading process's address space. The file's apparent size matches the kernel's physical address space (which on 64-bit systems can appear as terabytes even if physical RAM is only gigabytes, because the address space includes non-RAM regions like MMIO). AVML handles this by reading only the regions that correspond to actual RAM, skipping MMIO and reserved ranges.

Hardened distributions (CIS-benchmarked Ubuntu, RHEL with STIG, grsecurity-patched kernels) frequently restrict /proc/kcore access as a defense against kernel memory exposure. The restriction is sensible from a security posture — /proc/kcore is a window into kernel memory that attackers could use for credential extraction or kernel exploitation. For forensic acquisition, the same restriction blocks legitimate memory capture. The workaround is either to temporarily relax the restriction (if you have root) or to use LiME instead (kernel modules bypass /proc/kcore restrictions because they're already in the kernel).

When to use which — the Linux acquisition decision

This section gives you the decision rule. Don't memorise it — understand why each branch exists, and the decision falls out naturally.

The decision between LiME and AVML maps to the same fidelity-footprint-feasibility frame from MF1.1, with Linux-specific constraints layered on top.

Use LiME when you control the kernel version or have pre-built the module. The course lab is the canonical example: you installed Ubuntu 22.04 on Target-Linux, you know the kernel version, you can compile LiME against it. Production environments where you maintain a fleet of identical servers (same distribution, same kernel, same patch level) are similarly suited — pre-build LiME modules for your fleet's kernel versions and carry them on the IR toolkit. LiME's kernel-level read provides the highest fidelity, and the network output mode provides the lowest disk footprint.

Use AVML when you can't match the kernel version. Heterogeneous server estates, unfamiliar systems during incident response, cloud VMs where you don't control the kernel build, containerised environments where you have host access but not the kernel headers — AVML's single-binary portability solves the version-coupling problem. The fidelity tradeoff is acceptable for most investigations.

Use hypervisor-based acquisition (MF1.4) when you have hypervisor access. Same logic as Windows: zero guest footprint, zero version coupling, highest fidelity. VMware .vmem capture works identically for Linux guests and Windows guests.

Guided Procedure — Capture Target-Linux memory with LiME

This procedure runs against your MF0.9 Target-Linux VM (Ubuntu 22.04). You'll compile LiME, load the module, capture memory to a local file, and verify the image parses in Volatility 3.

Step 1 — Install prerequisites and clone LiME. SSH into Target-Linux. Run `sudo apt update && sudo apt install -y build-essential linux-headers-$(uname -r) git`. Then `git clone https://github.com/504ensicslabs/LiME.git && cd LiME/src && make`. The build produces `lime-$(uname -r).ko` in the current directory.
Expected output: `make` completes with no errors. `ls *.ko` shows a file named `lime-5.15.0-91-generic.ko` (or whatever your kernel version is). The version string in the filename must match `uname -r` exactly.
If it fails: "No rule to make target" → kernel headers not installed or version mismatch between `linux-headers-$(uname -r)` and the actual running kernel. Run `uname -r` and `apt list --installed | grep linux-headers` to compare. If they don't match, install the correct headers package or reboot into the kernel you have headers for.
Step 2 — Create evidence directory and load the module. Run `sudo mkdir -p /evidence && sudo insmod lime-$(uname -r).ko "path=/evidence/target-linux-baseline.lime format=lime"`. The module loads, captures memory, writes to the specified path, and remains loaded until you remove it.
Expected output: No terminal output (LiME is silent on success). `ls -lh /evidence/target-linux-baseline.lime` shows a file approximately equal to the VM's RAM size (2 GB for the standard Target-Linux build).
If it fails: "Invalid module format" → version mismatch between the compiled module and the running kernel. `modinfo lime-*.ko | grep vermagic` shows the compiled version; `uname -r` shows the running version. They must match exactly. Recompile against the correct headers. "Operation not permitted" → you're not root. Use `sudo`.
Step 3 — Unload the module and hash the image. Run `sudo rmmod lime` to unload the module. Then `sha256sum /evidence/target-linux-baseline.lime` and record the hash.
Expected output: `rmmod` returns silently (module unloaded). `sha256sum` prints a 64-character hex hash. This is your chain-of-custody anchor for the Linux baseline.
If it fails: `rmmod: ERROR: Module lime is not currently loaded` → the module already auto-unloaded after capture (some LiME builds do this). Not an error — the capture completed. Proceed to hash verification.
Step 4 — Transfer and verify in Volatility 3. Copy the image to your analysis workstation. Run `sha256sum` on the workstation copy to verify hash match. Then run `vol -f target-linux-baseline.lime linux.banner` — this is the Linux equivalent of `windows.info`.
Expected output: Hash matches the target-side hash. `linux.banner` reports the kernel version string (e.g., `Linux version 5.15.0-91-generic (buildd@lcy02-amd64-112) (gcc...)`). The version in the banner matches `uname -r` from step 1.
If it fails: Volatility 3 reports "Unable to determine OS" → the image format might be wrong (check that you used `format=lime` not `format=raw`), or Volatility 3 doesn't have the symbol table for this kernel. Run `vol -f image linux.banner --single-location file://path` and check for symbol-pack errors. For Ubuntu 22.04 stock kernels, the default Volatility 3 symbol pack should include the required ISF — if not, generate one with `dwarf2json`.
Decision Point

The situation. Northgate Engineering's RHEL 8.9 database server triggered a Sentinel alert for anomalous outbound traffic at 03:47. The SOC lead wants memory. The server is a physical host (no hypervisor), running kernel 4.18.0-513.24.1.el8_9.x86_64. Your IR toolkit has pre-built LiME modules for Ubuntu 22.04 kernels but not RHEL 8.9. You have root SSH access. You also have the AVML static binary on your toolkit USB.

The choice. Compile LiME on the target (requires installing kernel-devel and gcc on a production database server during an active incident), use your pre-built LiME module (wrong kernel version, won't load), or use AVML.

The correct call. AVML. The pre-built LiME module won't load — RHEL 8.9's kernel is a different version entirely from your Ubuntu 22.04 builds. Compiling LiME on the target is technically possible but forensically costly: yum install kernel-devel gcc modifies the target's package state, writes to disk, and increases the forensic footprint on a system you're trying to preserve. AVML avoids both problems — it's a single static binary, no compilation, no package installation, and it reads through /proc/kcore without kernel-version coupling. Document the decision: "LiME not used due to kernel-version mismatch (pre-built for Ubuntu, target is RHEL 8.9); AVML selected to avoid modifying production server's package state during active incident."

The operational lesson. Pre-building LiME modules only helps for the kernels you anticipated. A heterogeneous fleet — Ubuntu on workstations, RHEL on servers, Amazon Linux on EC2 — means you either maintain LiME builds for every kernel in your estate (expensive) or carry AVML as the universal fallback (pragmatic). Most IR teams do both: LiME for the kernels they know, AVML for everything else.

Compliance Myth: "Linux memory acquisition requires compiling code on the target system"

The myth. To capture Linux memory, you need to compile LiME on the target server, which means installing a compiler and kernel headers on a system that's part of an active investigation. The compilation changes the system state, which means the acquisition is forensically compromised before it begins. Linux memory acquisition is therefore fundamentally less forensically sound than Windows acquisition.

The reality. The myth is true only if LiME is your only option and you didn't pre-compile. Three alternatives avoid target-side compilation entirely. Pre-compiled LiME modules (built on a matching-kernel system in advance and carried on the IR toolkit) load with insmod — no compilation on target. AVML runs as a static binary with no compilation step at all. Hypervisor-based acquisition (MF1.4) captures the VM's memory from outside the guest and touches nothing inside it.

The forensically strongest Linux acquisition path is hypervisor suspension for VMs, followed by pre-compiled LiME or AVML for physical hosts. Compiling on the target is the last resort, not the default, and it's still forensically defensible if documented correctly — the compilation footprint is identifiable and excludable, the same way WinPmem's own process is identifiable in a Windows capture. The claim that Linux acquisition is "less sound" than Windows conflates the worst-case method with the only method.

Next

MF1.4 — Hypervisor-Based Acquisition. The gold standard for fidelity: suspend the VM, copy the .vmem file, resume. No guest-side tool, no driver, no kernel module, no smear. MF1.4 covers why this is the default for the course lab and when it's available in production.

Try it — Capture Target-Linux memory with LiME and verify in Volatility 3

Setup. Your MF0.9 Target-Linux VM running Ubuntu 22.04, with SSH access and root privileges. Internet access on the VM for apt install and git clone (if you haven't already installed the prerequisites).

Task. Execute the full Guided Procedure above: install prerequisites, compile LiME, load the module with format=lime, unload, hash, transfer to the analysis workstation, re-hash, and run vol -f target-linux-baseline.lime linux.banner. Confirm the banner's kernel version matches uname -r on Target-Linux.

Expected result. A LiME-format image approximately equal to Target-Linux's RAM size (2 GB default). Matching SHA-256 hashes on both systems. linux.banner output showing the Ubuntu 22.04 kernel version string. This is your Linux baseline image — keep it alongside the Windows baseline from MF1.2.

If your result doesn't match. If insmod fails with "Invalid module format," the kernel version mismatch is the cause — verify uname -r matches the .ko filename exactly. If linux.banner fails with "Unable to determine OS," Volatility 3 may be missing the ISF (Intermediate Symbol Format) for your kernel build — check the Volatility 3 symbol pack or generate a custom ISF with dwarf2json from the kernel's debug symbols package (linux-image-$(uname -r)-dbgsym).

Checkpoint — before moving on

You should be able to do the following without referring back to this sub. If you can't, the sections to re-read are noted.

1. Explain in one sentence why LiME requires exact kernel-version matching and what happens when the versions don't match. (§ LiME — kernel module acquisition)
2. State the single command to capture Linux memory with AVML, and name the constraint that would prevent AVML from working on a hardened system. (§ AVML — userspace acquisition)
3. Given a RHEL server with no pre-built LiME module available and no hypervisor access, state which tool you'd use and why compiling LiME on the target is the last-resort option. (§ Decision Point)

You've set up the lab and captured your first clean baselines.

MF0 built the three-VM lab and established the memory forensics landscape. MF1 taught acquisition with WinPmem and LiME, integrity verification, and chain of custody. From here, you execute attacks and investigate what they leave behind.

  • 8 attack modules (MF2–MF9) — process injection, credential theft, fileless malware, persistence, kernel drivers, Linux rootkits, timeline construction, and a multi-stage capstone
  • You run every attack yourself — from Kali against your target VMs, then capture memory and investigate your own attack's artifacts with Volatility 3
  • MF9 Capstone — multi-stage chain (initial access → privilege escalation → credential theft → persistence → data staging), three checkpoint captures, complete investigation report
  • The lab pack — PoC kernel driver and LKM rootkit source code, setup scripts, 21 exercises, 7 verification scripts, investigation report templates
  • Cross-platform coverage — Windows and Linux memory analysis in one course, with the timeline module integrating evidence from both
Unlock with Specialist — £25/mo See Full Syllabus

Cancel anytime