From 1de3ddb8d8707bb4c3c80f01cb65b37c3ab60e89 Mon Sep 17 00:00:00 2001 From: JoYo <> Date: Wed, 26 Jan 2022 13:46:29 -0500 Subject: [PATCH] fixed class member append hang, additional rizin architectures --- subdisassem/capstone_wrapper.py | 51 +++++++++--- subdisassem/rizin_wrapper.py | 135 ++++++++++++++++++++++++++++---- subdisassem/scripts.py | 19 +++++ 3 files changed, 177 insertions(+), 28 deletions(-) diff --git a/subdisassem/capstone_wrapper.py b/subdisassem/capstone_wrapper.py index 614ad74..7749cd4 100644 --- a/subdisassem/capstone_wrapper.py +++ b/subdisassem/capstone_wrapper.py @@ -54,50 +54,72 @@ class _CapstoneBase: def __lt__(self, other): return len(self) < len(other) + def __contains__(self, name: str): + return hasattr(self, name) + @property def objdump(self) -> str: - opcodes = str() + if "_objdump" in self: + return self._objdump + + _objdump = str() for opcode in self.disassembly: - opcodes += f"{opcode.address:#02x}:\t{opcode.mnemonic}\t{opcode.op_str}\n" + _objdump += f"{opcode.address:#02x}:\t{opcode.mnemonic}\t{opcode.op_str}\n" - return opcodes + self._objdump = _objdump + return self._objdump @property def disasm(self) -> list: - opcodes = list() + if "_disasm" in self: + return self._disasm + + _disasm = list() for opcode in self.disassembly: - opcodes.append([opcode.address, opcode.mnemonic, opcode.op_str]) + if not "unknown" == opcode.mnemonic: + _disasm.append([opcode.address, opcode.mnemonic, opcode.op_str]) - return opcodes + self._disasm = _disasm + return self._disasm @property def rets(self) -> list: - if hasattr(self, "_rets"): + if "_rets" in self: return self._rets - self._rets = list() + _rets = list() for opcode in self.disassembly: if "ret" in opcode.mnemonic: - self._rets.append(opcode.mnemonic) + _rets.append(opcode.mnemonic) + self._rets = _rets return self._rets @property def ret_rates(self) -> list: + if "_ret_rates" in self: + return self._ret_rates + rates = dict() for mnemonic in set(self.rets): rates[mnemonic] = self.rets.count(mnemonic) - listed = sorted(((value, key) for (key, value) in rates.items()), reverse=True) + _ret_rates = sorted( + ((value, key) for (key, value) in rates.items()), reverse=True + ) - return listed + self._ret_rates = _ret_rates + return self._ret_rates @property def mnemonic_rates(self) -> list: + if "_mnemonic_rates" in self: + return self._mnemonic_rates + mnemonics = list() for opcode in self.disassembly: @@ -108,9 +130,12 @@ class _CapstoneBase: for mnemonic in set(mnemonics): rates[mnemonic] = mnemonics.count(mnemonic) - listed = sorted(((value, key) for (key, value) in rates.items()), reverse=True) + _mnemonic_rates = sorted( + ((value, key) for (key, value) in rates.items()), reverse=True + ) - return listed + self._mnemonic_rates = _mnemonic_rates + return self._mnemonic_rates class x86_16(_CapstoneBase): diff --git a/subdisassem/rizin_wrapper.py b/subdisassem/rizin_wrapper.py index af14708..69302d6 100644 --- a/subdisassem/rizin_wrapper.py +++ b/subdisassem/rizin_wrapper.py @@ -20,31 +20,36 @@ class _RizinBase: return self.objdump def __len__(self) -> int: - return len(self.disassembly) + return len(self.disasm) def __lt__(self, other): return len(self) < len(other) + def __contains__(self, name: str): + return hasattr(self, name) + @property def objdump(self) -> str: - if hasattr(self, "_objdump"): + if "_objdump" in self: return self._objdump - self._objdump = str() + _objdump = str() for each in self.disassembly: offset = each.get("offset") opcode = each.get("opcode") - self._objdump += f"{offset:#02x}:\t{opcode}\n" + if opcode: + _objdump += f"{offset:#02x}:\t{opcode}\n" + self._objdump = _objdump return self._objdump @property def disasm(self) -> list: - if hasattr(self, "_disasm"): + if "_disasm" in self: return self._disasm - self._disasm = list() + _disasm = list() for each in self.disassembly: offset = each.get("offset") @@ -53,30 +58,32 @@ class _RizinBase: if opcode: mnemonic = opcode.split(" ")[0] opcode = opcode.split(" ")[1:] - else: - mnemonic = None - - self._disasm.append([offset, mnemonic, opcode]) + _disasm.append([offset, mnemonic, opcode]) + self._disasm = _disasm return self._disasm @property def rets(self) -> list: - if hasattr(self, "_rets"): + if "_rets" in self: return self._rets - self._rets = list() + _rets = list() for each in self.disasm: _, mnemonic, _ = each if mnemonic and "ret" in mnemonic: - self._rets.append(mnemonic) + _rets.append(mnemonic) + self._rets = _rets return self._rets @property def ret_rates(self) -> list: + if "_ret_rates" in self: + return self._ret_rates + rates = dict() for mnemonic in set(self.rets): @@ -86,10 +93,14 @@ class _RizinBase: ((value, key) for (key, value) in rates.items()), reverse=True ) - return _ret_rates + self._ret_rates = _ret_rates + return self._ret_rates @property def mnemonic_rates(self) -> list: + if "_mnemonic_rates" in self: + return self._mnemonic_rates + mnemonics = list() for each in self.disasm: @@ -107,8 +118,102 @@ class _RizinBase: ((value, key) for (key, value) in rates.items()), reverse=True ) - return _mnemonic_rates + self._mnemonic_rates = _mnemonic_rates + return self._mnemonic_rates + + +class _6502_8(_RizinBase): + arch_cmds = ["e asm.arch=6502", "e asm.bits=8"] + name = "6502/NES/C64/Tamagotchi/T-1000 CPU" + + +class _6502_16(_RizinBase): + arch_cmds = ["e asm.arch=6502", "e asm.bits=16"] + name = "6502/NES/C64/Tamagotchi/T-1000 CPU" + + +class _8051(_RizinBase): + arch_cmds = ["e asm.arch=8051", "e asm.bits=8"] + name = "8051 Intel CPU" + + +class amd29k(_RizinBase): + arch_cmds = ["e asm.arch=amd29k", "e asm.bits=32"] + name = "AMD 29k RISC CPU" + + +class arc_16(_RizinBase): + arch_cmds = ["e asm.arch=arc", "e asm.bits=16"] + name = "Argonaut RISC Core" + + +class arc_32(_RizinBase): + arch_cmds = ["e asm.arch=arc", "e asm.bits=32"] + name = "Argonaut RISC Core" + + +class arm_as_16(_RizinBase): + arch_cmds = ["e asm.arch=arm.as", "e asm.bits=16"] + name = "as ARM Assembler (use RZ_ARM32_AS and RZ_ARM64_AS environment)" + + +class arm_as_32(_RizinBase): + arch_cmds = ["e asm.arch=arm.as", "e asm.bits=32"] + name = "as ARM Assembler (use RZ_ARM32_AS and RZ_ARM64_AS environment)" + + +class arm_as_64(_RizinBase): + arch_cmds = ["e asm.arch=arm.as", "e asm.bits=64"] + name = "as ARM Assembler (use RZ_ARM32_AS and RZ_ARM64_AS environment)" + + +class arm_16(_RizinBase): + arch_cmds = ["e asm.arch=arm", "e asm.bits=16"] + name = "Capstone ARM disassembler" + + +class arm_32(_RizinBase): + arch_cmds = ["e asm.arch=arm", "e asm.bits=32"] + name = "Capstone ARM disassembler" + + +class arm_64(_RizinBase): + arch_cmds = ["e asm.arch=arm", "e asm.bits=64"] + name = "Capstone ARM disassembler" + + +class arm_gnu_16(_RizinBase): + arch_cmds = ["e asm.arch=arm.gnu", "e asm.bits=16"] + name = "Acorn RISC Machine CPU" + + +class arm_gnu_32(_RizinBase): + arch_cmds = ["e asm.arch=arm.gnu", "e asm.bits=32"] + name = "Acorn RISC Machine CPU" + + +class arm_gnu_64(_RizinBase): + arch_cmds = ["e asm.arch=arm.gnu", "e asm.bits=64"] + name = "Acorn RISC Machine CPU" + + +class arm_wine_16(_RizinBase): + arch_cmds = ["e asm.arch=arm.winedbg", "e asm.bits=16"] + name = "WineDBG's ARM disassembler" + + +class arm_wine_32(_RizinBase): + arch_cmds = ["e asm.arch=arm.winedbg", "e asm.bits=32"] + name = "WineDBG's ARM disassembler" class x86_16(_RizinBase): arch_cmds = ["e asm.arch=x86", "e asm.bits=16"] + + +class x86_32(_RizinBase): + arch_cmds = ["e asm.arch=x86", "e asm.bits=32"] + + +class x86_64(_RizinBase): + arch_cmds = ["e asm.arch=x86", "e asm.bits=64"] diff --git a/subdisassem/scripts.py b/subdisassem/scripts.py index 8e8b1bb..25381aa 100644 --- a/subdisassem/scripts.py +++ b/subdisassem/scripts.py @@ -111,7 +111,26 @@ def subdisassem_script(): session.commit() rizin_archs = [ + rizin_wrapper._6502_8, + rizin_wrapper._6502_16, + rizin_wrapper._8051, + rizin_wrapper.amd29k, + rizin_wrapper.arc_16, + rizin_wrapper.arc_32, + rizin_wrapper.arm_as_16, + rizin_wrapper.arm_as_32, + rizin_wrapper.arm_as_64, + rizin_wrapper.arm_16, + rizin_wrapper.arm_32, + rizin_wrapper.arm_64, + rizin_wrapper.arm_gnu_16, + rizin_wrapper.arm_gnu_32, + rizin_wrapper.arm_gnu_64, + rizin_wrapper.arm_wine_16, + rizin_wrapper.arm_wine_32, rizin_wrapper.x86_16, + rizin_wrapper.x86_32, + rizin_wrapper.x86_64, ] for arch in rizin_archs: