Source code for winregrc.scripts.catalog

#!/usr/bin/env python3
"""Script to extract a catalog of Windows Registry keys and values."""

import argparse
import logging
import re
import sys

from dfwinreg import creg as dfwinreg_creg
from dfwinreg import regf as dfwinreg_regf
from dfwinreg import registry as dfwinreg_registry

from winregrc import catalog
from winregrc import output_writers


[docs] class StdoutWriter(output_writers.StdoutOutputWriter): """Stdout output writer."""
[docs] def WriteKeyPath(self, key_path): """Writes a key path to the output. Args: key_path (str): key path. """ self.WriteText(f"{key_path:s}\n")
[docs] def WriteValueDescriptor(self, value_name, value_data_type): """Writes a value descriptor to the output. Args: value_name (str): name of the value. value_data_type (str): data type of the value. """ self.WriteText(f"\t{value_name:s}\t{value_data_type:s}\n")
[docs] def Main(): """Entry point of console script to extract Windows Registry catalogs. Returns: int: exit code that is provided to sys.exit(). """ argument_parser = argparse.ArgumentParser( description=("Extracts a catalog of Windows Registry keys and values.") ) argument_parser.add_argument( "--group_keys", "--group-keys", dest="group_keys", action="store_true", default=False, help="Group keys with similar values.", ) argument_parser.add_argument( "source", nargs="?", action="store", metavar="PATH", default=None, help="path of a Windows Registry file.", ) options = argument_parser.parse_args() if not options.source: print("Source value is missing.") print("") argument_parser.print_help() print("") return 1 logging.basicConfig(level=logging.INFO, format="[%(levelname)s] %(message)s") with open(options.source, "rb") as file_object: try: registry_file = dfwinreg_regf.REGFWinRegistryFile() registry_file.Open(file_object) except OSError: registry_file = None if not registry_file: try: registry_file = dfwinreg_creg.CREGWinRegistryFile() registry_file.Open(file_object) except OSError: registry_file = None if not registry_file: print("Unable to open Windows Registry file.") return 1 # Using dfWinReg to determine Windows native key paths if available. registry = dfwinreg_registry.WinRegistry() key_path_prefix = registry.GetRegistryFileMapping(registry_file) registry_file.SetKeyPathPrefix(key_path_prefix) root_key = registry_file.GetRootKey() output_writer_object = StdoutWriter() if not output_writer_object.Open(): print("Unable to open output writer.") print("") return 1 collector_object = catalog.CatalogCollector(group_keys=options.group_keys) def AlphanumericCompare(key): return ( int(text) if text.isdigit() else text.lower() for text in re.split("([0-9]+)", key[0]) ) try: has_results = False for key_descriptor in collector_object.Collect(root_key): output_writer_object.WriteKeyPath(key_descriptor.key_path) for key_path in key_descriptor.grouped_key_paths: output_writer_object.WriteKeyPath(key_path) for value_name, data_type_string in sorted( key_descriptor.value_descriptors, key=AlphanumericCompare ): output_writer_object.WriteValueDescriptor( value_name, data_type_string ) if options.group_keys: output_writer_object.WriteText("\n") has_results = True finally: output_writer_object.Close() if not has_results: print("No keys and values found.") return 0
if __name__ == "__main__": sys.exit(Main())