Battelle / afl-unicorn

afl-unicorn lets you fuzz any piece of binary that can be emulated by Unicorn Engine.

Home Page:https://medium.com/@njvoss299/afl-unicorn-fuzzing-arbitrary-binary-code-563ca28936bf

Geek Repo:Geek Repo

Github PK Tool:Github PK Tool

ERROR: Failed to execute a single instruction (error: Unhandled CPU exception (UC_ERR_EXCEPTION))!

yuroc0598 opened this issue · comments

commented

Hi, I installed afl-unicorn and the sample tests work perfectly. However, when I run afl-unicorn on a arm busybox that require dynamic loaded libraries, I got this error: ERROR: Failed to execute a single instruction (error: Unhandled CPU exception (UC_ERR_EXCEPTION))!

My question is can afl-unicorn work with arm binaries that require dynamic loaded libraries? Thank you in advance.

Afl-unicorn will work with dynamically loaded libraries, but only if your Unicorn script handles the loading. This is where taking a process-memory snapshot would make everything much, much easier.

Keep in mind that Unicorn only has the context and content of memory that you provide to it. This includes the mapped memory ranges and the content of them. Unicorn merely executes assembly instructions based and updates memory and registers as directed by the instructions. Any instruction which interacts with requires that that memory is already mapped. In the case of dynamically loaded libraries, this typically occurs in the kernel itself via system calls. You must emulate or otherwise bypass this process in order for Unicorn to know what to do.

Long story short, yes, afl-unicorn can handle this, but it's up to you to make it work. By far the easiest thing to do is going to be to take a full process memory snapshot after the libraries are loaded, and then have afl-unicorn only emulate the smallest section of code possible that is required to fuzz interesting functionality. In a perfect world, attach a debugger to the target process, set a breakpoint at the entry point of where you want to start fuzzing, and dump the memory via the debugger.

If taking a run-time process memory snapshot is not possible, then you will need to hook the underlying functions which dynamically load the library and replace them with Unicorn-based code which emulates them (aka map memory, load the desired library binary into that mapped region, fixup dynamic links, etc.). This will also end up being dramatically slower during fuzzing, as you will be executing way more code than you need to to fuzz the interesting parts.

Good luck!

commented

Cool! Thanks for the detailed reply, Nathan. I read this post written by you and tried to follow the steps. However, I couldn't get the armel program binary running on ubuntu. I tried gdb-multiarch but got cored dumped right after the "run" command was issued in gdb. Did I miss anything about the dumping the running process ?

######$ gdb-multiarch ./busybox
.....
Reading symbols from ./busybox...(no debugging symbols found)...done.
gef➤ set arch arm
The target architecture is assumed to be arm
gef➤ r
Starting program: XXXX/bin/busybox
warning: Selected architecture arm is not compatible with reported target architecture i386:x86-64
warning: Architecture rejected target-supplied description
/build/gdb-GT4MLW/gdb-8.1/gdb/i387-tdep.c:924: internal-error: void i387_supply_xsave(regcache*, int, const void*): Assertion `tdep->st0_regnum >= I386_ST0_REGNUM' failed.
A problem internal to GDB has been detected,
further debugging may prove unreliable.

This is a bug, please report it. For instructions, see:
http://www.gnu.org/software/gdb/bugs/.

Aborted (core dumped)

Thank you again for your help!