This package allows you to find bugs in Rust code using american-fuzzy-lop.
This was performed on one core of an i7-4790K at 4.8 GHz. The code under
test is examples/hello.rs
in this repository.
First, add this project as a Cargo dependency:
[dependencies.afl-coverage-plugin]
git = "https://github.com/kmcallister/afl.rs"
[dependencies.afl-coverage]
git = "https://github.com/kmcallister/afl.rs"
Then you can add afl instrumentation to one or more crates:
#![feature(plugin)]
#![plugin(afl_coverage_plugin)]
You will also need a test executable that exercises the instrumented functions,
in a deterministic way based on input from stdin. This executable should link
the afl_coverage
run-time library:
extern crate afl_coverage;
This will produce a binary that you can pass to afl-fuzz
in the usual manner.
afl instrumentation adds some run-time overhead, so it's a good candidate for
conditional compilation, perhaps through a Cargo feature.
To look for logic errors in safe Rust code, set AFL_RS_CRASH_ON_PANIC=1
in
the environment when you invoke afl-fuzz
. This causes the fuzzer to treat any
Rust panic as a crash.
If your program has a slow set-up phase that does not depend on the input data,
you can set AFL_DEFER_FORKSRV=1
for a substantial speed-up, provided that you
insert a call to afl_coverage::init()
after the set-up and before any
dependence on input. There are various other caveats, described in the section
"Bonus feature: deferred instrumentation" in llvm_mode/README.llvm
distributed with afl. See also examples/deferred-init.rs
in
this repository.
See the afl documentation for other configuration variables. Some of these are
set at compile time in config.h
. For the most part they only affect
afl-fuzz
itself, and will work fine with this library. However, if you change
SHM_ENV_VAR
, MAP_SIZE
, or FORKSRV_FD
, you should update this library's
src/config.h
to match.
afl.rs
needs to compile against a version of LLVM that matches rustc
's. The
easy solution (if you can wait on a slow build) is to build rustc
from
source and put it in your PATH
. Then afl.rs
's build
script will find llvm-config
automatically. Otherwise, the environment
variable LLVM_CONFIG
should hold the path to llvm-config
when you build
afl.rs
.
It does not require clang++
; it will use CXX
with a fallback to g++
.
Your C++ compiler must support C++11.
- httparse: #9
- image: #414
- rustc: #24275, #24276
- rust-url: #108
- regex: #84
- rustc-serialize: #109, #110
- serde: #75, #77, #82
- tar-rs: #23
- xml-rs: #93
- Logic errors in tendril and its html5ever integration
These bugs aren't nearly as serious as the memory-safety issues afl has
discovered in C and C++ projects.
That's because Rust is memory-safe by default, but also because not many people
have tried afl.rs yet! Over time we will update this section with the most
interesting bugs, whether they're logic errors or memory-safety problems
arising from unsafe
code. Pull requests are welcome!