def test_MACHO_macho32_exe(assertion): global log_history macho_32 = open(__dir__ + 'macho_32.out', 'rb').read() macho_32_hash = hashlib.md5(macho_32).hexdigest() e = MACHO(macho_32) d = e.pack() assertion(macho_32_hash, hashlib.md5(d).hexdigest(), 'Packing after reading 32-bit Mach-O executable') assertion(e.entrypoint, 8000, 'entrypoint in a 32-bit Mach-O executable') assertion(e.virt.max_addr(), 16384, 'Maximum address in a 32-bit Mach-O executable') e.entrypoint = 8010 assertion(e.entrypoint, 8010, 'Changing entrypoint in a 32-bit Mach-O executable') e.entrypoint = 9000 assertion(e.entrypoint, 8010, 'Changing entrypoint with an invalid address') assertion([('error', ('Address %#x not mapped in memory', 9000), {})], log_history, 'Changing entrypoint with an invalid address (logs)') log_history = []
def test_MACHO_macho32_obj(assertion): global log_history # Parsing and modifying files macho_32 = open(__dir__ + 'macho_32.o', 'rb').read() macho_32_hash = hashlib.md5(macho_32).hexdigest() e = MACHO(macho_32) d = e.pack() assertion(macho_32_hash, hashlib.md5(d).hexdigest(), 'Packing after reading 32-bit Mach-O object') assertion(e.entrypoint, -1, 'No entrypoint in a Mach-O object') assertion([('error', ('Not a unique loader with entrypoint: []', ), {})], log_history, 'No entrypoint in a Mach-O object (logs)') assertion(len(e.symbols), 3, 'Number of symbols in a Mach-O object') d = ("\n".join([_.otool() for _ in e.symbols])).encode('latin1') assertion('9543b68138927d012139e526f159846c', hashlib.md5(d).hexdigest(), 'Display symbols') assertion( e.symbols['_printf'].otool(), '_printf NO_SECT UX 0x00000000 0000', 'Find symbol by name') assertion('SymbolNotFound', e.symbols[10].__class__.__name__, 'Find symbol by invalid index') e.symbols[0].sectionindex = 5 assertion( e.symbols[0].otool(), '_a INVALID(5) SX 0x00000000 0000', 'Display symbol with invalid section') e.symbols[0].sectionindex = 0xff assertion( e.symbols[0].otool(), '_a INVALID(255) SX 0x00000000 0000', 'Display symbol with too big section index') log_history = [] e.entrypoint = 0 assertion([('error', ('Not a unique loader with entrypoint: []', ), {})], log_history, 'Cannot set entrypoint in a Mach-O object (logs)') log_history = [] for s in e.sect.sect: if not hasattr(s, 'reloclist'): continue d = s.reloclist[0].pack() assertion('a8f95e95126c45ff26d5c838300443bc', hashlib.md5(d).hexdigest(), 'Not scattered relocation in a 32-bit Mach-O object') d = s.reloclist[2].pack() assertion('4f66fe3447267f2bf90da8108ef10ba6', hashlib.md5(d).hexdigest(), 'Scattered relocation in a 32-bit Mach-O object') break
def test_MACHO_fat(assertion): global log_history macho_fat = open(__dir__ + 'macho_fat.out', 'rb').read() macho_fat_hash = hashlib.md5(macho_fat).hexdigest() e = MACHO(macho_fat) d = e.pack() assertion(macho_fat_hash, hashlib.md5(d).hexdigest(), 'Packing after reading fat Mach-O') assertion(e.virt.max_addr(), -1, 'No unique maximum address in a Mach-O fat') assertion([('error', ('Not a unique memory mapping in Mach-O fat', ), {})], log_history, 'No unique maximum address in a Mach-O fat (logs)') log_history = [] assertion(e.entrypoint, -1, 'Many entrypoints in a fat Mach-O') assertion([('error', ('Not a unique entrypoint in Mach-O fat', ), {})], log_history, 'Many entrypoints in a fat Mach-O (logs)') log_history = [] e.entrypoint = 0 assertion([('error', ('Not a unique entrypoint in Mach-O fat', ), {})], log_history, 'Cannot set entrypoint directly in a fat Mach-O (logs)') log_history = []