migrate windows and linux tests to dedicated files

This commit is contained in:
Abyss Watcher
2025-03-04 16:54:11 +01:00
parent f7dfab57fd
commit a162fceed4
4 changed files with 944 additions and 799 deletions
View File
+617
View File
@@ -0,0 +1,617 @@
import contextlib
import tempfile
import os
import re
from test import test_volatility, LinuxSamples
class TestLinuxVolshell:
def test_linux_volshell(self, image, volatility, python):
out = test_volatility.basic_volshell_test(
image, volatility, python, globalargs=("-l",)
)
assert out.count(b"<task_struct") > 100
class TestLinuxPslist:
def test_linux_generic_pslist(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.pslist.PsList", image, volatility, python
)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.find(b"watchdog") != -1
assert out.count(b"\n") > 10
class TestLinuxCheckIdt:
def test_linux_generic_check_idt(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.check_idt.Check_idt", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"__kernel__") >= 10
assert out.count(b"\n") > 10
class TestLinuxCheckSyscall:
def test_linux_generic_check_syscall(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.check_syscall.Check_syscall", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.find(b"sys_close") != -1
assert out.find(b"sys_open") != -1
assert out.count(b"\n") > 100
class TestLinuxLsmod:
def test_linux_generic_lsmod(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.lsmod.Lsmod", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"\n") > 10
class TestLinuxLsof:
def test_linux_generic_lsof(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.lsof.Lsof", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"socket:") >= 10
assert out.count(b"\n") > 35
class TestLinuxProcMaps:
def test_linux_generic_proc_maps(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.proc.Maps", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"anonymous mapping") >= 10
assert out.count(b"\n") > 100
class TestLinuxTtyCheck:
def test_linux_generic_tty_check(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.tty_check.tty_check", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.find(b"__kernel__") != -1
assert out.count(b"\n") >= 5
class TestLinuxSockstat:
def test_linux_generic_sockstat(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.sockstat.Sockstat", image, volatility, python
)
assert rc == 0
assert out.count(b"AF_UNIX") >= 354
assert out.count(b"AF_BLUETOOTH") >= 5
assert out.count(b"AF_INET") >= 32
assert out.count(b"AF_INET6") >= 20
assert out.count(b"AF_PACKET") >= 1
assert out.count(b"AF_NETLINK") >= 43
class TestLinuxLibraryList:
def test_linux_specific_library_list(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"linux.library_list.LibraryList",
image,
volatility,
python,
pluginargs=("--pids", "2363"),
)
assert rc == 0
assert re.search(
rb"NetworkManager\s2363\s0x7f52cdda0000\s/lib/x86_64-linux-gnu/libnss_files.so.2",
out,
)
assert out.count(b"\n") > 10
class TestLinuxPstree:
def test_linux_generic_pstree(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.pstree.PsTree", image, volatility, python
)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.count(b"\n") > 10
class TestLinuxPidhashtable:
def test_linux_generic_pidhashtable(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.pidhashtable.PIDHashTable", image, volatility, python
)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.count(b"\n") > 10
class TestLinuxBash:
def test_linux_bash(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.bash.Bash", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxBoottime:
def test_linux_generic_boottime(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.boottime.Boottime", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"utc") >= 1
class TestLinuxCapabilities:
def test_linux_generic_capabilities(self, image, volatility, python):
rc, out, err = test_volatility.runvol_plugin(
"linux.capabilities.Capabilities",
image,
volatility,
python,
globalargs=("-vvv",),
)
if rc != 0 and err.count(b"Unsupported kernel capabilities implementation") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxCheckCreds:
def test_linux_generic_check_creds(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.check_creds.Check_creds", image, volatility, python
)
# linux-sample-1.bin has no processes sharing credentials.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxElfs:
def test_linux_generic_elfs(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.elfs.Elfs", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxEnvars:
def test_linux_generic_envars(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.envars.Envars", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxKthreads:
def test_linux_generic_kthreads(self, image, volatility, python):
rc, out, err = test_volatility.runvol_plugin(
"linux.kthreads.Kthreads",
image,
volatility,
python,
globalargs=("-vvv",),
)
if rc != 0 and err.count(b"Unsupported kthread implementation") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxMalfind:
def test_linux_generic_malfind(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.malfind.Malfind", image, volatility, python
)
# linux-sample-1.bin has no process memory ranges with potential injected code.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxMountinfo:
def test_linux_generic_mountinfo(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.mountinfo.MountInfo", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxPsaux:
def test_linux_generic_psaux(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.psaux.PsAux", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 50
class TestLinuxPtrace:
def test_linux_generic_ptrace(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.ptrace.Ptrace", image, volatility, python
)
# linux-sample-1.bin has no processes being ptraced.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxVmaregexscan:
def test_linux_generic_vmaregexscan(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.vmaregexscan.VmaRegExScan",
image,
volatility,
python,
pluginargs=("--pid", "1", "--pattern", "\\x7fELF"),
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxVmayarascanYaraRule:
def test_linux_specific_vmayarascan_yara_rule(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
yara_rule_01 = r"""
rule fullvmayarascan
{
strings:
$s1 = "_nss_files_parse_grent"
$s2 = "/lib64/ld-linux-x86-64.so.2"
$s3 = "(bufferend - (char *) 0) % sizeof (char *) == 0"
condition:
all of them
}
"""
# FIXME: When the minimum Python version includes 3.12, replace the following with:
# with tempfile.NamedTemporaryFile(delete_on_close=False) as fd: ...
fd, filename = tempfile.mkstemp(suffix=".yar")
try:
with os.fdopen(fd, "w") as f:
f.write(yara_rule_01)
rc, out, _err = test_volatility.runvol_plugin(
"linux.vmayarascan.VmaYaraScan",
image,
volatility,
python,
pluginargs=("--pid", "8600", "--yara-file", filename),
)
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(filename)
assert rc == 0
assert out.count(b"\n") > 4
class TestLinuxVmayarascanYaraString:
def test_linux_generic_vmayarascan_yara_string(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.vmayarascan.VmaYaraScan",
image,
volatility,
python,
pluginargs=("--pid", "1", "--yara-string", "ELF"),
)
assert rc == 0
assert out.count(b"\n") > 10
class TestLinuxPageCacheFiles:
def test_linux_specific_page_cache_files(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"linux.pagecache.Files",
image,
volatility,
python,
pluginargs=("--find", "/etc/passwd"),
)
assert rc == 0
assert out.count(b"\n") > 4
# inode_num inode_addr ... file_path
assert re.search(
rb"146829\s0x88001ab5c270.*?/etc/passwd",
out,
)
class TestLinuxPageCacheInodepages:
def test_linux_specific_page_cache_inodepages(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
inode_address = hex(0x88001AB5C270)
inode_dump_filename = f"inode_{inode_address}.dmp"
rc, out, _err = test_volatility.runvol_plugin(
"linux.pagecache.InodePages",
image,
volatility,
python,
pluginargs=("--inode", inode_address),
)
assert rc == 0
assert out.count(b"\n") > 4
# PageVAddr PagePAddr MappingAddr .. DumpSafe
assert re.search(
rb"0xea000054c5f8\s0x18389000\s0x88001ab5c3b0.*?True",
out,
)
try:
rc, out, _err = test_volatility.runvol_plugin(
"linux.pagecache.InodePages",
image,
volatility,
python,
pluginargs=("--inode", inode_address, "--dump"),
)
assert rc == 0
assert out.count(b"\n") >= 4
assert os.path.exists(inode_dump_filename)
with open(inode_dump_filename, "rb") as fp:
inode_contents = fp.read()
assert inode_contents.count(b"\n") > 30
assert inode_contents.count(b"root:x:0:0:root:/root:/bin/bash") > 0
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(inode_dump_filename)
class TestLinuxCheckAfinfo:
def test_linux_generic_check_afinfo(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.check_afinfo.Check_afinfo", image, volatility, python
)
# linux-sample-1.bin has no suspicious results.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxCheckModules:
def test_linux_generic_check_modules(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.check_modules.Check_modules", image, volatility, python
)
# linux-sample-1.bin has no suspicious results.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxEbpf:
def test_linux_generic_ebpf_progs(self, image, volatility, python):
rc, out, err = test_volatility.runvol_plugin(
"linux.ebpf.EBPF",
image,
volatility,
python,
globalargs=("-vvv",),
)
if rc != 0 and err.count(b"Unsupported kernel") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") > 4
class TestLinuxIomem:
def test_linux_generic_iomem(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.iomem.IOMem", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 100
class TestLinuxKeyboardNotifiers:
def test_linux_generic_keyboard_notifiers(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.keyboard_notifiers.Keyboard_notifiers", image, volatility, python
)
# linux-sample-1.bin has no suspicious results for this plugin.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxKmesg:
def test_linux_generic_kmesg(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.kmsg.Kmsg", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 100
class TestLinuxNetfilter:
def test_linux_generic_netfilter(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.netfilter.Netfilter", image, volatility, python
)
# linux-sample-1.bin has no suspicious results for this plugin.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxPsscan:
def test_linux_generic__psscan(self, image, volatility, python):
rc, out, _err = test_volatility.runvol_plugin(
"linux.psscan.PsScan", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 100
class TestLinuxHiddenModules:
def test_linux_specific_hidden_modules(self, volatility, python):
# TODO: this check should be specific, against a distinct infected sample
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"linux.hidden_modules.Hidden_modules", image, volatility, python
)
# linux-sample-1.bin has no hidden modules.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
class TestLinuxIpAddr:
def test_linux_specific_ip_addr(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, err = test_volatility.runvol_plugin(
"linux.ip.Addr", image, volatility, python
)
assert re.search(
rb"2\s+eth0\s+00:0c:29:8f:ed:ca\s+False\s+192.168.201.161\s+24\s+global\s+UP",
out,
)
assert re.search(
rb"2\s+eth0\s+00:0c:29:8f:ed:ca\s+False\s+fe80::20c:29ff:fe8f:edca\s+64\s+link\s+UP",
out,
)
assert out.count(b"\n") >= 8
assert rc == 0
class TestLinuxIpLink:
def test_linux_specific_ip_link(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, err = test_volatility.runvol_plugin(
"linux.ip.Link", image, volatility, python
)
assert re.search(
rb"-\s+lo\s+00:00:00:00:00:00\s+UNKNOWN\s+16436\s+noqueue\s+0\s+LOOPBACK,LOWER_UP,UP",
out,
)
assert re.search(
rb"-\s+eth0\s+00:0c:29:8f:ed:ca\s+UP\s+1500\s+pfifo_fast\s+1000\s+BROADCAST,LOWER_UP,MULTICAST,UP",
out,
)
assert out.count(b"\n") >= 6
assert rc == 0
class TestLinuxKallsyms:
def test_linux_specific_kallsyms(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"linux.kallsyms.Kallsyms",
image,
volatility,
python,
pluginargs=("--modules",),
)
# linux-sample-1.bin has no hidden modules.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") > 1000
# Addr Type Size Exported SubSystem ModuleName SymbolName Description
# 0xffffa009eba9 t 28 False module usbcore usb_mon_register Symbol is in the text (code) section
assert re.search(
rb"0xffffa009eba9\s+t\s+28\s+False\s+module\s+usbcore\s+usb_mon_register\s+Symbol is in the text \(code\) section",
out,
)
class TestLinuxPscallstack:
def test_linux_specific_pscallstack(self, volatility, python):
image = LinuxSamples.LINUX_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"linux.pscallstack.PsCallStack",
image,
volatility,
python,
pluginargs=("--pid", "1"),
)
assert rc == 0
assert out.count(b"\n") > 30
# TID Comm Position Address Value Name Type Module
# 1 init 39 0x88001f999a40 0xffff81109039 do_select T kernel
assert re.search(
rb"1\s+init\s+39\s+0x88001f999a40.*?0xffff81109039\s+do_select\s+T\s+kernel",
out,
)
+326
View File
@@ -0,0 +1,326 @@
import json
import hashlib
import shutil
import contextlib
import tempfile
import os
from test import test_volatility, WindowsSamples
class TestWindowsVolshell:
def test_windows_volshell(self, image, volatility, python):
out = test_volatility.basic_volshell_test(
image, volatility, python, globalargs=("-w",)
)
assert out.count(b"<EPROCESS") > 40
class TestWindowsPslist:
def test_windows_generic_pslist(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.pslist.PsList",
image,
volatility,
python,
# Notice that this is needed to hit lru_cache when "specific" will run
globalargs=("-r", "json"),
)
assert rc == 0
out = out.lower()
assert out.find(b"system") != -1
assert out.find(b"csrss.exe") != -1
assert out.find(b"svchost.exe") != -1
assert out.count(b"\n") > 10
def test_windows_specific_pslist(self, volatility, python):
image = WindowsSamples.WINDOWSXP_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"windows.pslist.PsList",
image,
volatility,
python,
globalargs=("-r", "json"),
)
assert rc == 0
expected_row = {
"CreateTime": None,
"ExitTime": None,
"File output": "Disabled",
"Handles": 1140,
"ImageFileName": "System",
"Offset(V)": 2185004992,
"PID": 4,
"PPID": 0,
"SessionId": None,
"Threads": 61,
"Wow64": False,
"__children": [],
}
assert test_volatility.match_output_row(json.loads(out), expected_row)
class TestWindowsPsscan:
def test_windows_generic_psscan(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.psscan.PsScan", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.find(b"system") != -1
assert out.find(b"csrss.exe") != -1
assert out.find(b"svchost.exe") != -1
assert out.count(b"\n") > 10
class TestWindowsDlllist:
def test_windows_generic_dlllist(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.dlllist.DllList", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"\n") > 10
class TestWindowsModules:
def test_windows_generic_modules(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.modules.Modules", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"\n") > 10
class TestWindowsHivelist:
def test_windows_generic_hivelist(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.registry.hivelist.HiveList", image, volatility, python
)
assert rc == 0
out = out.lower()
not_xp = out.find(b"\\systemroot\\system32\\config\\software")
if not_xp == -1:
assert (
out.find(
b"\\device\\harddiskvolume1\\windows\\system32\\config\\software"
)
!= -1
)
assert out.count(b"\n") > 10
class TestWindowsDumpfiles:
def test_windows_specific_dumpfiles(self, volatility, python):
image = WindowsSamples.WINDOWSXP_GENERIC.value.path
with open("./test/known_files.json") as json_file:
known_files = json.load(json_file)
failed_chksms = 0
file_name = os.path.basename(image)
try:
for addr in known_files["windows_dumpfiles"][file_name]:
path = tempfile.mkdtemp()
rc, _out, _err = test_volatility.runvol_plugin(
"windows.dumpfiles.DumpFiles",
image,
volatility,
python,
globalargs=("-o", path),
pluginargs=("--virtaddr", addr),
)
for file in os.listdir(path):
with open(os.path.join(path, file), "rb") as fp:
if (
hashlib.md5(fp.read()).hexdigest()
not in known_files["windows_dumpfiles"][file_name][addr]
):
failed_chksms += 1
shutil.rmtree(path)
json_file.close()
assert failed_chksms == 0
assert rc == 0
except Exception as e:
json_file.close()
print("Key Error raised on " + str(e))
assert False
class TestWindowsHandles:
def test_windows_generic_handles(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.handles.Handles",
image,
volatility,
python,
pluginargs=("--pid", "4"),
)
assert rc == 0
assert out.find(b"System Pid 4") != -1
assert (
out.find(
b"MACHINE\\SYSTEM\\CONTROLSET001\\CONTROL\\SESSION MANAGER\\MEMORY MANAGEMENT\\PREFETCHPARAMETERS"
)
!= -1
)
assert out.find(b"MACHINE\\SYSTEM\\SETUP") != -1
assert out.count(b"\n") > 500
class TestWindowsSvcscan:
def test_windows_generic_svcscan(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.svcscan.SvcScan", image, volatility, python
)
assert rc == 0
assert out.find(b"Microsoft ACPI Driver") != -1
assert out.count(b"\n") > 250
class TestWindowsThrdscan:
def test_windows_generic_thrdscan(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.thrdscan.ThrdScan", image, volatility, python
)
assert rc == 0
assert out.find(b"\t4\t8") != -1
assert out.find(b"\t4\t12") != -1
assert out.find(b"\t4\t16") != -1
class TestWindowsPrivileges:
def test_windows_generic_privileges(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.privileges.Privs",
image,
volatility,
python,
pluginargs=("--pid", "4"),
)
assert rc == 0
assert out.find(b"SeCreateTokenPrivilege") != -1
assert out.find(b"SeCreateGlobalPrivilege") != -1
assert out.find(b"SeAssignPrimaryTokenPrivilege") != -1
assert out.count(b"\n") > 20
class TestWindowsGetsids:
def test_windows_generic_getsids(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.getsids.GetSIDs",
image,
volatility,
python,
pluginargs=("--pid", "4"),
)
assert rc == 0
assert out.find(b"Local System") != -1
assert out.find(b"Administrators") != -1
assert out.find(b"Everyone") != -1
assert out.find(b"Authenticated Users") != -1
class TestWindowsEnvars:
def test_windows_generic_envars(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.envars.Envars", image, volatility, python
)
assert rc == 0
assert out.find(b"PATH") != -1
assert out.find(b"PROCESSOR_ARCHITECTURE") != -1
assert out.find(b"USERNAME") != -1
assert out.find(b"SystemRoot") != -1
assert out.find(b"CommonProgramFiles") != -1
assert out.count(b"\n") > 500
class TestWindowsCallbacks:
def test_windows_generic_callbacks(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.callbacks.Callbacks", image, volatility, python
)
assert rc == 0
assert out.find(b"PspCreateProcessNotifyRoutine") != -1
assert out.find(b"KeBugCheckCallbackListHead") != -1
assert out.find(b"KeBugCheckReasonCallbackListHead") != -1
assert out.count(b"KeBugCheckReasonCallbackListHead ") > 5
class TestWindowsVadwalk:
def test_windows_generic_vadwalk(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.vadwalk.VadWalk", image, volatility, python
)
assert rc == 0
assert out.find(b"Vad") != -1
assert out.find(b"VadS") != -1
assert out.find(b"Vadl") != -1
assert out.find(b"VadF") != -1
assert out.find(b"0x0") != -1
class TestWindowsDevicetree:
def test_windows_generic_devicetree(self, volatility, python, image):
rc, out, _err = test_volatility.runvol_plugin(
"windows.devicetree.DeviceTree", image, volatility, python
)
assert rc == 0
assert out.find(b"DEV") != -1
assert out.find(b"DRV") != -1
assert out.find(b"ATT") != -1
assert out.find(b"FILE_DEVICE_CONTROLLER") != -1
assert out.find(b"FILE_DEVICE_DISK") != -1
assert out.find(b"FILE_DEVICE_DISK_FILE_SYSTEM") != -1
class TestWindowsVadyarascan:
def test_windows_specific_vadyarascan_yara_rule(self, volatility, python):
image = WindowsSamples.WINDOWSXP_GENERIC.value.path
yara_rule_01 = r"""
rule fullvadyarascan
{
strings:
$s1 = "!This program cannot be run in DOS mode."
$s2 = "Qw))Pw"
$s3 = "W_wD)Pw"
$s4 = "1Xw+2Xw"
$s5 = "xd`wh``w"
$s6 = "0g`w0g`w8g`w8g`w@g`w@g`wHg`wHg`wPg`wPg`wXg`wXg`w`g`w`g`whg`whg`wpg`wpg`wxg`wxg`w"
condition:
all of them
}
"""
fd, filename = tempfile.mkstemp(suffix=".yar")
try:
with os.fdopen(fd, "w") as f:
f.write(yara_rule_01)
rc, out, _err = test_volatility.runvol_plugin(
"windows.vadyarascan.VadYaraScan",
image,
volatility,
python,
pluginargs=("--pid", "4012", "--yara-file", filename),
)
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(filename)
assert rc == 0
assert out.count(b"\n") > 4
def test_windows_specific_vadyarascan_yara_string(self, volatility, python):
image = WindowsSamples.WINDOWSXP_GENERIC.value.path
rc, out, _err = test_volatility.runvol_plugin(
"windows.vadyarascan.VadYaraScan",
image,
volatility,
python,
pluginargs=("--pid", "4012", "--yara-string", "MZ"),
)
assert rc == 0
assert out.count(b"\n") > 10
+1 -799
View File
@@ -133,806 +133,8 @@ def basic_volshell_test(image, volatility, python, globalargs):
return out
# WINDOWS
def test_windows_volshell(image, volatility, python):
out = basic_volshell_test(image, volatility, python, globalargs=["-w"])
assert out.count(b"<EPROCESS") > 40
def test_windows_pslist(image, volatility, python):
rc, out, _err = runvol_plugin("windows.pslist.PsList", image, volatility, python)
out = out.lower()
assert out.find(b"system") != -1
assert out.find(b"csrss.exe") != -1
assert out.find(b"svchost.exe") != -1
assert out.count(b"\n") > 10
assert rc == 0
rc, out, _err = runvol_plugin(
"windows.pslist.PsList", image, volatility, python, pluginargs=["--pid", "4"]
)
out = out.lower()
assert out.find(b"system") != -1
assert out.count(b"\n") < 10
assert rc == 0
def test_windows_psscan(image, volatility, python):
rc, out, _err = runvol_plugin("windows.psscan.PsScan", image, volatility, python)
out = out.lower()
assert out.find(b"system") != -1
assert out.find(b"csrss.exe") != -1
assert out.find(b"svchost.exe") != -1
assert out.count(b"\n") > 10
assert rc == 0
def test_windows_dlllist(image, volatility, python):
rc, out, _err = runvol_plugin("windows.dlllist.DllList", image, volatility, python)
out = out.lower()
assert out.count(b"\n") > 10
assert rc == 0
def test_windows_modules(image, volatility, python):
rc, out, _err = runvol_plugin("windows.modules.Modules", image, volatility, python)
out = out.lower()
assert out.count(b"\n") > 10
assert rc == 0
def test_windows_hivelist(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.registry.hivelist.HiveList", image, volatility, python
)
out = out.lower()
not_xp = out.find(b"\\systemroot\\system32\\config\\software")
if not_xp == -1:
assert (
out.find(b"\\device\\harddiskvolume1\\windows\\system32\\config\\software")
!= -1
)
assert out.count(b"\n") > 10
assert rc == 0
def test_windows_dumpfiles(image, volatility, python):
with open("./test/known_files.json") as json_file:
known_files = json.load(json_file)
failed_chksms = 0
file_name = os.path.basename(image)
try:
for addr in known_files["windows_dumpfiles"][file_name]:
path = tempfile.mkdtemp()
rc, _out, _err = runvol_plugin(
"windows.dumpfiles.DumpFiles",
image,
volatility,
python,
globalargs=["-o", path],
pluginargs=["--virtaddr", addr],
)
for file in os.listdir(path):
with open(os.path.join(path, file), "rb") as fp:
if (
hashlib.md5(fp.read()).hexdigest()
not in known_files["windows_dumpfiles"][file_name][addr]
):
failed_chksms += 1
shutil.rmtree(path)
json_file.close()
assert failed_chksms == 0
assert rc == 0
except Exception as e:
json_file.close()
print("Key Error raised on " + str(e))
assert False
def test_windows_handles(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.handles.Handles", image, volatility, python, pluginargs=["--pid", "4"]
)
assert out.find(b"System Pid 4") != -1
assert (
out.find(
b"MACHINE\\SYSTEM\\CONTROLSET001\\CONTROL\\SESSION MANAGER\\MEMORY MANAGEMENT\\PREFETCHPARAMETERS"
)
!= -1
)
assert out.find(b"MACHINE\\SYSTEM\\SETUP") != -1
assert out.count(b"\n") > 500
assert rc == 0
def test_windows_svcscan(image, volatility, python):
rc, out, _err = runvol_plugin("windows.svcscan.SvcScan", image, volatility, python)
assert out.find(b"Microsoft ACPI Driver") != -1
assert out.count(b"\n") > 250
assert rc == 0
def test_windows_thrdscan(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.thrdscan.ThrdScan", image, volatility, python
)
# find pid 4 (of system process) which starts with lowest tids
assert out.find(b"\t4\t8") != -1
assert out.find(b"\t4\t12") != -1
assert out.find(b"\t4\t16") != -1
# assert out.find(b"this raieses AssertionError") != -1
assert rc == 0
def test_windows_privileges(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.privileges.Privs", image, volatility, python, pluginargs=["--pid", "4"]
)
assert out.find(b"SeCreateTokenPrivilege") != -1
assert out.find(b"SeCreateGlobalPrivilege") != -1
assert out.find(b"SeAssignPrimaryTokenPrivilege") != -1
assert out.count(b"\n") > 20
assert rc == 0
def test_windows_getsids(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.getsids.GetSIDs", image, volatility, python, pluginargs=["--pid", "4"]
)
assert out.find(b"Local System") != -1
assert out.find(b"Administrators") != -1
assert out.find(b"Everyone") != -1
assert out.find(b"Authenticated Users") != -1
assert rc == 0
def test_windows_envars(image, volatility, python):
rc, out, _err = runvol_plugin("windows.envars.Envars", image, volatility, python)
assert out.find(b"PATH") != -1
assert out.find(b"PROCESSOR_ARCHITECTURE") != -1
assert out.find(b"USERNAME") != -1
assert out.find(b"SystemRoot") != -1
assert out.find(b"CommonProgramFiles") != -1
assert out.count(b"\n") > 500
assert rc == 0
def test_windows_callbacks(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.callbacks.Callbacks", image, volatility, python
)
assert out.find(b"PspCreateProcessNotifyRoutine") != -1
assert out.find(b"KeBugCheckCallbackListHead") != -1
assert out.find(b"KeBugCheckReasonCallbackListHead") != -1
assert out.count(b"KeBugCheckReasonCallbackListHead ") > 5
assert rc == 0
def test_windows_vadwalk(image, volatility, python):
rc, out, _err = runvol_plugin("windows.vadwalk.VadWalk", image, volatility, python)
assert out.find(b"Vad") != -1
assert out.find(b"VadS") != -1
assert out.find(b"Vadl") != -1
assert out.find(b"VadF") != -1
assert out.find(b"0x0") != -1
assert rc == 0
def test_windows_devicetree(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.devicetree.DeviceTree", image, volatility, python
)
assert out.find(b"DEV") != -1
assert out.find(b"DRV") != -1
assert out.find(b"ATT") != -1
assert out.find(b"FILE_DEVICE_CONTROLLER") != -1
assert out.find(b"FILE_DEVICE_DISK") != -1
assert out.find(b"FILE_DEVICE_DISK_FILE_SYSTEM") != -1
assert rc == 0
def test_windows_vadyarascan_yara_rule(image, volatility, python):
yara_rule_01 = r"""
rule fullvadyarascan
{
strings:
$s1 = "!This program cannot be run in DOS mode."
$s2 = "Qw))Pw"
$s3 = "W_wD)Pw"
$s4 = "1Xw+2Xw"
$s5 = "xd`wh``w"
$s6 = "0g`w0g`w8g`w8g`w@g`w@g`wHg`wHg`wPg`wPg`wXg`wXg`w`g`w`g`whg`whg`wpg`wpg`wxg`wxg`w"
condition:
all of them
}
"""
# FIXME: When the minimum Python version includes 3.12, replace the following with:
# with tempfile.NamedTemporaryFile(delete_on_close=False) as fd: ...
fd, filename = tempfile.mkstemp(suffix=".yar")
try:
with os.fdopen(fd, "w") as f:
f.write(yara_rule_01)
rc, out, _err = runvol_plugin(
"windows.vadyarascan.VadYaraScan",
image,
volatility,
python,
pluginargs=["--pid", "4012", "--yara-file", filename],
)
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(filename)
out = out.lower()
assert out.count(b"\n") > 4
assert rc == 0
def test_windows_vadyarascan_yara_string(image, volatility, python):
rc, out, _err = runvol_plugin(
"windows.vadyarascan.VadYaraScan",
image,
volatility,
python,
pluginargs=["--pid", "4012", "--yara-string", "MZ"],
)
out = out.lower()
assert out.count(b"\n") > 10
assert rc == 0
# LINUX
def test_linux_volshell(image, volatility, python):
out = basic_volshell_test(image, volatility, python, globalargs=["-l"])
assert out.count(b"<task_struct") > 100
def test_linux_pslist(image, volatility, python):
rc, out, _err = runvol_plugin("linux.pslist.PsList", image, volatility, python)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.find(b"watchdog") != -1
assert out.count(b"\n") > 10
def test_linux_check_idt(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.check_idt.Check_idt", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.count(b"__kernel__") >= 10
assert out.count(b"\n") > 10
def test_linux_check_syscall(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.check_syscall.Check_syscall", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.find(b"sys_close") != -1
assert out.find(b"sys_open") != -1
assert out.count(b"\n") > 100
def test_linux_lsmod(image, volatility, python):
rc, out, _err = runvol_plugin("linux.lsmod.Lsmod", image, volatility, python)
assert rc == 0
out = out.lower()
assert out.count(b"\n") > 10
def test_linux_lsof(image, volatility, python):
rc, out, _err = runvol_plugin("linux.lsof.Lsof", image, volatility, python)
assert rc == 0
out = out.lower()
assert out.count(b"socket:") >= 10
assert out.count(b"\n") > 35
def test_linux_proc_maps(image, volatility, python):
rc, out, _err = runvol_plugin("linux.proc.Maps", image, volatility, python)
assert rc == 0
out = out.lower()
assert out.count(b"anonymous mapping") >= 10
assert out.count(b"\n") > 100
def test_linux_tty_check(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.tty_check.tty_check", image, volatility, python
)
assert rc == 0
out = out.lower()
assert out.find(b"__kernel__") != -1
assert out.count(b"\n") >= 5
def test_linux_sockstat(image, volatility, python):
rc, out, _err = runvol_plugin("linux.sockstat.Sockstat", image, volatility, python)
assert rc == 0
assert out.count(b"AF_UNIX") >= 354
assert out.count(b"AF_BLUETOOTH") >= 5
assert out.count(b"AF_INET") >= 32
assert out.count(b"AF_INET6") >= 20
assert out.count(b"AF_PACKET") >= 1
assert out.count(b"AF_NETLINK") >= 43
def test_linux_library_list(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.library_list.LibraryList",
image,
volatility,
python,
pluginargs=["--pids", "2363"],
)
assert rc == 0
assert re.search(
rb"NetworkManager\s2363\s0x7f52cdda0000\s/lib/x86_64-linux-gnu/libnss_files.so.2",
out,
)
assert out.count(b"\n") > 10
def test_linux_pstree(image, volatility, python):
rc, out, _err = runvol_plugin("linux.pstree.PsTree", image, volatility, python)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.count(b"\n") > 10
def test_linux_pidhashtable(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.pidhashtable.PIDHashTable", image, volatility, python
)
assert rc == 0
out = out.lower()
assert (out.find(b"init") != -1) or (out.find(b"systemd") != -1)
assert out.count(b"\n") > 10
def test_linux_bash(image, volatility, python):
rc, out, _err = runvol_plugin("linux.bash.Bash", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_boottime(image, volatility, python):
rc, out, _err = runvol_plugin("linux.boottime.Boottime", image, volatility, python)
assert rc == 0
out = out.lower()
assert out.count(b"utc") >= 1
def test_linux_capabilities(image, volatility, python):
rc, out, err = runvol_plugin(
"linux.capabilities.Capabilities",
image,
volatility,
python,
globalargs=["-vvv"],
)
if rc != 0 and err.count(b"Unsupported kernel capabilities implementation") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_check_creds(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.check_creds.Check_creds", image, volatility, python
)
# linux-sample-1.bin has no processes sharing credentials.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_elfs(image, volatility, python):
rc, out, _err = runvol_plugin("linux.elfs.Elfs", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_envars(image, volatility, python):
rc, out, _err = runvol_plugin("linux.envars.Envars", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_kthreads(image, volatility, python):
rc, out, err = runvol_plugin(
"linux.kthreads.Kthreads",
image,
volatility,
python,
globalargs=["-vvv"],
)
if rc != 0 and err.count(b"Unsupported kthread implementation") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_malfind(image, volatility, python):
rc, out, _err = runvol_plugin("linux.malfind.Malfind", image, volatility, python)
# linux-sample-1.bin has no process memory ranges with potential injected code.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_mountinfo(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.mountinfo.MountInfo", image, volatility, python
)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_psaux(image, volatility, python):
rc, out, _err = runvol_plugin("linux.psaux.PsAux", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 50
def test_linux_ptrace(image, volatility, python):
rc, out, _err = runvol_plugin("linux.ptrace.Ptrace", image, volatility, python)
# linux-sample-1.bin has no processes being ptraced.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_vmaregexscan(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.vmaregexscan.VmaRegExScan",
image,
volatility,
python,
pluginargs=["--pid", "1", "--pattern", "\\x7fELF"],
)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_vmayarascan_yara_rule(image, volatility, python):
yara_rule_01 = r"""
rule fullvmayarascan
{
strings:
$s1 = "_nss_files_parse_grent"
$s2 = "/lib64/ld-linux-x86-64.so.2"
$s3 = "(bufferend - (char *) 0) % sizeof (char *) == 0"
condition:
all of them
}
"""
# FIXME: When the minimum Python version includes 3.12, replace the following with:
# with tempfile.NamedTemporaryFile(delete_on_close=False) as fd: ...
fd, filename = tempfile.mkstemp(suffix=".yar")
try:
with os.fdopen(fd, "w") as f:
f.write(yara_rule_01)
rc, out, _err = runvol_plugin(
"linux.vmayarascan.VmaYaraScan",
image,
volatility,
python,
pluginargs=["--pid", "8600", "--yara-file", filename],
)
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(filename)
assert rc == 0
assert out.count(b"\n") > 4
def test_linux_vmayarascan_yara_string(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.vmayarascan.VmaYaraScan",
image,
volatility,
python,
pluginargs=["--pid", "1", "--yara-string", "ELF"],
)
assert rc == 0
assert out.count(b"\n") > 10
def test_linux_page_cache_files(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.pagecache.Files",
image,
volatility,
python,
pluginargs=["--find", "/etc/passwd"],
)
assert rc == 0
assert out.count(b"\n") > 4
# inode_num inode_addr ... file_path
assert re.search(
rb"146829\s0x88001ab5c270.*?/etc/passwd",
out,
)
def test_linux_page_cache_inodepages(image, volatility, python):
inode_address = hex(0x88001AB5C270)
inode_dump_filename = f"inode_{inode_address}.dmp"
rc, out, _err = runvol_plugin(
"linux.pagecache.InodePages",
image,
volatility,
python,
pluginargs=["--inode", inode_address],
)
assert rc == 0
assert out.count(b"\n") > 4
# PageVAddr PagePAddr MappingAddr .. DumpSafe
assert re.search(
rb"0xea000054c5f8\s0x18389000\s0x88001ab5c3b0.*?True",
out,
)
try:
rc, out, _err = runvol_plugin(
"linux.pagecache.InodePages",
image,
volatility,
python,
pluginargs=["--inode", inode_address, "--dump"],
)
assert rc == 0
assert out.count(b"\n") >= 4
assert os.path.exists(inode_dump_filename)
with open(inode_dump_filename, "rb") as fp:
inode_contents = fp.read()
assert inode_contents.count(b"\n") > 30
assert inode_contents.count(b"root:x:0:0:root:/root:/bin/bash") > 0
finally:
with contextlib.suppress(FileNotFoundError):
os.remove(inode_dump_filename)
def test_linux_check_afinfo(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.check_afinfo.Check_afinfo", image, volatility, python
)
# linux-sample-1.bin has no suspicious results.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_check_modules(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.check_modules.Check_modules", image, volatility, python
)
# linux-sample-1.bin has no suspicious results.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_ebpf_progs(image, volatility, python):
rc, out, err = runvol_plugin(
"linux.ebpf.EBPF",
image,
volatility,
python,
globalargs=["-vvv"],
)
if rc != 0 and err.count(b"Unsupported kernel") > 0:
# The linux-sample-1.bin kernel implementation isn't supported.
# However, we can still check that the plugin requirements are met.
return None
assert rc == 0
assert out.count(b"\n") > 4
def test_linux_iomem(image, volatility, python):
rc, out, _err = runvol_plugin("linux.iomem.IOMem", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 100
def test_linux_keyboard_notifiers(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.keyboard_notifiers.Keyboard_notifiers", image, volatility, python
)
# linux-sample-1.bin has no suspicious results for this plugin.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_kmesg(image, volatility, python):
rc, out, _err = runvol_plugin("linux.kmsg.Kmsg", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 100
def test_linux_netfilter(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.netfilter.Netfilter", image, volatility, python
)
# linux-sample-1.bin has no suspicious results for this plugin.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_psscan(image, volatility, python):
rc, out, _err = runvol_plugin("linux.psscan.PsScan", image, volatility, python)
assert rc == 0
assert out.count(b"\n") > 100
def test_linux_hidden_modules(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.hidden_modules.Hidden_modules", image, volatility, python
)
# linux-sample-1.bin has no hidden modules.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") >= 4
def test_linux_ip_addr(image, volatility, python):
rc, out, err = runvol_plugin("linux.ip.Addr", image, volatility, python)
assert re.search(
rb"2\s+eth0\s+00:0c:29:8f:ed:ca\s+False\s+192.168.201.161\s+24\s+global\s+UP",
out,
)
assert re.search(
rb"2\s+eth0\s+00:0c:29:8f:ed:ca\s+False\s+fe80::20c:29ff:fe8f:edca\s+64\s+link\s+UP",
out,
)
assert out.count(b"\n") >= 8
assert rc == 0
def test_linux_ip_link(image, volatility, python):
rc, out, err = runvol_plugin("linux.ip.Link", image, volatility, python)
assert re.search(
rb"-\s+lo\s+00:00:00:00:00:00\s+UNKNOWN\s+16436\s+noqueue\s+0\s+LOOPBACK,LOWER_UP,UP",
out,
)
assert re.search(
rb"-\s+eth0\s+00:0c:29:8f:ed:ca\s+UP\s+1500\s+pfifo_fast\s+1000\s+BROADCAST,LOWER_UP,MULTICAST,UP",
out,
)
assert out.count(b"\n") >= 6
assert rc == 0
def test_linux_kallsyms(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.kallsyms.Kallsyms",
image,
volatility,
python,
pluginargs=["--modules"],
)
# linux-sample-1.bin has no hidden modules.
# This validates that plugin requirements are met and exceptions are not raised.
assert rc == 0
assert out.count(b"\n") > 1000
# Addr Type Size Exported SubSystem ModuleName SymbolName Description
# 0xffffa009eba9 t 28 False module usbcore usb_mon_register Symbol is in the text (code) section
assert re.search(
rb"0xffffa009eba9\s+t\s+28\s+False\s+module\s+usbcore\s+usb_mon_register\s+Symbol is in the text \(code\) section",
out,
)
def test_linux_pscallstack(image, volatility, python):
rc, out, _err = runvol_plugin(
"linux.pscallstack.PsCallStack",
image,
volatility,
python,
pluginargs=["--pid", "1"],
)
assert rc == 0
assert out.count(b"\n") > 30
# TID Comm Position Address Value Name Type Module
# 1 init 39 0x88001f999a40 0xffff81109039 do_select T kernel
assert re.search(
rb"1\s+init\s+39\s+0x88001f999a40.*?0xffff81109039\s+do_select\s+T\s+kernel",
out,
)
# MAC
# TODO: Migrate and integrate in testing (once analysis is fixed ?)
def test_mac_volshell(image, volatility, python):