def ParseStringOption(self, options, argument_name, default_value=None): argument_value = getattr(options, argument_name, None) if not argument_value: return default_value if isinstance(argument_value, bytes): encoding = sys.stdin.encoding # Note that sys.stdin.encoding can be None. if not encoding: encoding = self.preferred_encoding try: argument_value = codecs.decode(argument_value, encoding) except UnicodeDecodeError as exception: raise errors.BadConfigOption( ('Unable to convert option: {0:s} to Unicode with error: ' '{1!s}.').format(argument_name, exception)) elif not isinstance(argument_value, str): raise errors.BadConfigOption( 'Unsupported option: {0:s} string type required.'.format( argument_name)) return argument_value
def BuildArtifactsRegistry(cls, artifact_definitions_path, custom_artifacts_path): if artifact_definitions_path and not os.path.isdir( artifact_definitions_path): raise errors.BadConfigOption( 'No such artifacts filter file: {0:s}.'.format( artifact_definitions_path)) if custom_artifacts_path and not os.path.isfile(custom_artifacts_path): raise errors.BadConfigOption( 'No such artifacts filter file: {0:s}.'.format( custom_artifacts_path)) registry = artifacts_registry.ArtifactDefinitionsRegistry() reader = artifacts_reader.YamlArtifactsReader() try: registry.ReadFromDirectory(reader, artifact_definitions_path) except (KeyError, artifacts_errors.FormatError) as exception: raise errors.BadConfigOption( ('Unable to read artifact definitions from: {0:s} with error: ' '{1!s}').format(artifact_definitions_path, exception)) if custom_artifacts_path: try: registry.ReadFromFile(reader, custom_artifacts_path) except (KeyError, artifacts_errors.FormatError) as exception: raise errors.BadConfigOption(( 'Unable to read artifact definitions from: {0:s} with error: ' '{1!s}').format(custom_artifacts_path, exception)) return registry
def _ParseCredentialOptions(self, options): """Parses the credential options. Args: options (argparse.Namespace): command line arguments. Raises: BadConfigOption: if the options are invalid. """ credentials = getattr(options, 'credentials', []) if not isinstance(credentials, list): raise errors.BadConfigOption('Unsupported credentials value.') for credential_string in credentials: credential_type, _, credential_data = credential_string.partition( ':') if not credential_type or not credential_data: raise errors.BadConfigOption( 'Badly formatted credential: {0:s}.'.format( credential_string)) if credential_type not in self._SUPPORTED_CREDENTIAL_TYPES: raise errors.BadConfigOption( 'Unsupported credential type for: {0:s}.'.format( credential_string)) if credential_type in self._BINARY_DATA_CREDENTIAL_TYPES: try: credential_data = codecs.decode(credential_data, 'hex') except TypeError: raise errors.BadConfigOption( 'Unsupported credential data for: {0:s}.'.format( credential_string)) self._credentials.append((credential_type, credential_data))
def set_conn_and_path(self): # Create a database connection try: if self.standalone_check: self._cursor = database_sqlite.Database( self.case_id, self.evidence_id, self._source_path, self._output_file_path) self._cursor.initialize() self._output_writer.Write("Standalone version\n") else: self._cursor = database.Database() self._cursor.open() except Exception as exception: self._output_writer.Write( 'Failed for connect to the database: {0!s}'.format(exception)) return # set root path if platform.system() == 'Windows': if self._output_file_path is None: raise errors.BadConfigOption('Missing output file path.') self._root_tmp_path = self._output_file_path + os.sep + 'tmp' if not os.path.exists(self._root_tmp_path): os.mkdir(self._root_tmp_path) # set storage path and temp path try: self.CreateStorageAndTempPath(cursor=self._cursor, case_id=self.case_id, evd_id=self.evidence_id) except Exception as exception: self._output_writer.Write(str(exception)) return False
def _ParseSourcePathOption(self, options): self._source_path = self.ParseStringOption(options, 'source') if self._source_path: self._source_path = os.path.abspath(self._source_path) if not self._source_path and not self.case_id and not self.evidence_id: raise errors.BadConfigOption('Missing source path.')
def _ParseStorageMediaImageOptions(self, options): self._partitions = getattr(options, 'partitions', 'all') if self._partitions: try: self._ParseVolumeIdentifiersString(self._partitions, prefix='p') except ValueError: raise errors.BadConfigOption('Unsupported partitions') self._volumes = getattr(options, 'volumes', None) if self._volumes: try: self._ParseVolumeIdentifiersString(self._volumes, prefix='apfs') except ValueError: raise errors.BadConfigOption('Unsupported volumes')
def _ParseStringOption(cls, options, argument_name, default_value=None): """Parses a string command line argument. Args: options (argparse.Namespace): parser options. argument_name (str): name of the command line argument. default_value (Optional[str]): default value of the command line argument. Returns: str: command line argument value or the default value if the command line argument is not set Raises: BadConfigOption: if the command line argument value cannot be converted to a Unicode string. """ argument_value = getattr(options, argument_name, None) if argument_value is None: return default_value #if isinstance(argument_value, py2to3.BYTES_TYPE): if isinstance(argument_value, bytes): encoding = sys.stdin.encoding # Note that sys.stdin.encoding can be None. if not encoding: encoding = locale.getpreferredencoding() if not encoding: encoding = cls._PREFERRED_ENCODING try: argument_value = argument_value.decode(encoding) except UnicodeDecodeError as exception: raise errors.BadConfigOption(( 'Unable to convert option: {0:s} to Unicode with error: ' '{1!s}.').format(argument_name, exception)) #elif not isinstance(argument_value, py2to3.UNICODE_TYPE): elif not isinstance(argument_value, str): raise errors.BadConfigOption( 'Unsupported option: {0:s} string type required.'.format( argument_name)) return argument_value
def _ParseTimezoneOption(self, options): time_zone_string = self.ParseStringOption(options, 'timezone') if isinstance(time_zone_string, (str, )): if time_zone_string.lower() == 'list': self.list_timezones = True elif time_zone_string: try: pytz.timezone(time_zone_string) except pytz.UnknownTimeZoneError: raise errors.BadConfigOption( 'Unknown time zone: {0:s}'.format(time_zone_string)) self._time_zone = time_zone_string
def ParseSignatureOptions(self): path = '../config/signatures.conf' if not os.path.exists(path): raise IOError( 'No such format specification file: {0:s}'.format(path)) try: specification_store = self._ReadSpecificationFile(path) except IOError as exception: raise errors.BadConfigOption( ('Unable to read format specification file: {0:s} with error: ' '{1!s}').format(path, exception)) self.signature_specifications = specification_store
def ParseSignatureOptions(self): self.main_path = os.path.dirname(os.path.abspath(__file__)) path = self.main_path + os.sep + '..' + os.sep + '..' + os.sep + 'config' + os.sep + 'signatures.conf' #print(self.main_path, path) if not os.path.exists(path): raise IOError( 'No such format specification file: {0:s}'.format(path)) try: specification_store = self._ReadSpecificationFile(path) except IOError as exception: raise errors.BadConfigOption(( 'Unable to read format specification file: {0:s} with error: ' '{1!s}').format(path, exception)) self.signature_specifications = specification_store
def _ParseVSSProcessingOptions(self, options): vss_only = False vss_stores = None self._process_vss = not getattr(options, 'no_vss', False) if self._process_vss: vss_only = getattr(options, 'vss_only', False) vss_stores = getattr(options, 'vss_stores', None) if vss_stores: try: self._ParseVolumeIdentifiersString(vss_stores, prefix='vss') except ValueError: raise errors.BadConfigOption('Unsupported VSS stores') self._vss_only = vss_only self._vss_stores = vss_stores
def _ParseNumericOption(cls, options, argument_name, default_value=None): """Parses a numeric command line argument. Args: options (argparse.Namespace): parser options. argument_name (str): name of the command line argument. default_value (Optional[int]): default value of the command line argument. Returns: int: command line argument value or the default value if the command line argument is not set Raises: BadConfigOption: if the command line argument value cannot be converted to a Unicode string. """ argument_value = getattr(options, argument_name, None) if argument_value is None: return default_value #if not isinstance(argument_value, py2to3.INTEGER_TYPES): if not isinstance(argument_value, (int, )): raise errors.BadConfigOption( 'Unsupported option: {0:s} integer type required.'.format( argument_name)) return argument_value
def ExtractDataFromSources(self, mode): self._output_writer.Write('Processing started.\n') investigator = {'investigator1': 'test', 'department': 'DFRC'} self.AddInvestigatorInformation(investigator) if not self.case_id or not self.evidence_id: raise errors.BadConfigOption( 'case_id or evidence_id does not exist.\n') # Set database connection and make root, tmp path try: self.set_conn_and_path() except errors.BadConfigOption as exception: self._output_writer.Write('ERROR: {0!s}\n'.format(exception)) return False # scan source scan_context = self.ScanSource(self._source_path) self._source_type = scan_context.source_type # set partition_list if self.ignore: self.set_partition_list() # set configuration configuration = self._CreateProcessingConfiguration() # set signature check options if self.signature_check: self._signature_tool.ParseSignatureOptions() self._signature_tool.SetScanner( self._signature_tool.signature_specifications) if self.rds_check: self.LoadReferenceDataSet() self.print_now_time(f'Start {mode} Image') disk_info = [] if not self.ignore: # After analyzing of an IMAGE, Put the partition information into the partition_info TABLE. disk_info = self.InsertImageInformation() # check partition_list if mode == 'Analyze' and not self._partition_list: if configuration.source_path_specs[0].TYPE_INDICATOR == 'APFS': pass else: raise errors.BadConfigObject('partition does not exist.\n') # print partition_list print('partition_list: ' + str(self._partition_list)) if mode == 'Analyze' and not self.ignore: self.print_now_time(f'Insert File Information') # After analyzing of filesystem, Put the block and file information into the block_info and file_info TABLE. self.InsertFileInformation() # create process engine = process_engine.ProcessEngine() # determine operating system self.print_now_time(f'Determine Operation System') self._Preprocess(engine) # set timezone self.print_now_time(f'Set Timezone') if self._time_zone is not pytz.UTC: engine.knowledge_base.SetTimeZone(self._time_zone) # set modules self.print_now_time(f'Set Modules') engine.SetProcessModules( module_filter_expression=configuration.module_filter_expression) # carpe.py if mode == 'Analyze': # parse Artifacts engine.Process(configuration) # set advanced modules engine.SetProcessAdvancedModules( advanced_module_filter_expression=configuration. advanced_module_filter_expression) # parse advanced modules engine.ProcessAdvancedModules(configuration) # carpe_carve.py elif mode == 'Carve': # check partition_list if not self._partition_list: print("No partition") engine.process_carve(configuration, is_partition=False) else: print(self._partition_list) engine.process_carve(configuration, is_partition=True) # carpe_extract.py elif mode == 'Extract': for par in disk_info: if par['length'] != 0: par['length'] /= (1024 * 1024) # byte to MB info = "" info += "vol_name: " + par['vol_name'] + "\n" info += "filesystem: " + str(par['filesystem']) + "\n" info += "par_label: " + par['par_label'] + "\n" info += "size: " + str(int(par['length'])) + "MB\n" print(info) self.print_now_time(f'Start Extract File/Directory') module = engine._modules.get('extract_connector', None) module.ExtractTargetDirToPath( source_path_spec=configuration.source_path_specs[ int(self.par_num[1:]) - 1], configuration=configuration, dir_path=self.extract_path, output_path=self._output_file_path) self.print_now_time(f'Finish Extract File/Directory') self._cursor.close() self.print_now_time(f'Finish {mode} Image')
def ParseOptions(cls, options, configuration_object): """Parses and validates options. Args: options (argparse.Namespace): parser options. configuration_object (CLITool): object to be configured by the argument helper. Raises: BadConfigObject: when the configuration object is of the wrong type. BadConfigOption: if the required artifact definitions are not defined. """ if not isinstance(configuration_object, tools.CLITool): raise errors.BadConfigObject( 'Configuration object is not an instance of CLITool') artifacts_path = getattr(options, 'artifact_definitions_path', None) if (not artifacts_path or not os.path.exists(artifacts_path)): artifacts_path = os.path.dirname(cls._PATH) artifacts_path = os.path.dirname(artifacts_path) artifacts_path = os.path.dirname(artifacts_path) artifacts_path = os.path.join(artifacts_path, 'artifacts') if not os.path.exists( artifacts_path) and 'VIRTUAL_ENV' in os.environ: artifacts_path = os.path.join(os.environ['VIRTUAL_ENV'], 'share', 'artifacts') if not os.path.exists(artifacts_path): artifacts_path = os.path.join(sys.prefix, 'share', 'artifacts') if not os.path.exists(artifacts_path): artifacts_path = os.path.join(sys.prefix, 'local', 'share', 'artifacts') if sys.prefix != '/usr': if not os.path.exists(artifacts_path): artifacts_path = os.path.join('/usr', 'share', 'artifacts') if not os.path.exists(artifacts_path): artifacts_path = os.path.join('/usr', 'local', 'share', 'artifacts') if not os.path.exists(artifacts_path): artifacts_path = None if not artifacts_path or not os.path.exists(artifacts_path): raise errors.BadConfigOption( 'Unable to determine path to artifact definitions.') custom_artifacts_path = getattr(options, 'custom_artifact_definitions_path', None) if custom_artifacts_path and not os.path.isfile(custom_artifacts_path): raise errors.BadConfigOption( 'No such artifacts filter file: {0:s}.'.format( custom_artifacts_path)) if custom_artifacts_path: logger.info('Custom artifact filter file: {0:s}'.format( custom_artifacts_path)) registry = artifacts_registry.ArtifactDefinitionsRegistry() reader = artifacts_reader.YamlArtifactsReader() logger.info('Determined artifact definitions path: {0:s}'.format( artifacts_path)) try: registry.ReadFromDirectory(reader, artifacts_path) except (KeyError, artifacts_errors.FormatError) as exception: raise errors.BadConfigOption( ('Unable to read artifact definitions from: {0:s} with error: ' '{1!s}').format(artifacts_path, exception)) for name in preprocessors_manager.PreprocessPluginsManager.GetNames(): if not registry.GetDefinitionByName(name): raise errors.BadConfigOption( 'Missing required artifact definition: {0:s}'.format(name)) if custom_artifacts_path: try: registry.ReadFromFile(reader, custom_artifacts_path) except (KeyError, artifacts_errors.FormatError) as exception: raise errors.BadConfigOption(( 'Unable to read artifact definitions from: {0:s} with error: ' '{1!s}').format(custom_artifacts_path, exception)) setattr(configuration_object, '_artifact_definitions_path', artifacts_path) setattr(configuration_object, '_custom_artifacts_path', custom_artifacts_path)