solve (3326B)
1#!/usr/bin/env python3 2 3import angr 4import claripy 5import logging 6import subprocess 7import cle 8 9try: 10 import binaryninja 11except: 12 pass 13 14check1 = b"A@F01" 15check2 = b"\xc56i9\xf4j\x0fk\xc4L\xfa\xd3\x8f\x99\xc0\xce" 16check2_rev = b"00GHK-L1MNS" # from cracked md5 hash 17 18def checkpoint(sim, find, text, **kwargs): 19 while len(sim.active) > 0: 20 sim.explore(find=find, **kwargs, step_func=step_func) 21 print(text, sim) 22 assert(len(sim.found) > 0) 23 sim.stash(from_stash="found", to_stash="active") 24 25def step_func(sim): 26 if sim.active != [] and bv != None: 27 for state in sim.active: 28 for bb in bv.get_basic_blocks_at(state.solver.eval(state.regs.rip)): 29 bb.set_user_highlight(binaryninja.HighlightStandardColor.MagentaHighlightColor) 30 sim.drop(stash="avoid") 31 32 print(sim.active) 33 34 35def run(_bv=None): 36 global bv 37 bv = _bv 38 39 logging.getLogger('angr.sim_manager').setLevel(logging.DEBUG) 40 41 key = [claripy.BVS(f"key_{i}", 8) for i in range(29)] + [b"\x00"] 42 43 cmd = ["gdb", "-ex", "b *0x402030", "-ex", "run", 44 "-ex", "gcore core.dump", "-ex", "exit", "--batch", 45 "--args", "./licensecheck", "12345-12345-12345-12345-12345"] 46 subprocess.run(cmd) 47 48 project = angr.Project("core.dump", main_opts={"backend": "elfcore"}, 49 rebase_granularity=0x1000) 50 binfile = angr.SimFile("licensecheck", open("licensecheck", "rb").read()) 51 state = project.factory.blank_state(fs={"licensecheck": binfile}) 52 53 elfcore = None 54 for o in project.loader.all_objects: 55 if type(o) == cle.backends.elf.elfcore.ELFCore: 56 elfcore = o 57 break 58 assert(elfcore is not None) 59 60 for reg in elfcore.initial_register_values(): 61 try: 62 setattr(state.regs, reg[0], reg[1]) 63 except Exception as e: 64 print("skip-reg", e) 65 66 state.memory.store(state.solver.eval(state.regs.rdi), claripy.Concat(*key)) 67 68 for i in range(29): 69 if i >= 18: 70 state.solver.add(key[i] == check2_rev[i-18]) 71 elif (i + 1) % 6 == 0: 72 state.solver.add(key[i] == ord(b'-')) 73 else: 74 isalpha = claripy.And(key[i] >= ord('A'), key[i] <= ord('Z')) 75 isnum = claripy.And(key[i] >= ord('0'), key[i] <= ord('9')) 76 state.solver.add(claripy.Or(isalpha, isnum)) 77 78 # plt sim hooks 79 project.hook(0x4010e0, angr.SIM_PROCEDURES["libc"]["strncpy"]()) 80 project.hook(0x4010f0, angr.SIM_PROCEDURES["libc"]["memcmp"]()) 81 project.hook(0x401140, angr.SIM_PROCEDURES["libc"]["strcmp"]()) 82 project.hook(0x401190, angr.SIM_PROCEDURES["libc"]["strlen"]()) 83 84 # libc hooks 85 project.hook(0x40ce40, angr.SIM_PROCEDURES["libc"]["fopen"]()) 86 project.hook(0x40cf40, angr.SIM_PROCEDURES["libc"]["fread"]()) 87 project.hook(0x40d040, angr.SIM_PROCEDURES["libc"]["puts"]()) 88 89 sim = project.factory.simgr(state) 90 checkpoint(sim, 0x402092, "start of loop", avoid=0x4020cb) 91 92 for state in sim.active: 93 state.regs.rip = 0x4020d0 94 95 checkpoint(sim, 0x40245c, "after check1", avoid=0x4020cb) 96 checkpoint(sim, 0x4024aa, "after check2", avoid=0x4020cb) 97 checkpoint(sim, 0x4016ed, "final", avoid=0x4016ec) 98 print(sim.active[0].solver.eval_upto(claripy.Concat(*key), cast_to=bytes, n=2)) 99 100if __name__ == "__main__": 101 run()