
    XfG                     x   d Z ddlZddlZddlZddlmZmZmZmZm	Z	m
Z
mZ ddlmZmZmZmZ ddlmZ  ej        e          Z G d dej        j                  Zded	efd
Z G d dej        j                  Z G d de          Z G d dej        j                  Z G d deej         j!                  Z"dS )a  A `Context` maintains the accumulated state required for various plugins and
framework functions.

This has been made an object to allow quick swapping and changing of
contexts, to allow a plugin to act on multiple different contexts
without them interfering with each other.
    N)CallableIterableListOptionalSetTupleUnion)	constants
interfacessymbols
exceptions)	templatesc                       e Zd ZdZd fdZedej        j        fd            Z	e	j
        dej        j        ddfd            Z	edej        j        fd            Zedej        j        fd	            Zedej        j        fd
            Zdej        j        ddfdZ	 ddeeej        j        f         dededee         dej        j        f
dZ	 	 ddedededee         dee         dej        j        fdZ xZS )Contexta  Maintains the context within which to construct objects.

    The context object is the main method of carrying around state that's been constructed for the purposes of
    investigating memory.  It contains a symbol_space of all the symbols that can be accessed by plugins using the
    context.  It also contains the memory made up of data and translation layers, and it contains a factory method
    for creating new objects.

    Other context objects can be constructed as long as they support the
    :class:`~volatility3.framework.interfaces.context.ContextInterface`.  This is the primary context object to be used
    in the volatility framework.  It maintains the
    returnNc                 *   t                                                       t          j                    | _        t                      | _        t          j        	                                | _
        t          j                                        | _        dS )zInitializes the context.N)super__init__r   SymbolSpace_symbol_spaceModuleCollection_module_spacer   layersLayerContainer_memoryconfigurationHierarchicalDict_config)self	__class__s    Y/home/panchajanya/Development/work/volatility3/volatility3/framework/contexts/__init__.pyr   zContext.__init__#   sh    $022-//!(7799!/@@BB    c                     | j         S )znReturns a mutable copy of the configuration, but does not allow the
        whole configuration to be altered.)r   r   s    r!   configzContext.config-        |r"   valuec                 p    t          |t          j        j                  st	          d          || _        d S )Nz'Config must be of type HierarchicalDict)
isinstancer   r   r   	TypeErrorr   )r   r'   s     r!   r%   zContext.config3   s5    %!9!JKK 	GEFFFr"   c                     | j         S )z.A container for modules loaded in this context)r   r$   s    r!   moduleszContext.modules9   s     !!r"   c                     | j         S )zJThe space of all symbols that can be accessed within this
        context.)r   r$   s    r!   symbol_spacezContext.symbol_space>   s     !!r"   c                     | j         S )z{A LayerContainer object, allowing access to all data and translation
        layers currently available within the context.)r   r$   s    r!   r   zContext.layersD   r&   r"   layerc                 :    | j                             |           dS )a  Adds a named translation layer to the context.

        Args:
            layer: The layer to be added to the memory

        Raises:
            volatility3.framework.exceptions.LayerException: if the layer is already present, or has
                unmet dependencies
        N)r   	add_layerr   r0   s     r!   r2   zContext.add_layerL   s      	u%%%%%r"   object_type
layer_nameoffsetnative_layer_namec           	      2   t          |t          j        j                  sK	 | j                            |          }n# t          j        $ r | j                            |          }Y n^w xY wt          |t          j
                  r$| j                            |j        j                  }|}|                    |j                   |                                } |j        di |  || t          j                            ||||j                            S )a  Object factory, takes a context, symbol, offset and optional
        layername.

        Looks up the layername in the context, finds the object template based on the symbol,
        and constructs an object using the object template on the layer at the offset.

        Args:
            object_type: The name (or template) of the symbol type on which to construct the object.  If this is a name, it should contain an explicit table name.
            layer_name: The name of the layer on which to construct the object
            offset: The offset within the layer at which the data used to create the object lives
            native_layer_name: The name of the layer the object references (for pointers) if different to layer_name

        Returns:
            A fully constructed object
        )r5   r6   r7   size)contextobject_info )r)   r   objectsTemplater   get_typer   SymbolErrorget_enumerationr   ReferenceTemplatevol	type_nameupdateclone
update_volObjectInformationr9   )r   r4   r5   r6   r7   	argumentsobject_templates          r!   objectzContext.objectZ   s5   . +z'9'BCC 
	2R"&"4"="=k"J"J) R R R"&"4"D"D["Q"QR +y'BCC U"099+/:STT)O_0111)//11""//Y///"*<<%"3$)	 =  
 
 
 	
s   < )A('A(module_namer9   c                     |r t                               | |||||          S t                              | ||||          S )a  Constructs a new os-independent module.

        Args:
            module_name: The name of the module
            layer_name: The layer within the context in which the module exists
            offset: The offset at which the module exists in the layer
            native_layer_name: The default native layer for objects constructed by the module
            size: The size, in bytes, that the module occupies from offset location within the layer named layer_name
        )rL   r5   r6   r9   r7   )rL   r5   r6   r7   )SizedModulecreateModule)r   rL   r5   r6   r7   r9   s         r!   modulezContext.module   sg    "  	%%'%"3 &    }}#!/  
 
 	
r"   )r   NN)NN) __name__
__module____qualname____doc__r   propertyr   r   r   r%   setterr:   ModuleContainerr,   r   SymbolSpaceInterfacer.   r   r   DataLayerInterfacer2   r	   strr=   r>   intr   ObjectInterfacerK   ModuleInterfacerQ   __classcell__r    s   @r!   r   r      s1       
 
C C C C C C 
0A    X
 ]J4E $    ]
 "+; " " " X" "j0E " " " X"
 
)8    X
&z0C 
& 
& 
& 
& 
&& ,0-
 -
3
 2 ;;<-
 -
 	-

 $C=-
 
		+-
 -
 -
 -
h ,0" 
  
 
  
 	 

 $C= 
 sm 
 
		+ 
  
  
  
  
  
  
  
r"   r   methodr   c           	           dt           dt          f fd}dD ]P}t          t          j        j                   }t          ||          rt          ||t          ||                     Q|S )z;Returns a symbol using the symbol_table_name of the Module.namer   c                 
   t           j        |vr| j        t           j        z   |z   }n:|                    | j        t           j        z             rnt	          d            t          | j        j                  |          S )Nz-Cannot reference another module when calling )r
   BANGsymbol_table_name
startswith
ValueErrorgetattr_contextr.   )r   rd   rb   s     r!   wrapperz#get_module_wrapper.<locals>.wrapper   s~    >%%)IN:TADD__T3inDEE 	WUVUUVVV:wt}16::4@@@r"   )__annotations__rV   rT   rS   rU   )r\   r   rj   r   r:   r_   hasattrsetattr)rb   rl   entryproxy_interfaces   `   r!   get_module_wrapperrr      s    AC AH A A A A A A 	E 	E "*"4"DfMM?E** 	EGUGOU$C$CDDDNr"   c                      e Zd Zedej        j        dedededd f
d            Z		 	 	 dd	eded
e
e         deddf
dZ	 	 	 dded
e
e         ded	e
eedf                  ddf
dZddededee         fdZed             Z ed          Z ed          Z ed          Z ed          Z ed          Z ed          ZdS )rP   r:   rL   r5   r6   r   c                    t           j        j        }|j                            |          }|                    dd           }| |dd|          }||j         ||d          <   ||j         ||d          <   d|vr||d<   |D ]*}	|                    |	d           |j         |||	          <   + | |||          }
|                    |
           |
j        |j        |<   |
S )Nconfig_path	temporaryr,   r5   r6   rg   )	r   r   	path_joinr,   free_module_namegetr%   
add_modulerd   )clsr:   rL   r5   r6   kwargspathjoinrx   ru   arg
return_vals              r!   rO   zModule.create   s    +5"?;;KHHjj55"(;	;KLLK>Hxx\::;:@xxX667f,,*5F&' 	O 	OC9?C9N9NGN88K5566S+/?@@
:&&&&0o{#r"   NFr4   r7   absolutez"interfaces.objects.ObjectInterfacec                     t           j        |vr| j        t           j        z   |z   }nt          d          |t	          d          |s
|| j        z  }d|v r|d=  | j        j        d|| j        ||p| j	        d|S )a  Returns an object created using the symbol_table_name and layer_name
        of the Module.

        Args:
            object_type: Name of the type/enumeration (within the module) to construct
            offset: The location of the object, ignored when symbol_type is SYMBOL
            native_layer_name: Name of the layer in which constructed objects are made (for pointers)
            absolute: whether the type's offset is absolute within memory or relative to the module
        ;Cannot reference another module when constructing an objectNz.Offset must not be None for non-symbol objectsr5   r4   r5   r6   r7   r<   )
r
   rf   rg   ri   r*   _offsetrk   rK   _layer_name_native_layer_name)r   r4   r6   r7   r   r|   s         r!   rK   zModule.object   s    " >,,09>AKOKKM   >LMMM 	#dl"F 6!!|$#t}# 
#'/J43J	
 

 
 
 	
r"   symbol_namec                 t   t           j        |vr| j        t           j        z   |z   }nt          d          | j        j                            |          }|j        }|s
|| j        z  }|&|j	        t          d|j         d          |j	        }d|v r|d=  | j        j        d|| j        ||p| j        d|S )a  Returns an object based on a specific symbol (containing type and
        offset information) and the layer_name of the Module.  This will throw
        a ValueError if the symbol does not contain an associated type, or if
        the symbol name is invalid.  It will throw a SymbolError if the symbol
        cannot be found.

        Args:
            symbol_name: Name of the symbol (within the module) to construct
            native_layer_name: Name of the layer in which constructed objects are made (for pointers)
            absolute: whether the symbol's address is absolute or relative to the module
            object_type: Override for the type from the symobl to use (or if the symbol type is missing)
        r   NzSymbol z4 has no associated type and no object_type specifiedr5   r   r<   )r
   rf   rg   ri   rk   r.   
get_symboladdressr   typer*   rd   rK   r   r   )r   r   r7   r   r4   r|   
symbol_valr6   s           r!   object_from_symbolzModule.object_from_symbol  s   ( >,,09>AKOKKM  
 ]/::;GG
# 	#dl"F&cjoccc   )o 6!!|$ $t}# 
#'/J43J	
 

 
 
 	
r"   r   r9   c                     |dk     rt          d          t          | j        j                            || j        z
  || j                            S )cReturns the symbols within this module that live at the specified
        absolute offset provided.r   "Size must be strictly non-negative)r6   r9   
table_name)ri   listrk   r.   get_symbols_by_locationr   rg   )r   r6   r9   s      r!    get_symbols_by_absolute_locationz'Module.get_symbols_by_absolute_locationE  s^     !88ABBBM&>>,1 ?  
 
 	
r"   c                 :    | j         j        | j                 j        S rR   )r:   r.   rg   r   r$   s    r!   r   zModule.symbolsR  s    |()?@HHr"   r   r?   rA   
has_symbolhas_typehas_enumeration)NNF)NFNr   )rS   rT   rU   classmethodr   r:   ContextInterfacer\   r]   rO   r   boolrK   r	   r   r   r   rW   r   rr   r   r?   rA   r   r   r   r<   r"   r!   rP   rP      s       #4  	
  
   [@ +/'
 '
'
 '
 $C=	'

 '
 
.'
 '
 '
 '
X ,0RV5
 5
5
 $C=5
 	5

 eC)M$MNO5
 
.5
 5
 5
 5
n
 
s 
# 
dSVi 
 
 
 
 I I XI $#L11J!!*--H(():;;O##L11J!!*--H(():;;OOOr"   rP   c                        e Zd Zedefd            Ze ej                    defd                        Z	ddedede
e         f fdZ xZS )	rN   r   c                 @    | j                             dd          }|pdS )z3Returns the size of the module (0 for unknown size)r9   r   )r%   ry   )r   r9   s     r!   r9   zSizedModule.size_  s#     {vq))yqr"   c                 h   | j         j        | j                 }t          |t          j        j                  st          d          t          j        t          t          t          |                    | j        | j        d                              d                                                    S )zHashes the module for equality checks.

        The mapping should be sorted and should be quicker than reading
        the data We turn it into JSON to make a common string and use a
        quick hash, because collisions are unlikely
        z7Hashing modules on non-TranslationLayers is not allowedT)ignore_errorszutf-8)rk   r   r5   r)   r   TranslationLayerInterfacer*   hashlibmd5bytesr\   r   mappingr6   r9   	hexdigestr3   s     r!   hashzSizedModule.hashe  s     $T_5%!2!LMM 	WUVVV{Dt{DITRRSSTT 
 

 )++	r"   r   r6   r9   c                 r    || j         | j        z   k    rg S t                                          ||          S )r   )r   r9   r   r   )r   r6   r9   r    s      r!   r   z,SizedModule.get_symbols_by_absolute_locationx  s8     DL49,,,Iww77EEEr"   r   )rS   rT   rU   rW   r]   r9   	functools	lru_cacher\   r   r   r   r`   ra   s   @r!   rN   rN   ^  s        c    X
 Yc     X"F Fs F# FdSVi F F F F F F F F F Fr"   rN   c                        e Zd ZdZ	 ddeeej        j                          ddf fdZ	ddZ
ddedefd	Zedd
            Z	 ddededeeeee         f                  fdZ xZS )r   zRClass to contain a collection of SizedModules and reason about their
    contents.Nr,   r   c                 X    i | _         t                                          |           d S rR   )_prefix_countr   r   )r   r,   r    s     r!   r   zModuleCollection.__init__  s+      !!!!!r"   c                     g }t                      }| j        D ]E}|j        |vs|j        dk    r/|                    |           |                    |j                   Ft          |          S )zReturns a new deduplicated ModuleCollection featuring no repeated
        modules (based on data hash)

        All 0 sized modules will have identical hashes and are therefore
        included in the deduplicated version
        r   )set_modulesr   r9   appendaddr   )r   new_modulesseenmods       r!   deduplicatezModuleCollection.deduplicate  sq     = 	# 	#Cxt##sx1}}""3'''""",,,r"   rQ   prefixc                     || j         vrd| j         |<   |S | j         |         }|t          |          z   | v r|dz  }|t          |          z   | v || j         |<   |t          |          z   S )zReturns an unused module name   )r   r\   )r   r   counts      r!   rx   z!ModuleCollection.free_module_name  s    +++)*Dv&M"6*s5zz!T))QJE s5zz!T))%*6"E

""r"   c                 :    t                               d           | S )zPA name indexed dictionary of modules using that name in this
        collection.z_This method has been deprecated in favour of the ModuleCollection acting as a dictionary itself)vollogwarningr$   s    r!   r,   zModuleCollection.modules  s$     	m	
 	
 	
 r"   r   r6   r9   c              #     K   |dk     rt          d          | j        D ]d}| j        |         }t          |t                    r@||j        |j        z   k    r-||z   |j        k    r|j        |                    ||          fV  edS )zReturns a tuple of (module_name, list_of_symbol_names) for each
        module, where symbols live at the absolute offset in memory
        provided.r   r   N)ri   r   r)   rN   r6   r9   rd   r   )r   r6   r9   rL   rQ   s        r!   'get_module_symbols_by_absolute_locationz8ModuleCollection.get_module_symbols_by_absolute_location  s       !88ABBB= 		 		K];/F&+.. fmfk999TMV]22 ??MM   		 		r"   rR   )r   r   )rQ   r   )rS   rT   rU   rV   r   r   r   r:   r_   r   r   r\   rx   rW   r,   r]   r   r   r   r`   ra   s   @r!   r   r     s         MQ" "Z%7%G HI"	" " " " " "- - - -	# 	#s 	## 	# 	# 	# 	#    X () !$	%T#Y'	(       r"   r   c                   :    e Zd Zdej        j        dededdfdZdS )ConfigurableModuler:   ru   rd   r   Nc           	      ,   t           j        j                            | ||           | j        d         }| j        d         }| j        d         }t           j        j                            | ||           t
                              | ||||||           d S )Nr5   r6   rg   )r   r   ConfigurableInterfacer   r%   rP   )r   r:   ru   rd   r5   r6   rg   s          r!   r   zConfigurableModule.__init__  s     	 6??';	
 	
 	
 [.
X& K(;< 6??';	
 	
 	
 	'4V5F
	
 	
 	
 	
 	
r"   )rS   rT   rU   r   r:   r   r\   r   r<   r"   r!   r   r     sN        
!):
IL
TW
	
 
 
 
 
 
r"   r   )#rV   r   r   loggingtypingr   r   r   r   r   r   r	   volatility3.frameworkr
   r   r   r   volatility3.framework.objectsr   	getLoggerrS   r   r:   r   r   r\   rr   r_   rP   rN   rY   r   r   r   r   r<   r"   r!   <module>r      s          H H H H H H H H H H H H H H H H H H L L L L L L L L L L L L 3 3 3 3 3 3		8	$	$S
 S
 S
 S
 S
j 1 S
 S
 S
ls x    4U< U< U< U< U<Z/ U< U< U<pF F F F F& F F FD> > > > >z)9 > > >B
 
 
 
 
!9!O 
 
 
 
 
r"   