예제 #1
0
def apply_external_simprocs():
    objs = get_objects(angrgdb.load_project())
    for o in objs:
        l.info("Applying simprocs to " + o)
        try:
            p = angr.Project(o,
                             main_opts={
                                 'base_addr': objs[o][0],
                                 'force_rebase': True
                             },
                             load_options={"auto_load_libs": False})
            process_got(p)
        except Exception as ee:
            l.warning("Failed to apply simprocs to " + o + ": " + str(ee))
    process_got(angrgdb.load_project())
예제 #2
0
def process_got(proj):
    debugger = angrgdb.get_debugger()
    target_proj = angrgdb.load_project()

    got_start, got_end = get_got(proj)
    plt_start, plt_end = get_plt(proj)

    entry_len = proj.arch.bits // 8
    get_mem = debugger.get_dword if entry_len == 4 else debugger.get_qword

    got_start += 3 * entry_len  # skip first 3 entries
    empty_state = proj.factory.blank_state()

    for a in range(got_start, got_end, entry_len):
        state_val = empty_state.solver.eval(
            getattr(empty_state.mem[a], "uint%d_t" % proj.arch.bits).resolved)

        if state_val in proj._sim_procedures:
            dbg_val = get_mem(a)
            name = proj._sim_procedures[state_val].display_name

            if proj._sim_procedures[state_val].is_stub:
                l.debug("Skipping re-hooking of %s cause is a stub" % name)
            elif not target_proj.is_hooked(dbg_val):
                l.info("Re-hooking %s (got: 0x%x) to 0x%x" %
                       (name, a, dbg_val))
                target_proj.hook_symbol(dbg_val,
                                        proj._sim_procedures[state_val])
예제 #3
0
 def _driller_init_bounds(self):
     project = angrgdb.load_project()
     if self.cfg is None:
         self.cfg = project.analyses.CFGFast()
     begin = 0xffffffffffffffff
     end = 0
     for bb in project.kb.functions["driller_init"].graph:
         begin = min(begin, bb.addr)
         end = max(end, bb.addr + bb.size)
     return begin, end
예제 #4
0
 def main_return_blocks(self):
     if self._main_returns is None:
         project = angrgdb.load_project()
         if self.cfg is None:
             self.cfg = project.analyses.CFGFast()
         self._main_returns = set()
         for bb in project.kb.functions["main"].blocks:
             for i in bb.capstone.insns:
                 if i.mnemonic == "ret":
                     self._main_returns.add(bb.addr)
     return self._main_returns
예제 #5
0
    def _drill_input(self):
        """
        Symbolically step down a path with a tracer, trying to concretize inputs for unencountered
        state transitions.
        """

        p = angrgdb.load_project()

        trace, crash_addr = self.runner.tracer(self.input)
        start_addr = self.runner.get_start_addr(trace)

        for bb in self.runner.main_return_blocks():
            try:
                idx = trace.index(bb)
            except ValueError:
                continue
            trace = trace[:idx + 1]

        for addr, proc in self._hooks.items():
            p.hook(addr, proc)
            l.debug("Hooking %#x -> %s...", addr, proc.display_name)

        s = angrgdb.StateShot(sync_brk=False,
                              concrete_imports=self.exclude_simprocs,
                              stdin=angr.SimFileStream)

        if self.zero_fill:
            s.options.add(angr.options.ZERO_FILL_UNCONSTRAINED_MEMORY)
            s.options.add(angr.options.ZERO_FILL_UNCONSTRAINED_REGISTERS)

        if self.sync_brk:  # don't use angrdbg brk but ask for it to the runner
            s.posix.set_brk(s.solver.BVV(self.runner.brk(), p.arch.bits))
        if self.sync_fs:
            s.regs.fs = self.runner.fs()
        s.regs.rax = 0xabadcafe  #flag for exit driller_init

        s.preconstrainer.preconstrain_file(self.input, s.posix.stdin,
                                           self.stdin_bound)

        simgr = p.factory.simulation_manager(s,
                                             save_unsat=True,
                                             hierarchy=False,
                                             save_unconstrained=True)

        start_addr = self.runner.get_start_addr(trace)

        t = Tracer(start_addr, trace=trace, crash_addr=crash_addr)
        self._core = DrillerCore(trace=trace, fuzz_bitmap=self.fuzz_bitmap)

        simgr.use_technique(t)
        simgr.use_technique(angr.exploration_techniques.Oppologist())
        simgr.use_technique(self._core)

        self._set_concretizations(simgr.one_active)

        l.info("Drilling into %r.", self.input)
        l.debug("Input is %r.", self.input)

        start_addr_idx = trace.index(start_addr)
        with progressbar.ProgressBar(max_value=(len(trace) -
                                                start_addr_idx)) as bar:
            while simgr.active and simgr.one_active.globals['trace_idx'] < len(
                    trace) - 1:
                simgr.step()
                #print("RIP", simgr.one_active.regs.rip)
                #print("TRACE", simgr.one_active.globals['trace_idx'], hex(trace[simgr.one_active.globals['trace_idx']]))
                bar.update(simgr.one_active.globals['trace_idx'] -
                           start_addr_idx)
                l.debug("stepped to " + str(simgr.one_active.regs.rip))

                if len(simgr.unconstrained) > 0:
                    while len(simgr.unconstrained) > 0:
                        state = simgr.unconstrained.pop(0)
                        l.debug(
                            "Found a unconstrained state, exploring to some extent."
                        )
                        w = self._writeout(state.history.bbl_addrs[-1], state)
                        if w is not None:
                            yield w

                # Check here to see if a crash has been found.
                if self.redis and self.redis.sismember(
                        self.identifier + '-finished', True):
                    return

                if 'diverted' not in simgr.stashes:
                    continue

                while simgr.diverted:
                    state = simgr.diverted.pop(0)
                    l.debug(
                        "Found a diverted state, exploring to some extent.")
                    w = self._writeout(state.history.bbl_addrs[-1], state)
                    if w is not None:
                        yield w
                    if self.explore_found:
                        for i in self._symbolic_explorer_stub(state):
                            yield i