Secure your code as it's written. Use Snyk Code to scan source code in minutes - no build needed - and fix issues immediately.
def iter_subkeys(self):
if not self.header.subkey_count:
return None
# Go to the offset where the subkey list starts (+4 is because of the cell header)
target_offset = REGF_HEADER_SIZE + 4 + self.header.subkeys_list_offset
self._stream.seek(target_offset)
# Read the signature
try:
signature = Bytes(2).parse_stream(self._stream)
except StreamError as ex:
raise RegistryParsingException(f'Bad subkey at offset {target_offset}: {ex}')
# LF, LH and RI contain subkeys
if signature in [HASH_LEAF_SIGNATURE, FAST_LEAF_SIGNATURE, LEAF_INDEX_SIGNATURE]:
yield from self._parse_subkeys(self._stream, signature=signature)
# RI contains pointers to arrays of subkeys
elif signature == INDEX_ROOT_SIGNATURE:
ri_record = RIRecord(self._stream)
if ri_record.header.element_count > 0:
for element in ri_record.header.elements:
# We skip 6 because of the signature as well as the cell header
element_target_offset = REGF_HEADER_SIZE + 4 + element.subkey_list_offset
self._stream.seek(element_target_offset)
yield from self._parse_subkeys(self._stream)
def _parse_subkeys(stream, signature=None):
"""
Parse an LI , LF or LH Record
:param stream: A stream at the header of the LH or LF entry, skipping the signature
:return:
"""
if not signature:
signature = stream.read(2)
if signature in [HASH_LEAF_SIGNATURE, FAST_LEAF_SIGNATURE]:
subkeys = LF_LH_SK_ELEMENT.parse_stream(stream)
elif signature == LEAF_INDEX_SIGNATURE:
subkeys = INDEX_LEAF.parse_stream(stream)
else:
raise RegistryParsingException(f'Expected a known signature, got: {signature} at offset {stream.tell()}')
for subkey in subkeys.elements:
stream.seek(REGF_HEADER_SIZE + subkey.key_node_offset)
# This cell should always be allocated, therefor we expect a negative size
cell_size = Int32sl.parse_stream(stream) * -1
# We read to this offset and skip 2 bytes, because that is the cell size we just read
nk_cell = Cell(cell_type='nk', offset=stream.tell() + 2, size=cell_size)
nk_record = NKRecord(cell=nk_cell, stream=stream)
yield nk_record