def __init__(self, infile, cache=False, cfg_options=None, debugangr=False): self.infile = infile self.error = False self._stack_patch_data = [] self.stack_increases = {} if cfg_options is None: cfg_options = {} cachename = infile + '.fcfg' l.info("Loading %s", infile) try: if not cache: raise IOError('f**k off') fh = open(cachename, 'rb') self.project, self.cfg = pickle.load(fh) self.cfg.project = self.project fh.close() except (IOError, OSError, pickle.UnpicklingError): if debugangr: import ipdb ipdb.set_trace() self.project = Project(infile, load_options={'auto_load_libs': False}) self.cfg = self.project.analyses.CFGFast(**cfg_options) try: fh = open(cachename, 'wb') pickle.dump((self.project, self.cfg), fh, -1) fh.close() except (IOError, OSError, pickle.PicklingError): l.exception('Error pickling CFG')
def test_initial_allocation(): # not strictly about alignment but it's about stack initialization so whatever p = Project(os.path.join(os.path.dirname(__file__), '../../binaries/tests/x86_64/true'), auto_load_libs=False) s = p.factory.entry_state(add_options={o.STRICT_PAGE_ACCESS}) s.memory.load(s.regs.sp - 0x10000, 4)
def init_project(): project = Project( thing=INSTR_BIN, ignore_functions=['printf', '__trace_jump', '__trace_jump_set']) entry = project.factory.entry_state(stdin=SimFileStream) simgr = project.factory.simulation_manager(entry) simgr.use_technique(DFS()) return simgr
def solve(): ''' Function Solve: 1. Create the angr project 2. Remove Lazy Solves 3. Set up command line arguments 4. Explore 5. Print flag from found path Python v2.7.12 angr v7.7.9.8.post1 Performance: Pylint score: 10/10 Runtime: ~6 seconds ''' # Create the angr project proj = Project('./challenge', load_options={"auto_load_libs": False}) initial_state = proj.factory.entry_state() # Discard lazy solves to speed up angr initial_state.options.discard("LAZY_SOLVES") # Program wants 31 command line arguments # The first argument is the program: ./challenge # The rest or the arguments are each one byte of the flag argument_list = ['./challenge'] for i in range(0, 30): argument_list.append(BVS("argv{}".format(i), 8)) # Pass arguments to program initial_state = proj.factory.entry_state(args=argument_list) # Create the path group path_group = proj.factory.simgr(initial_state) # Address of call to sym.success__ in main. successAddress = 0x400c70 # Find a path to the desired address path_group.explore(find=successAddress) # Get first found path found = path_group.found[0] # For every argument find the value used in the path flag = "" for arg in argument_list[1:]: flag += found.state.se.eval(arg, cast_to=str) # Print the result print flag
def test_struct_ffi(self): with open(os.path.join(test_location, '../tests_src/test_structs.c')) as fp: decls = parse_file(fp.read()) p = Project(os.path.join(test_location, 'x86_64/test_structs.o'), auto_load_libs=False) def make_callable(name): return p.factory.callable(p.loader.find_symbol(name).rebased_addr, decls[0][name]) test_small_struct_return = make_callable('test_small_struct_return') result = test_small_struct_return() self.assertIsInstance(result, SimStructValue) self.assertTrue((result.a == 1).is_true()) self.assertTrue((result.b == 2).is_true())
def explore(): project = Project( thing=UNINSTR_BIN, ignore_functions=['printf', '__trace_jump', '__trace_jump_set']) entry = project.factory.entry_state(stdin=SimFileStream) symex_paths_gen = my_symex_rec(entry, [entry]) symex_paths = [symex_path for symex_path in symex_paths_gen] global SIMPOOL SIMPOOL = Pool(processes=CORE) if (CORE > 1 and not SIMPOOL) else None if SIMPOOL: conex_paths = SIMPOOL.map(enumerate_path, symex_paths) else: conex_paths = [ enumerate_path(symex_path) for symex_path in symex_paths ] return len(conex_paths)
def __init__(self, project, cfg, trace, hooked_symbol, gdb): # type: (Project, CFGFast, List[Branch], Dict[str, SimProcedure], Any) -> None self.project = project self.main_cfg = cfg.copy() self.main_object = project.loader.main_object self.trace = trace self.hooked_symbol = hooked_symbol self.new_trace = [] # type: List[Branch] self.gdb = gdb self.omitted_symbol = hooked_symbol self.omitted_section = [] # type: List[Tuple[int, int]] # self.analyze_unsupported() self.cfgs = {} # type: Dict[Any, CFGFast] self.libc_object = None for lib in self.project.loader.all_elf_objects: # FIXME: not a good way if lib.get_symbol('__libc_memalign'): self.libc_object = lib if lib != self.project.loader.main_object: self.cfgs[lib] = Project( lib.binary, load_options={ "auto_load_libs": False }, show_progressbar=True).analyses.CFGFast() else: self.cfgs[lib] = self.main_cfg # HACK: weirdly, these functions in glibc are plt stubs resolved to self self.libc_special_name = { 'malloc': ('__libc_malloc', 0x484130), 'calloc': ('__libc_calloc', 0x484d10), 'realloc': ('__libc_realloc', 0x4846c0), 'free': ('__libc_free', 0x4844f0), 'memalign': ('__libc_memalign', 0x1019e00) } self.analyze_hook()
def angr_project(self) -> Project: return Project(self.executable, **self.load_options())
def __init__(self, angr_args): self.b = Project(angr_args[0], **angr_args[1])
from angr import Project, SimProcedure from angr import sim_options as so import libc ##### constraint ##### # 1. have symbol # 2. have win function [system('/bin/sh')] # 3. pie disable # 4. dynamic loading libc project = Project('../challenges/tcache_dup') #project.hook_symbol('malloc', libc.fakeMalloc()) #project.hook_symbol('free', libc.fakeFree()) extras = {so.REVERSE_MEMORY_NAME_MAP, so.TRACK_ACTION_HISTORY} es = project.factory.entry_state(add_options=extras) print(f'entry_state: {es}') simgr = project.factory.simulation_manager(es, save_unconstrained=True) #simgr.run() def overflow_filter(simgr): print(simgr) if len(simgr.unconstrained) > 0: print("[+] found some unconstrained states, checking exploitability") for state in simgr.unconstrained: eip = state.regs.pc bits = state.arch.bits state_copy = state.copy() print(f'eip: {eip}') print(f'bits: {bits}')
from angr import Project import angrop import sys from io import StringIO from multiprocessing import cpu_count binary = sys.argv[1] ropchain_path = sys.argv[2] project = Project(binary) rop = project.analyses.ROP() rop.find_gadgets(processes=cpu_count(), show_progress=False) chain = rop.execve(b"/bin/sh\x00") script_path = "{}.angrop.script".format(binary) with open(script_path, 'w') as script: stdout = sys.stdout sys.stdout = StringIO() chain.print_payload_code() output = sys.stdout.getvalue() sys.stdout = stdout script.write(output) with open(ropchain_path, 'wb') as ropchain_f: payload = chain.payload_str() ropchain_f.write(payload)
from angr import Project import claripy SUCCESS = 0x001046dd FAIL = 0x001046eb BASE_ADDR = 0x100000 FLAG_LEN = 200 STDIN_FD = 0 prj = Project('./rev', main_opts={'base_addr': BASE_ADDR}) flag_chars = [claripy.BVS(f'flag_{_}', 8) for _ in range(FLAG_LEN)] flag = claripy.Concat(*flag_chars + [claripy.BVV('\n', 8)]) state = prj.factory.full_init_state(stdin=flag) for _ in flag_chars: state.solver.add(_ >= ord('!')) state.solver.add(_ <= ord('~')) simgr = prj.factory.simulation_manager(state) simgr.explore(find=SUCCESS, avoid=FAIL) print(f'[+] Found: {len(simgr.found)}') if len(simgr.found) > 0: for _ in simgr.found: print(_.posix.dumps(STDIN_FD))