From 73132dad6f62560f598dd9265d06d625582b9250 Mon Sep 17 00:00:00 2001 From: Martin Date: Thu, 5 Oct 2017 16:36:09 +0200 Subject: [PATCH 1/3] over.misc.hexdump now accepts anything as long as it's convertible to bytes --- over/misc.py | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/over/misc.py b/over/misc.py index c7ff740..4167191 100644 --- a/over/misc.py +++ b/over/misc.py @@ -130,8 +130,10 @@ def hexdump(data, indent=0, offset=16, show_header=True, show_offsets=True, show output_io = io.StringIO() if not output else output - if type(data) is not bytes: - raise ValueError("data must be bytes") + try: + data = bytes(data) + except: + raise ValueError("data must be bytes or similar") offset_figures = math.ceil(math.log2(len(data)) / 8) * 2 if data else 2 format_str = "%%0%dx " %(offset_figures) From 0d1794d4b633c87c3f7f462ab49716ae51e3a8c6 Mon Sep 17 00:00:00 2001 From: Martin Date: Fri, 6 Oct 2017 11:27:42 +0200 Subject: [PATCH 2/3] added over.misc.raw_to_hex and over.misc.hex_to_raw --- over/misc.py | 28 ++++++++++++++++++++++++++++ 1 file changed, 28 insertions(+) diff --git a/over/misc.py b/over/misc.py index 4167191..fd9f13c 100644 --- a/over/misc.py +++ b/over/misc.py @@ -191,3 +191,31 @@ def hexdump(data, indent=0, offset=16, show_header=True, show_offsets=True, show if not output: output_io.seek(0) return output_io.read() + +# -------------------------------------------------- + +def raw_to_hex(raw, spaces=True): + """ + Converts a bytearray (or bytes) into its textual hexadecimal representation. + """ + + output = [] + + for o in raw: + output.append(hex(o)[2:].zfill(2)) + + return (" " if spaces else "").join(output) + +def hex_to_raw(text): + """ + Converts a hexadecimal representation of a byte array into a bytearray. + """ + + output = [] + + text = text.replace(" ", "") + + for i in range(len(text)//2): + output.append(int(text[2*i:2*i+2], 16)) + + return bytearray(output) From 853e05a27541c851976142535040c953b58919bc Mon Sep 17 00:00:00 2001 From: Martin Date: Fri, 6 Oct 2017 15:17:47 +0200 Subject: [PATCH 3/3] rewrote over.types.ndict to use composition instead of inheritance due to obscue issues on raspbian --- over/types.py | 35 ++++++++++++++++++++++++++++------- 1 file changed, 28 insertions(+), 7 deletions(-) diff --git a/over/types.py b/over/types.py index ef7a671..db19466 100644 --- a/over/types.py +++ b/over/types.py @@ -5,9 +5,9 @@ from collections import OrderedDict # -------------------------------------------------- -class ndict(OrderedDict): +class ndict: """ - An OrderedDict subclass whose keys are exposed as attributes. + An OrderedDict wrapper whose keys are exposed as attributes. >>> d = ndict() >>> d.alpha = 1 @@ -20,17 +20,38 @@ class ndict(OrderedDict): {"alpha": 1, "beta": 42} """ + __methods__ = ["values", "items"] + + def __init__(self, *args, **kwargs): + object.__setattr__(self, "d", OrderedDict(*args, **kwargs)) + + def __repr__(self): + return "|" + repr(self.d) + + def __iter__(self): + return self.d.__iter__() + def __getattr__(self, name): """ @while looking up an attribute """ - if name in self: - return self[name] - elif name.replace("_", "-") in self: - return self[name.replace("_", "-")] + safe_name = name.replace("_", "-") + + if name in self.__methods__: + return getattr(self.d, name) + if name in self.d: + return self.d[name] + elif safe_name in self.d: + return self.d[safe_name] else: raise AttributeError('"ndict" object has no attribute "%s"' %(name)) def __setattr__(self, name, value): - self[name] = value + self.d[name] = value + + def __getitem__(self, key): + return self.d[key] + + def __setitem__(self, key, value): + self.d[key] = value