about summary refs log tree commit diff
diff options
context:
space:
mode:
authorllzmb <46303940+llzmb@users.noreply.github.com>2021-11-24 13:30:00 +0100
committerllzmb <46303940+llzmb@users.noreply.github.com>2021-11-24 13:30:00 +0100
commit4f1310db5171ed52660d664551005f305f22a29d (patch)
tree56f387f5fb52cdad2d1dcccd6cbbfc1c579a3401
parent6cce577b907eb2ac58b0bc5ddacf373627b3480f (diff)
downloadafl++-4f1310db5171ed52660d664551005f305f22a29d.tar.gz
Edit instrumentation READMEs
-rw-r--r--instrumentation/README.gcc_plugin.md84
-rw-r--r--instrumentation/README.persistent_mode.md7
2 files changed, 7 insertions, 84 deletions
diff --git a/instrumentation/README.gcc_plugin.md b/instrumentation/README.gcc_plugin.md
index 33cf1c33..f251415b 100644
--- a/instrumentation/README.gcc_plugin.md
+++ b/instrumentation/README.gcc_plugin.md
@@ -87,89 +87,13 @@ reports to afl@aflplus.plus.
 
 ## 4) Bonus feature #1: deferred initialization
 
-AFL++ tries to optimize performance by executing the targeted binary just once,
-stopping it just before `main()`, and then cloning this "main" process to get a
-steady supply of targets to fuzz.
-
-Although this approach eliminates much of the OS-, linker- and libc-level costs
-of executing the program, it does not always help with binaries that perform
-other time-consuming initialization steps - say, parsing a large config file
-before getting to the fuzzed data.
-
-In such cases, it's beneficial to initialize the forkserver a bit later, once
-most of the initialization work is already done, but before the binary attempts
-to read the fuzzed input and parse it; in some cases, this can offer a 10x+
-performance gain. You can implement delayed initialization in GCC mode in a
-fairly simple way:
-
-First, locate a suitable location in the code where the delayed cloning can take
-place. This needs to be done with *extreme* care to avoid breaking the binary.
-In particular, the program will probably malfunction if you select a location
-after:
-
-- The creation of any vital threads or child processes - since the forkserver
-  can't clone them easily.
-
-- The initialization of timers via `setitimer()` or equivalent calls.
-
-- The creation of temporary files, network sockets, offset-sensitive file
-  descriptors, and similar shared-state resources - but only provided that their
-  state meaningfully influences the behavior of the program later on.
-
-- Any access to the fuzzed input, including reading the metadata about its size.
-
-With the location selected, add this code in the appropriate spot:
-
-```c
-#ifdef __AFL_HAVE_MANUAL_CONTROL
-  __AFL_INIT();
-#endif
-```
-
-You don't need the #ifdef guards, but they will make the program still work as
-usual when compiled with a compiler other than afl-gcc-fast/afl-clang-fast.
-
-Finally, recompile the program with afl-gcc-fast (afl-gcc or afl-clang will
-*not* generate a deferred-initialization binary) - and you should be all set!
+See
+[README.persistent_mode.md#3) Deferred initialization](README.persistent_mode.md#3-deferred-initialization).
 
 ## 5) Bonus feature #2: persistent mode
 
-Some libraries provide APIs that are stateless or whose state can be reset in
-between processing different input files. When such a reset is performed, a
-single long-lived process can be reused to try out multiple test cases,
-eliminating the need for repeated `fork()` calls and the associated OS overhead.
-
-The basic structure of the program that does this would be:
-
-```c
-  while (__AFL_LOOP(1000)) {
-
-    /* Read input data. */
-    /* Call library code to be fuzzed. */
-    /* Reset state. */
-
-  }
-
-  /* Exit normally. */
-```
-
-The numerical value specified within the loop controls the maximum number of
-iterations before AFL++ will restart the process from scratch. This minimizes
-the impact of memory leaks and similar glitches; 1000 is a good starting point.
-
-A more detailed template is shown in ../utils/persistent_mode/. Similarly to the
-previous mode, the feature works only with afl-gcc-fast or afl-clang-fast;
-#ifdef guards can be used to suppress it when using other compilers.
-
-Note that as with the previous mode, the feature is easy to misuse; if you do
-not reset the critical state fully, you may end up with false positives or waste
-a whole lot of CPU power doing nothing useful at all. Be particularly wary of
-memory leaks and the state of file descriptors.
-
-When running in this mode, the execution paths will inherently vary a bit
-depending on whether the input loop is being entered for the first time or
-executed again. To avoid spurious warnings, the feature implies
-`AFL_NO_VAR_CHECK` and hides the "variable path" warnings in the UI.
+See
+[README.persistent_mode.md#4) Persistent mode](README.persistent_mode.md#4-persistent-mode).
 
 ## 6) Bonus feature #3: selective instrumentation
 
diff --git a/instrumentation/README.persistent_mode.md b/instrumentation/README.persistent_mode.md
index d0ccba8c..14e59f4a 100644
--- a/instrumentation/README.persistent_mode.md
+++ b/instrumentation/README.persistent_mode.md
@@ -164,10 +164,9 @@ you do not fully reset the critical state, you may end up with false positives
 or waste a whole lot of CPU power doing nothing useful at all. Be particularly
 wary of memory leaks and of the state of file descriptors.
 
-PS. Because there are task switches still involved, the mode isn't as fast as
-"pure" in-process fuzzing offered, say, by LLVM's LibFuzzer; but it is a lot
-faster than the normal `fork()` model, and compared to in-process fuzzing,
-should be a lot more robust.
+When running in this mode, the execution paths will inherently vary a bit
+depending on whether the input loop is being entered for the first time or
+executed again.
 
 ## 5) Shared memory fuzzing