将 Volatility 3 内存取证框架从 Python 移植到 Rust 的版本。它读取相同的内存镜像,以相同的选项运行相同的插件,并输出相同的结果,逐字节一致,但速度要快得多。
本项目是 Volatility 3 的移植版本,因此属于 Volatility 软件许可证 1.0 下的“附加作品”,并以相同的许可证发布。全文见 LICENSE,在线版本见 https://www.volatilityfoundation.org/license/vsl-v1.0。每个源文件都保留了记录其派生来源的声明。
本项目与 Volatility Foundation 无关联,也未获得其认可。使用 Volatility 名称仅用于说明本项目的移植来源。
需要 Rust 1.85 或更高版本,然后执行:
cargo build --release
生成的二进制文件位于 target/release/vol-rs。无需任何可选依赖。符号解压缩、RC4、DES、AES、YARA 匹配、x86 反汇编、PNG 写入和 tar 归档均已内置,而 Python 版本则需要依赖 pycryptodomex、yara-python、capstone 和 pillow。
./target/release/vol-rs -f memory.raw windows.pslist.PsList
./target/release/vol-rs -f memory.lime linux.bash.Bash
./target/release/vol-rs -f memory.raw -r csv windows.netscan.NetScan
./target/release/vol-rs windows.malfind.Malfind --help
./target/release/vol-rs --list-plugins
Python 版本接受的每个选项在此同样支持,名称和默认值均相同,包括 -o、-r、-s、-c、-e、--filters、--hide-columns、--save-config、--stackers 和 --single-swap-locations。每个插件自身的选项也完全匹配,帮助页面中均有展示:全部 197 个插件的帮助页面与 Python 版本逐字符一致。
符号包存放于 $XDG_DATA_HOME/vol-rs/symbols,若该变量未设置,则存放于 ~/.local/share/vol-rs/symbols。其他位置的符号包可通过 --symbol-dirs 或 VOLRS_SYMBOL_PATH 环境变量指定。Windows 符号按需从 Microsoft 符号服务器获取,并缓存在 ~/.cache/vol-rs 下。
两个版本均针对相同的捕获文件运行并进行差异比对,包括头部框架和末尾换行符:
| 检查项 | 结果 |
|---|---|
| 无参数运行的 Windows 插件 | 100 个中 99 个完全一致 |
| 无参数运行的 Linux 插件 | 57 个中 56 个完全一致 |
| 带参数运行的实例 | 43 个中 43 个完全一致 |
未比对一致的八个文件属于下方“已知差异”中列出的两种情况。其中七个是 Python 版本在报告无法转储后遗留在磁盘上的部分文件,本移植版本不会创建这些文件;另一个是 tar 归档,其内容一致,但时间戳记录了各自的运行时间。
上述计数中缺失的两个插件是 Python 版本在测试机器上无法完成的插件。windows.memmap.Memmap 在输出 780 万行后被内存不足杀手终止,linux.pscallstack.PsCallStack 在结束前被终止。在这两种情况下,Python 版本先写出的每一行都被精确复现。
在所有无参数运行的插件中,Windows 扫描在此处耗时 273 秒,而 Python 版本耗时 5723 秒;Linux 扫描在此处耗时 68 秒,而 Python 版本耗时 3130 秒。
以下为每个捕获文件中差距最大的十个插件(针对所有无参数运行的插件):
BENCHMARKS.md 包含其余内容:两个捕获文件上的所有插件、带参数运行的实例,以及测量所用机器的信息。
少数内容无法完全一致,且均为有意为之:
linux.pagecache.RecoverFs 会在其写入的 tar 归档中的每个文件上盖上插件运行时刻的时间戳,因此任意两次运行结果都不会一致,即使是两次 Python 运行也是如此。表格内容一致,解包后的目录树也一致。--save-config 和 timeliner --record-config 会记录描述镜像的所有设置,但不记录 Python 版本对导入组件版本是否足够新的检查,因为本移植版本没有此类检查需要记录。linux.mountinfo --mount-format 会拼接一个 Python 集合,因此其列顺序在两次 Python 运行之间会发生变化。本移植版本先列出挂载选项,再列出文件系统选项,顺序与内核保存的顺序一致。frameworkinfo 和 isfinfo 描述的是工具本身而非镜像,因此它们报告的是本移植版本自身的层、插件和符号文件。windows.dumpfiles 不会遗留 Python 版本在发现无法读取文件之前创建的部分文件。表格内容一致,目录差异仅在于这些文件。--help 中命名缓存目录的行指向本移植版本自身的缓存目录。以下内容均已移植并构建成功,但尚未针对真实证据运行:
Volatility 3 是 Volatility Foundation 及其贡献者的成果。本项目是对其设计、插件集和输出格式的移植,其存在正是因为这些工作是开放的。
| 提取类插件写入的文件 |
| 比较了 1,747 个文件,两个工具写入的每个文件均相同 |
| 插件帮助页面 | 197 个中 197 个完全一致 |
| 插件 | Rust | Python | 加速比 |
|---|
windows.malware.suspicious_threads.SuspiciousThreads | 0.47 秒 | 281.6 秒 | x599 |
windows.suspicious_threads.SuspiciousThreads | 0.50 秒 | 259.1 秒 | x518 |
windows.malware.hollowprocesses.HollowProcesses | 0.52 秒 | 257.9 秒 | x496 |
windows.suspended_threads.SuspendedThreads | 0.090 秒 | 42.0 秒 | x467 |
windows.malware.malfind.Malfind | 0.52 秒 | 236.5 秒 | x455 |
windows.hollowprocesses.HollowProcesses | 0.59 秒 | 263.0 秒 | x446 |
windows.debugregisters.DebugRegisters | 0.090 秒 | 37.0 秒 | x411 |
windows.malfind.Malfind | 0.65 秒 | 239.7 秒 | x369 |
windows.vadinfo.VadInfo | 0.99 秒 | 329.7 秒 | x333 |
windows.verinfo.VerInfo | 0.99 秒 | 150.7 秒 | x152 |
| 插件 | Rust | Python | 加速比 |
|---|
linux.library_list.LibraryList | 1.99 秒 | 788.7 秒 | x396 |
linux.kallsyms.Kallsyms | 2.41 秒 | 161.6 秒 | x67 |
linux.netfilter.Netfilter | 0.89 秒 | 56.3 秒 | x63 |
linux.lsof.Lsof | 0.89 秒 | 55.6 秒 | x62 |
linux.sockstat.Sockstat | 1.60 秒 | 97.2 秒 | x61 |
linux.check_idt.Check_idt | 0.82 秒 | 49.7 秒 | x61 |
linux.malware.netfilter.Netfilter | 1.07 秒 | 62.0 秒 | x58 |
linux.pagecache.Files | 1.67 秒 | 93.4 秒 | x56 |
linux.kthreads.Kthreads | 0.87 秒 | 47.2 秒 | x54 |
linux.proc.Maps | 2.53 秒 | 135.4 秒 | x54 |