AFL Overview


  1. 1. Introduction
  2. 2. Model
  3. 3. fuzzing-binaries-without-execve
  4. 4. write_to_testcase
  5. 5. fuzz_one
  6. 6. Document
  7. 7. Mutations
  8. 8. Related Work



technical whitepaper

AFL is a mutational, coverage guided fuzzer. It mutates a set of test cases (seed) to reach previously unexplored points in the program. When this happens, the test case triggering a new coverage is saved as part of the test case queue.

the overall algorithm can be summed up as:

  1. Load user-supplied initial test cases into the queue,
  2. Take next input file from the queue,
  3. Attempt to trim the test case to the smallest size that doesn’t alter the measured behavior of the program,
  4. Repeatedly mutate the file using a balanced and well-researched variety of traditional fuzzing strategies,
  5. If any of the generated mutations resulted in a new state transition recorded by the instrumentation, add mutated output as a new entry in the queue.
  6. Go to 2.

afl-cmin & afl-tmin: They can be used for test case and test corpus minimization. This can be useful when the test cases generated by afl-fuzz would be used by other fuzzers.




It is an embedding fork server with less overhead.


Write modified data to file for testing. If out_file is set, the old file is unlinked and a new one is created. Otherwise, out_fd is rewound and truncated.


abandon_entry: exception happens.

break 7 if buf[0] == 'h'  -- afl-fuzz.c:6



Interpreting output:

Fuzzer dictionaries:

By default, afl-fuzz mutation engine is optimized for compact data formats - say, images, multimedia, compressed data, regular expression syntax, or shell scripts. It is somewhat less suited for languages with particularly verbose and redundant verbiage - notably including HTML, SQL, or JavaScript.

It needs relevant input data to keep high performance.


There are some unfortunate trade-offs with ASAN and 64-bit binaries.


The mutations of AFL are divided into two categories: deterministic and havoc (indeterministic).