Skip to content

Instantly share code, notes, and snippets.

@kendfss
Created March 26, 2021 13:46
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save kendfss/6addbbc530cb5a20c89501179424dca5 to your computer and use it in GitHub Desktop.
Save kendfss/6addbbc530cb5a20c89501179424dca5 to your computer and use it in GitHub Desktop.
Simple script for nagivating the windows registry.
"""
I was working on this until I found a more simple library:
https://github.com/shpaker/winregistry
Feel free to use/extend it if you really want to handle key objects for some reason, otherwise go ahead and try Shpaker's library because it really naturalizes the workflow without going for any of my arbitrary decisions
"""
__all__ = 'RegKey paths image_line hkeys access_code_names'.split()
from winreg import HKEY_CURRENT_USER, KEY_READ, OpenKey, EnumKey, EnumValue, QueryInfoKey, QueryValue, QueryValueEx
import os, winreg
from tabulate import tabulate
from sl4ng import show, splitall, pop, getsource, mainame, tipo, eq
def enum(key):
i = 1
while i:
try:
subkey = EnumKey(key, i - 1)
yield subkey
i += 1
except WindowsError as e:
i = 0
hkey_names = {
winreg.HKEY_CLASSES_ROOT: 'HKEY_CLASSES_ROOT',
# Registry entries subordinate to this key define types (or classes) of documents and the properties associated with those types. Shell and COM applications use the information stored under this key.
winreg.HKEY_CURRENT_USER: 'HKEY_CURRENT_USER',
# Registry entries subordinate to this key define the preferences of the current user. These preferences include the settings of environment variables, data about program groups, colors, printers, network connections, and application preferences.
winreg.HKEY_LOCAL_MACHINE: 'HKEY_LOCAL_MACHINE',
# Registry entries subordinate to this key define the physical state of the computer, including data about the bus type, system memory, and installed hardware and software.
winreg.HKEY_USERS: 'HKEY_USERS',
# Registry entries subordinate to this key define the default user configuration for new users on the local computer and the user configuration for the current user.
winreg.HKEY_PERFORMANCE_DATA: 'HKEY_PERFORMANCE_DATA',
# Registry entries subordinate to this key allow you to access performance data. The data is not actually stored in the registry; the registry functions cause the system to collect the data from its source.
winreg.HKEY_CURRENT_CONFIG: 'HKEY_CURRENT_CONFIG',
# Contains information about the current hardware profile of the local computer system.
winreg.HKEY_DYN_DATA: 'HKEY_DYN_DATA',
# This key is not used in versions of Windows after 98.
}
hkeys = {'_'.join(name.lower().split('_')[1:]): key for key, name in hkey_names.items()}
access_code_names = {
winreg.KEY_ALL_ACCESS: 'KEY_ALL_ACCESS',
# Combines the STANDARD_RIGHTS_REQUIRED, KEY_QUERY_VALUE, KEY_SET_VALUE, KEY_CREATE_SUB_KEY, KEY_ENUMERATE_SUB_KEYS, KEY_NOTIFY, and KEY_CREATE_LINK access rights.
winreg.KEY_WRITE: 'KEY_WRITE',
# Combines the STANDARD_RIGHTS_WRITE, KEY_SET_VALUE, and KEY_CREATE_SUB_KEY access rights.
winreg.KEY_READ: 'KEY_READ',
# Combines the STANDARD_RIGHTS_READ, KEY_QUERY_VALUE, KEY_ENUMERATE_SUB_KEYS, and KEY_NOTIFY values.
winreg.KEY_EXECUTE: 'KEY_EXECUTE',
# Equivalent to KEY_READ.
winreg.KEY_QUERY_VALUE: 'KEY_QUERY_VALUE',
# Required to query the values of a registry key.
winreg.KEY_SET_VALUE: 'KEY_SET_VALUE',
# Required to create, delete, or set a registry value.
winreg.KEY_CREATE_SUB_KEY: 'KEY_CREATE_SUB_KEY',
# Required to create a subkey of a registry key.
winreg.KEY_ENUMERATE_SUB_KEYS: 'KEY_ENUMERATE_SUB_KEYS',
# Required to enumerate the subkeys of a registry key.
winreg.KEY_NOTIFY: 'KEY_NOTIFY',
# Required to request change notifications for a registry key or for subkeys of a registry key.
winreg.KEY_CREATE_LINK: 'KEY_CREATE_LINK',
# Reserved for system use.
}
access_codes = {'_'.join(name.lower().split('_')[:1]): code for code, name in access_code_names.items()}
short = winreg.HKEY_CLASSES_ROOT
class RegKey:
def __init__(self, root=HKEY_CURRENT_USER, path='', reserved=0, access=winreg.KEY_READ):
while isinstance(root, type(self)):
path = os.path.join(root.path, path)
root = root.root
path = os.sep.join(splitall('\/', path))
self.root = root
self.path = path
self.access = access
self.reserved = reserved
self.key = winreg.OpenKey(root, path, reserved=reserved, access=access)
self.__index = -1
def __enter__(self):
return self
def __exit__(self, *args):
del self
def __hash__(self):
return hash(self.key)
def __del__(self):
winreg.CloseKey(self.key)
def __len__(self):
return sum(1 for i in iter(self))
def __iter__(self):
i = 1
while i:
try:
subkey = winreg.EnumKey(self.key, i - 1)
yield self[subkey]
i += 1
except WindowsError as e:
i = 0
def __next__(self):
if self.__index < len(self):
self.__index += 1
return list(self)[self.__index]
self.__index = -1
raise StopIteration
def __getitem__(self, key:str):
key= os.sep.join(splitall('\/', key))
return type(self)(self.key, key, reserved=self.reserved, access=self.access)
def __truediv__(self, key:str):
return self.__getitem__(key)
def __repr__(self):
return f"{tipo(self)}(name={self.name}, subs={self.info[0]}, vals={self.info[1]})"
@property
def string(self):
if self.root in hkey_names:
return os.path.join(hkey_names[self.root], self.path)
@property
def name(self):
return nome if (nome := self.path.split(os.sep)[-1]) else hkey_names[self.root]
@property
def info(self):
return winreg.QueryInfoKey(self.key)
@property
def subs(self):
"""
Names of subkeys
"""
return tuple(i.name for i in iter(self))
@property
def super(self):
return type(self)(
self.root,
os.sep.join(self.path.split(os.sep)[:-1]),
reserved=self.reserved,
access=self.access
)
@property
def iter_values(self):
for value in range(self.info[1]):
yield winreg.EnumValue(self.key, value)
def up(self, distance:int=1):
if not self.key in hkey_names:
x = 'self'
for i in range(distance):
x += '.super'
return eval(''.join(x))
return self
def value(self, name, subkey:bool=False):
return (winreg.QueryValueEx(self.key, name), winreg.QueryValue(self.key, name))[subkey]
def values(self):
print(tabulate(self.iter_values, headers='name value type'.split()))
def sort(self, values:bool=False, verbose:bool=False, reverse:bool=True):
"""
Sort the subkeys of a given key by
Params:
values
sort by each key's value count instead of the number of subkeys each one has
verbose
display the subkey objects instead of their names
reverse (true -> descent)
sort by ascent instead of descent
"""
key = 1 if values else 0
d = {(sub.name, sub)[verbose]: sub.info[key] for sub in self}
return sorted(d, key=d.get, reverse=reverse)
def details(self):
for i in self:
if (content:=tuple(i.iter_values)):
print(i)
table = tabulate(content, headers='name value type'.split())
table = '\n\t' + '\n\t'.join(map(str.strip, table.splitlines()))
print(table)
print('\n'*2)
paths = RegKey(path=r'Software\Image-Line\Shared\Paths')
image_line = RegKey(path=r'Software\Image-Line')
if eval(mainame):
def vdirs(x=paths):
for n, v, t in x.iter_values:
if os.path.isdir(v):
print(n)
show(os.listdir(v), 1, head=0)
vdirs()
with RegKey(paths.root, paths.path) as key1:
print(key1)
print(str(key1))
with winreg.OpenKey(paths.root, paths.path) as key2:
print(key2)
print(str(key2))
print('\n'*3)
with RegKey(image_line, 'shared') as key3:
print(key3)
print(str(key3))
print('\n'*3)
with RegKey(hkeys['current_user'], 'software') as key4:
print(key4)
print(str(key4))
print('\n'*3)
with RegKey(key4, 'image-line') as key5:
print(key5)
print(str(key5))
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment