From 7308f4af0c4da19228b86c2b4aa8adb3773e952e Mon Sep 17 00:00:00 2001 From: Paul Kermann Date: Mon, 25 Apr 2022 11:21:05 +0300 Subject: [PATCH 1/5] minor improvments --- volatility3/framework/interfaces/objects.py | 19 ++++++++++--- volatility3/framework/interfaces/symbols.py | 14 ++++++++++ .../framework/symbols/windows/__init__.py | 27 +++++++++---------- .../symbols/windows/extensions/__init__.py | 8 ++---- 4 files changed, 44 insertions(+), 24 deletions(-) diff --git a/volatility3/framework/interfaces/objects.py b/volatility3/framework/interfaces/objects.py index e589abd15..c1fb29bb6 100644 --- a/volatility3/framework/interfaces/objects.py +++ b/volatility3/framework/interfaces/objects.py @@ -115,7 +115,15 @@ class ObjectInterface(metaclass = abc.ABCMeta): mask = context.layers[object_info.layer_name].address_mask normalized_offset = object_info.offset & mask - self._vol = collections.ChainMap({}, {'type_name': type_name, 'offset': normalized_offset}, object_info, kwargs) + vol_info_dict = {'type_name': type_name, 'offset': normalized_offset} + if constants.BANG in type_name: + table_name, struct_name = type_name.split(constants.BANG) + vol_info_dict["table_name"] = table_name + vol_info_dict["short_name"] = struct_name + else: + vol_info_dict["short_name"] = type_name + + self._vol = collections.ChainMap({}, vol_info_dict, object_info, kwargs) self._context = context def __getattr__(self, attr: str) -> Any: @@ -142,7 +150,7 @@ class ObjectInterface(metaclass = abc.ABCMeta): """ if constants.BANG not in self.vol.type_name: raise ValueError(f"Unable to determine table for symbol: {self.vol.type_name}") - table_name = self.vol.type_name[:self.vol.type_name.index(constants.BANG)] + table_name = self.vol.table_name if table_name not in self._context.symbol_space: raise KeyError(f"Symbol table not found in context's symbol_space for symbol: {self.vol.type_name}") return table_name @@ -156,7 +164,7 @@ class ObjectInterface(metaclass = abc.ABCMeta): """ # TODO: Carefully consider the implications of casting and how it should work if constants.BANG not in new_type_name: - symbol_table = self.vol['type_name'].split(constants.BANG)[0] + symbol_table = self.get_symbol_table_name() new_type_name = symbol_table + constants.BANG + new_type_name object_template = self._context.symbol_space.get_type(new_type_name) object_template = object_template.clone() @@ -169,6 +177,11 @@ class ObjectInterface(metaclass = abc.ABCMeta): size = object_template.size) return object_template(context = self._context, object_info = object_info) + def at_layer(self, new_layer_name) -> 'ObjectInterface': + """Returns the same object casted at a different layer. + """ + return self._context.object(self.vol.type_name, offset=self.vol.offset, layer_name=new_layer_name) + def has_member(self, member_name: str) -> bool: """Returns whether the object would contain a member called member_name. diff --git a/volatility3/framework/interfaces/symbols.py b/volatility3/framework/interfaces/symbols.py index b271de412..99690054d 100644 --- a/volatility3/framework/interfaces/symbols.py +++ b/volatility3/framework/interfaces/symbols.py @@ -167,6 +167,20 @@ class BaseSymbolTableInterface: """ raise NotImplementedError("Abstract method set_type_class not implemented yet.") + def try_set_type_class(self, name: str, clazz: Type[objects.ObjectInterface]) -> bool: + """Calls the set_type_class function but does not throw an exception. + Returns whether setting the type class was successfull. + Args: + name: The name of the type to override the class for + clazz: The actual class to override for the provided type name + """ + try: + self.set_type_class(name, clazz) + + return True + except ValueError: + return False + def get_type_class(self, name: str) -> Type[objects.ObjectInterface]: """Returns the class associated with a Symbol type.""" raise NotImplementedError("Abstract method get_type_class not implemented yet.") diff --git a/volatility3/framework/symbols/windows/__init__.py b/volatility3/framework/symbols/windows/__init__.py index f09dadedf..468d998c4 100755 --- a/volatility3/framework/symbols/windows/__init__.py +++ b/volatility3/framework/symbols/windows/__init__.py @@ -4,7 +4,7 @@ from volatility3.framework.symbols import intermed from volatility3.framework.symbols.windows import extensions -from volatility3.framework.symbols.windows.extensions import registry, pool +from volatility3.framework.symbols.windows.extensions import registry, pool, pe class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): @@ -38,6 +38,11 @@ class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): self.set_type_class('_SHARED_CACHE_MAP', extensions.SHARED_CACHE_MAP) self.set_type_class('_VACB', extensions.VACB) self.set_type_class('_POOL_TRACKER_BIG_PAGES', pool.POOL_TRACKER_BIG_PAGES) + self.set_type_class('_IMAGE_DOS_HEADER', pe.IMAGE_DOS_HEADER) + self.set_type_class('_IMAGE_NT_HEADERS', pe.IMAGE_NT_HEADERS) + + # Might not exist in 32-bit operating systems. + self.try_set_type_class('_IMAGE_NT_HEADERS64', pe.IMAGE_NT_HEADERS) # This doesn't exist in very specific versions of windows try: @@ -49,19 +54,11 @@ class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): pass # these don't exist in windows XP - try: - self.set_type_class('_MMADDRESS_NODE', extensions.MMVAD_SHORT) - except ValueError: - pass - + self.try_set_type_class('_MMADDRESS_NODE', extensions.MMVAD_SHORT) + # these were introduced starting in windows 8 - try: - self.set_type_class('_MM_AVL_NODE', extensions.MMVAD_SHORT) - except ValueError: - pass - + self.try_set_type_class('_MM_AVL_NODE', extensions.MMVAD_SHORT) + # these were introduced starting in windows 7 - try: - self.set_type_class('_RTL_BALANCED_NODE', extensions.MMVAD_SHORT) - except ValueError: - pass + self.try_set_type_class('_RTL_BALANCED_NODE', extensions.MMVAD_SHORT) + \ No newline at end of file diff --git a/volatility3/framework/symbols/windows/extensions/__init__.py b/volatility3/framework/symbols/windows/extensions/__init__.py index 7d083fbba..2f0f2388c 100755 --- a/volatility3/framework/symbols/windows/extensions/__init__.py +++ b/volatility3/framework/symbols/windows/extensions/__init__.py @@ -574,13 +574,9 @@ class EPROCESS(generic.GenericIntelProcess, pool.ExecutiveObject): proc_layer = self._context.layers[proc_layer_name] if not proc_layer.is_valid(self.Peb): raise exceptions.InvalidAddressException(proc_layer_name, self.Peb, - f"Invalid address at {self.Peb:0x}") + f"Invalid Peb address at {self.Peb:0x}") - sym_table = self.vol.type_name.split(constants.BANG)[0] - peb = self._context.object(f"{sym_table}{constants.BANG}_PEB", - layer_name = proc_layer_name, - offset = self.Peb) - return peb + return self.at_layer(proc_layer_name).Peb def load_order_modules(self) -> Iterable[interfaces.objects.ObjectInterface]: """Generator for DLLs in the order that they were loaded.""" From c8ab4eb814b79afd4a2553703d97a3749a2e1fd8 Mon Sep 17 00:00:00 2001 From: Paul Kermann Date: Mon, 25 Apr 2022 11:25:45 +0300 Subject: [PATCH 2/5] if not table name is present table name is an empty string --- volatility3/framework/interfaces/objects.py | 1 + 1 file changed, 1 insertion(+) diff --git a/volatility3/framework/interfaces/objects.py b/volatility3/framework/interfaces/objects.py index c1fb29bb6..8c7167a78 100644 --- a/volatility3/framework/interfaces/objects.py +++ b/volatility3/framework/interfaces/objects.py @@ -121,6 +121,7 @@ class ObjectInterface(metaclass = abc.ABCMeta): vol_info_dict["table_name"] = table_name vol_info_dict["short_name"] = struct_name else: + vol_info_dict["table_name"] = "" vol_info_dict["short_name"] = type_name self._vol = collections.ChainMap({}, vol_info_dict, object_info, kwargs) From 8bd7daf28fdbaf95dcfce1cfaa4e25517d24cd71 Mon Sep 17 00:00:00 2001 From: Paul Kermann Date: Mon, 2 May 2022 09:33:41 +0300 Subject: [PATCH 3/5] fix minor improvments --- volatility3/framework/interfaces/objects.py | 10 +--------- volatility3/framework/interfaces/symbols.py | 2 +- volatility3/framework/symbols/windows/__init__.py | 8 ++++---- .../framework/symbols/windows/extensions/__init__.py | 6 +++++- 4 files changed, 11 insertions(+), 15 deletions(-) diff --git a/volatility3/framework/interfaces/objects.py b/volatility3/framework/interfaces/objects.py index 8c7167a78..98ceca3d0 100644 --- a/volatility3/framework/interfaces/objects.py +++ b/volatility3/framework/interfaces/objects.py @@ -116,14 +116,6 @@ class ObjectInterface(metaclass = abc.ABCMeta): normalized_offset = object_info.offset & mask vol_info_dict = {'type_name': type_name, 'offset': normalized_offset} - if constants.BANG in type_name: - table_name, struct_name = type_name.split(constants.BANG) - vol_info_dict["table_name"] = table_name - vol_info_dict["short_name"] = struct_name - else: - vol_info_dict["table_name"] = "" - vol_info_dict["short_name"] = type_name - self._vol = collections.ChainMap({}, vol_info_dict, object_info, kwargs) self._context = context @@ -151,7 +143,7 @@ class ObjectInterface(metaclass = abc.ABCMeta): """ if constants.BANG not in self.vol.type_name: raise ValueError(f"Unable to determine table for symbol: {self.vol.type_name}") - table_name = self.vol.table_name + table_name = self.vol.type_name[:self.vol.type_name.index(constants.BANG)] if table_name not in self._context.symbol_space: raise KeyError(f"Symbol table not found in context's symbol_space for symbol: {self.vol.type_name}") return table_name diff --git a/volatility3/framework/interfaces/symbols.py b/volatility3/framework/interfaces/symbols.py index 99690054d..9f2cb9fc9 100644 --- a/volatility3/framework/interfaces/symbols.py +++ b/volatility3/framework/interfaces/symbols.py @@ -167,7 +167,7 @@ class BaseSymbolTableInterface: """ raise NotImplementedError("Abstract method set_type_class not implemented yet.") - def try_set_type_class(self, name: str, clazz: Type[objects.ObjectInterface]) -> bool: + def optional_set_type_class(self, name: str, clazz: Type[objects.ObjectInterface]) -> bool: """Calls the set_type_class function but does not throw an exception. Returns whether setting the type class was successfull. Args: diff --git a/volatility3/framework/symbols/windows/__init__.py b/volatility3/framework/symbols/windows/__init__.py index 468d998c4..b5129bb04 100755 --- a/volatility3/framework/symbols/windows/__init__.py +++ b/volatility3/framework/symbols/windows/__init__.py @@ -42,7 +42,7 @@ class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): self.set_type_class('_IMAGE_NT_HEADERS', pe.IMAGE_NT_HEADERS) # Might not exist in 32-bit operating systems. - self.try_set_type_class('_IMAGE_NT_HEADERS64', pe.IMAGE_NT_HEADERS) + self.optional_set_type_class('_IMAGE_NT_HEADERS64', pe.IMAGE_NT_HEADERS) # This doesn't exist in very specific versions of windows try: @@ -54,11 +54,11 @@ class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): pass # these don't exist in windows XP - self.try_set_type_class('_MMADDRESS_NODE', extensions.MMVAD_SHORT) + self.optional_set_type_class('_MMADDRESS_NODE', extensions.MMVAD_SHORT) # these were introduced starting in windows 8 - self.try_set_type_class('_MM_AVL_NODE', extensions.MMVAD_SHORT) + self.optional_set_type_class('_MM_AVL_NODE', extensions.MMVAD_SHORT) # these were introduced starting in windows 7 - self.try_set_type_class('_RTL_BALANCED_NODE', extensions.MMVAD_SHORT) + self.optional_set_type_class('_RTL_BALANCED_NODE', extensions.MMVAD_SHORT) \ No newline at end of file diff --git a/volatility3/framework/symbols/windows/extensions/__init__.py b/volatility3/framework/symbols/windows/extensions/__init__.py index 2f0f2388c..e7da0316d 100755 --- a/volatility3/framework/symbols/windows/extensions/__init__.py +++ b/volatility3/framework/symbols/windows/extensions/__init__.py @@ -576,7 +576,11 @@ class EPROCESS(generic.GenericIntelProcess, pool.ExecutiveObject): raise exceptions.InvalidAddressException(proc_layer_name, self.Peb, f"Invalid Peb address at {self.Peb:0x}") - return self.at_layer(proc_layer_name).Peb + sym_table = self.get_symbol_table_name() + peb = self._context.object(f"{sym_table}{constants.BANG}_PEB", + layer_name = proc_layer_name, + offset = self.Peb) + return peb def load_order_modules(self) -> Iterable[interfaces.objects.ObjectInterface]: """Generator for DLLs in the order that they were loaded.""" From bb1e41f59be2444a4efeb7f81043f3ed214211fa Mon Sep 17 00:00:00 2001 From: Paul Kermann Date: Mon, 2 May 2022 09:36:50 +0300 Subject: [PATCH 4/5] remove at_layer --- volatility3/framework/interfaces/objects.py | 5 ----- 1 file changed, 5 deletions(-) diff --git a/volatility3/framework/interfaces/objects.py b/volatility3/framework/interfaces/objects.py index 98ceca3d0..2240c58c9 100644 --- a/volatility3/framework/interfaces/objects.py +++ b/volatility3/framework/interfaces/objects.py @@ -170,11 +170,6 @@ class ObjectInterface(metaclass = abc.ABCMeta): size = object_template.size) return object_template(context = self._context, object_info = object_info) - def at_layer(self, new_layer_name) -> 'ObjectInterface': - """Returns the same object casted at a different layer. - """ - return self._context.object(self.vol.type_name, offset=self.vol.offset, layer_name=new_layer_name) - def has_member(self, member_name: str) -> bool: """Returns whether the object would contain a member called member_name. From 14c11b24f6af44f627bc276c76b2b53d852724fa Mon Sep 17 00:00:00 2001 From: Mike Auty Date: Mon, 2 May 2022 14:33:35 +0100 Subject: [PATCH 5/5] Symbols: Make _IMAGE_NT_HEADERS optional since not all Windows versions contain it --- volatility3/framework/symbols/windows/__init__.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/volatility3/framework/symbols/windows/__init__.py b/volatility3/framework/symbols/windows/__init__.py index b5129bb04..899b89dc2 100755 --- a/volatility3/framework/symbols/windows/__init__.py +++ b/volatility3/framework/symbols/windows/__init__.py @@ -39,9 +39,9 @@ class WindowsKernelIntermedSymbols(intermed.IntermediateSymbolTable): self.set_type_class('_VACB', extensions.VACB) self.set_type_class('_POOL_TRACKER_BIG_PAGES', pool.POOL_TRACKER_BIG_PAGES) self.set_type_class('_IMAGE_DOS_HEADER', pe.IMAGE_DOS_HEADER) - self.set_type_class('_IMAGE_NT_HEADERS', pe.IMAGE_NT_HEADERS) - # Might not exist in 32-bit operating systems. + # Might not necessarily defined in every version of windows + self.optional_set_type_class('_IMAGE_NT_HEADERS', pe.IMAGE_NT_HEADERS) self.optional_set_type_class('_IMAGE_NT_HEADERS64', pe.IMAGE_NT_HEADERS) # This doesn't exist in very specific versions of windows