mirror of
https://github.com/volatilityfoundation/volatility3.git
synced 2026-09-08 10:47:38 +02:00
First stab at refactoring the add_process_layer code out of the Windows _EPROCESS structure.
This commit is contained in:
@@ -0,0 +1,40 @@
|
||||
import random
|
||||
import string
|
||||
|
||||
from volatility.framework import objects, interfaces
|
||||
|
||||
|
||||
class GenericIntelProcess(objects.Struct):
|
||||
def _add_process_layer(self, context, dtb, config_prefix = None, preferred_name = None):
|
||||
"""Constructs a new layer based on the process's DirectoryTableBase"""
|
||||
|
||||
if config_prefix is None:
|
||||
# TODO: Ensure collisions can't happen by verifying the config_prefix is empty
|
||||
random_prefix = ''.join(
|
||||
random.SystemRandom().choice(string.ascii_uppercase + string.digits) for _ in range(8))
|
||||
config_prefix = interfaces.configuration.path_join("temporary", "_" + random_prefix)
|
||||
|
||||
# Figure out a suitable name we can use for the new layer
|
||||
if preferred_name is None:
|
||||
preferred_name = context.memory.free_layer_name(
|
||||
prefix = self.vol.layer_name + "_Process_")
|
||||
else:
|
||||
if preferred_name in context.memory:
|
||||
preferred_name = context.memory.free_layer_name(prefix = preferred_name)
|
||||
|
||||
# Copy the parent's config and then make suitable changes
|
||||
parent_layer = context.memory[self.vol.layer_name]
|
||||
parent_config = parent_layer.build_configuration()
|
||||
# It's an intel layer, because we hardwire the "memory_layer" config option
|
||||
# FIXME: this could be for other architectures if we don't hardwire this/these values
|
||||
parent_config['memory_layer'] = parent_layer.config['memory_layer']
|
||||
parent_config['page_map_offset'] = dtb
|
||||
|
||||
# Set the new configuration and construct the layer
|
||||
config_path = interfaces.configuration.path_join(config_prefix, preferred_name)
|
||||
context.config.splice(config_path, parent_config)
|
||||
new_layer = parent_layer.__class__(context, config_path = config_path, name = preferred_name)
|
||||
|
||||
# Add the constructed layer and return the name
|
||||
context.memory.add_layer(new_layer)
|
||||
return preferred_name
|
||||
@@ -1,25 +1,24 @@
|
||||
import collections.abc
|
||||
import random
|
||||
import string
|
||||
|
||||
from volatility.framework import interfaces
|
||||
from volatility.framework import objects
|
||||
from volatility.framework import exceptions
|
||||
|
||||
from volatility.framework import objects
|
||||
# Keep these in a basic module, to prevent import cycles when symbol providers require them
|
||||
from volatility.framework.symbols.generic import GenericIntelProcess
|
||||
|
||||
|
||||
class _ETHREAD(objects.Struct):
|
||||
def owning_process(self, kernel_layer = None):
|
||||
"""Return the EPROCESS that owns this thread"""
|
||||
return self.ThreadsProcess.dereference(kernel_layer)
|
||||
|
||||
|
||||
class _CMHIVE(objects.Struct):
|
||||
@property
|
||||
def name(self):
|
||||
"""Determine a name for the hive. Note that some attributes are
|
||||
unpredictably blank across different OS versions while others are populated,
|
||||
so we check all possibilities and take the first one that's not empty"""
|
||||
|
||||
|
||||
for attr in ["FileFullPath", "FileUserName", "HiveRootPath"]:
|
||||
try:
|
||||
return getattr(self, attr).String
|
||||
@@ -28,6 +27,7 @@ class _CMHIVE(objects.Struct):
|
||||
|
||||
return None
|
||||
|
||||
|
||||
class _UNICODE_STRING(objects.Struct):
|
||||
@property
|
||||
def String(self):
|
||||
@@ -38,44 +38,20 @@ class _UNICODE_STRING(objects.Struct):
|
||||
encoding = "utf16")
|
||||
|
||||
|
||||
class _EPROCESS(objects.Struct):
|
||||
class _EPROCESS(GenericIntelProcess):
|
||||
def add_process_layer(self, context, config_prefix = None, preferred_name = None):
|
||||
"""Constructs a new layer based on the process's DirectoryTableBase"""
|
||||
|
||||
if config_prefix is None:
|
||||
# TODO: Ensure collisions can't happen by verifying the config_prefix is empty
|
||||
random_prefix = ''.join(
|
||||
random.SystemRandom().choice(string.ascii_uppercase + string.digits) for _ in range(8))
|
||||
config_prefix = interfaces.configuration.path_join("temporary", "_" + random_prefix)
|
||||
|
||||
# Figure out a suitable name we can use for the new layer
|
||||
if preferred_name is None:
|
||||
preferred_name = context.memory.free_layer_name(
|
||||
prefix = self.vol.layer_name + "_PID" + str(self.UniqueProcessId) + "_")
|
||||
else:
|
||||
if preferred_name in context.memory:
|
||||
preferred_name = context.memory.free_layer_name(prefix = preferred_name)
|
||||
|
||||
# Copy the parent's config and then make suitable changes
|
||||
parent_layer = context.memory[self.vol.layer_name]
|
||||
parent_config = parent_layer.build_configuration()
|
||||
parent_config['memory_layer'] = parent_layer.config['memory_layer']
|
||||
# Presumably for 64-bit systems, the DTB is defined as an array, rather than an unsigned long long
|
||||
if isinstance(self.Pcb.DirectoryTableBase, objects.Array):
|
||||
parent_config['page_map_offset'] = self.Pcb.DirectoryTableBase.cast("unsigned long long")
|
||||
dtb = self.Pcb.DirectoryTableBase.cast("unsigned long long")
|
||||
else:
|
||||
parent_config['page_map_offset'] = self.Pcb.DirectoryTableBase
|
||||
parent_config['page_map_offset'] = parent_config['page_map_offset'] & (
|
||||
(1 << parent_layer.bits_per_register) - 1)
|
||||
|
||||
# Set the new configuration and construct the layer
|
||||
config_path = interfaces.configuration.path_join(config_prefix, preferred_name)
|
||||
context.config.splice(config_path, parent_config)
|
||||
new_layer = parent_layer.__class__(context, config_path = config_path, name = preferred_name)
|
||||
dtb = self.Pcb.DirectoryTableBase
|
||||
dtb = dtb & ((1 << parent_layer.bits_per_register) - 1)
|
||||
|
||||
# Add the constructed layer and return the name
|
||||
context.memory.add_layer(new_layer)
|
||||
return preferred_name
|
||||
return self._add_process_layer(context, dtb, config_prefix, preferred_name)
|
||||
|
||||
def load_order_modules(self):
|
||||
"""Generator for DLLs in the order that they were loaded"""
|
||||
|
||||
Reference in New Issue
Block a user