#![feature(core_intrinsics)]
use std::intrinsics::abort;
use std::io::{self, Read};
use std::panic::{self, UnwindSafe};
#[cfg(not(test))]
#[link(name="afl-llvm-rt", kind="static")]
extern "C" {
fn __afl_manual_init();
}
#[cfg(not(test))]
pub unsafe fn init() {
__afl_manual_init();
}
pub fn handle_bytes<F>(closure: F)
where F: FnOnce(Vec<u8>) + UnwindSafe
{
let mut input = vec![];
let result = io::stdin().read_to_end(&mut input);
if result.is_err() {
return;
}
let result = panic::catch_unwind(|| {
closure(input);
});
if result.is_err() {
unsafe {
abort();
}
}
}
pub fn handle_string<F>(closure: F)
where F: FnOnce(String) + UnwindSafe
{
let mut input = String::new();
let result = io::stdin().read_to_string(&mut input);
if result.is_err() {
return;
}
let result = panic::catch_unwind(|| {
closure(input);
});
if result.is_err() {
unsafe {
abort();
}
}
}
pub fn handle_read<F>(closure: F)
where F: FnOnce(io::Stdin) + UnwindSafe
{
let result = panic::catch_unwind(|| {
closure(io::stdin());
});
if result.is_err() {
unsafe {
abort();
}
}
}
#[cfg(test)]
mod test {
use std::process::{Command, Stdio};
use std::thread;
use std::time;
extern crate libc;
extern crate tempdir;
#[test]
fn test_cargo_afl_fuzz() {
let temp_dir = tempdir::TempDir::new("aflrs").expect("Could not create temporary directory");
let temp_dir_path = temp_dir.path();
let mut child = Command::new("target/debug/cargo-afl-fuzz")
.stdout(Stdio::inherit())
.stderr(Stdio::inherit())
.arg("-i")
.arg(".")
.arg("-o")
.arg(temp_dir_path)
.arg("target/debug/examples/hello")
.spawn()
.expect("Could not run cargo-afl-fuzz");
thread::sleep(time::Duration::from_secs(7));
child.kill().unwrap();
assert!(temp_dir_path.join("fuzzer_stats").is_file());
}
}