afl-tmin creating new crashes from fuzzed inputs

240 views
Skip to first unread message

Filip Zarzyński

unread,
Nov 10, 2017, 11:51:14 AM11/10/17
to afl-...@googlegroups.com
Hi,

I recently stumbled upon results of running afl-tmin that I did not expect, I've
had ~1,5KB crashing input that got minimized (quiet fast I may add) to 10B, in
addition to minimization, tmining totally changed the execution path of that
input.

Instrumented binary was compiled with Clang and ASAN, before minimization it
ended on bad-free and after tmin it was global-buffer-overflow, also point of
crash, and trace where totally different

I mean, it's nice to have extra crash for free :) but still I decided to ping
you and share that effect, and ask if there is a way to run tmin in crash mode
so it would use instrumentation to preserve point of crash and maybe path

As I think about it it was predictable, as app has lot of crash points and tmin
crashing mode don't care about instrumentation and I know I can edit the app and
make it exit just before that bad-free if pointer is wild and use non-crashing
mode...  but I suppose it would be helpful not only to me to be able to minimize
different crashes on target that has them in different places out of the box.

FZ

PS:
Logs, if you care:

$ afl-tmin -t 10000 -m none -i ./bad_free -o bad_free_smaller ./app @@
afl-tmin 2.49b by <lca...@google.com>
[+] Read 1449 bytes from './bad_free'.
[*] Performing dry run (mem limit = 0 MB, timeout = 10000 ms)...
[+] Program exits with a signal, minimizing in crash mode.
[*] Stage #0: One-time block normalization...
[+] Block normalization complete, 1353 bytes replaced.
[*] --- Pass #1 ---
[*] Stage #1: Removing blocks of data...
    Block length = 128, remaining size = 1449
    Block length = 64, remaining size = 512
    Block length = 32, remaining size = 256
    Block length = 16, remaining size = 160
    Block length = 8, remaining size = 96
    Block length = 4, remaining size = 56
    Block length = 2, remaining size = 36
    Block length = 1, remaining size = 32
[+] Block removal complete, 1421 bytes deleted.
[*] Stage #2: Minimizing symbols (16 code points)...
[+] Symbol minimization finished, 4 symbols (4 bytes) replaced.
[*] Stage #3: Character minimization...
[+] Character minimization done, 1 byte replaced.
[*] --- Pass #2 ---
[*] Stage #1: Removing blocks of data...
    Block length = 1, remaining size = 28
[+] Block removal complete, 18 bytes deleted.
[*] Stage #2: Minimizing symbols (5 code points)...
[+] Symbol minimization finished, 0 symbols (0 bytes) replaced.
[*] Stage #3: Character minimization...
[+] Character minimization done, 0 bytes replaced.
[*] --- Pass #3 ---
[*] Stage #1: Removing blocks of data...
    Block length = 1, remaining size = 10
[+] Block removal complete, 0 bytes deleted.
 
     File size reduced by : 99.31% (to 10 bytes)
    Characters simplified : 13580.00%
     Number of execs done : 281
          Fruitless execs : path=137 crash=0 hang=0

[*] Writing output to 'bad_free_smaller'...
[+] We're done here. Have a nice day!


$ app ./bad_free
==18919==ERROR: AddressSanitizer: attempting free on address which was not
malloc()-ed: 0x00490000f100 in thread T0
[...]
Address 0x00490000f100 is a wild pointer.
SUMMARY: AddressSanitizer: bad-free (app+0x4dead)
==18919==ABORTING
Aborted

$ app ./bad_free_smaller
==18920==ERROR: AddressSanitizer: global-buffer-overflow on address
0x000000504657 at pc [...]
READ of size 1 at 0x000000504657 thread T0
[...]
0x000000504657 is located 9 bytes to the left of global variable [...] of size 16
0x000000504657 is located 119 bytes to the right of global variable[...] of size 512
SUMMARY: AddressSanitizer: global-buffer-overflow (app+0x4beaf)
[...]
==18920==ABORTING
Aborted

sorry for log obfuscation and not giving a sample but I work on closed-source ;/

FZ

--

- Filip Zarzyński

Jakub Wilk

unread,
Nov 10, 2017, 12:29:39 PM11/10/17
to afl-...@googlegroups.com
* Filip Zarzyński <filipza...@gmail.com>, 2017-11-10, 17:51:
>Instrumented binary was compiled with Clang and ASAN, before
>minimization it ended on bad-free and after tmin it was
>global-buffer-overflow, also point of crash, and trace where totally
>different
>
>I mean, it's nice to have extra crash for free :) but still I decided
>to ping you and share that effect, and ask if there is a way to run
>tmin in crash mode so it would use instrumentation to preserve point of
>crash and maybe path

Changelog for 2.49b says:

- Added AFL_TMIN_EXACT to allow path constraint for crash minimization.

See also this thread, which discusses alternatives:
https://groups.google.com/d/topic/afl-users/INyc3thzoiQ

For ASAN-ed binaries, I usually do something like this:

afl-tmin ... -- sh -c 'frobnicate @@ 2>&1 | grep -w bad-free && kill $$'

--
Jakub Wilk
Reply all
Reply to author
Forward
0 new messages