[PATCH] tests: integrate fuzz-dwfl-core into elfutils

Mark Wielaard mark@klomp.org
Fri Dec 17 10:46:50 GMT 2021

Hi Evgeny,

On Sun, Dec 12, 2021 at 03:16:58PM +0000, Evgeny Vereshchagin via Elfutils-devel wrote:
> The fuzz target was integrated into OSS-Fuzz in
> https://github.com/google/oss-fuzz/pull/6944 and since then it
> has been running there continously (uncovering various issues
> along the way). It's all well and good but since OSS-Fuzz
> is far from the elfutils repository it's unnecessarily hard
> to build the fuzz target locally, verify patches and more generally
> test new code to make sure that it doesn't introduce new issues (
> or reintroduce regressions). This patch aims to address all those
> issues by moving the fuzz target into the elfutils repository,
> integrating it into the testsuite and also providing a script
> that can be used to build full-fledged fuzzers utilizing libFuzzer.
> With this patch applied `make check` can be used to make sure
> that files kept in tests/fuzz-dwfl-core-corpus don't crash the
> code on various architecures.
> `--enable-sanitize-{address,undefined}` and/or `--enable-valgrind`
> can additionally be used to uncover issues like
> https://sourceware.org/bugzilla/show_bug.cgi?id=28685
> that don't always manifest themselves in simple segfaults. On top
> of all that now the fuzz target can be built and linked against
> libFuzzer locally by just running `./tests/build-fuzzers.sh`.

I like the general idea of this. I have been using src/stack as fuzz
target locally, but that is not ideal since it does too much. Having
specific fuzz target binaries is much better. I also like the idea of
making those fuzz-targets into regular testsuite targets. I am still
trying to wrap my head around the LLVMFuzzerTestOneInput and libfuzzer
requirements. I have experience with afl and honggfuzz which don't
have any external library requirement.

Also the LLVMFuzzerTestOneInput seems backwards. Shouldn't there be a
more generic name for a function that is called by a fuzzer? Maybe it
seems upside down because you translate from data stream to byte array
and back and then read in the reconstructed stream again. Once you
have the bytes you can simply call Elf *elf_memory (char *__image,
size_t __size), There is no need to first write out the image to disk
and then use a file descriptor to read it back in.

One thing I struggle with is the initial seed (corpus). It needs to be
as small as possible, but also contain some valid ELF (core) files, so
that the fuzzer knows which valid paths there are to try out. How did
you construct the initial corpus? I normally try to create at least
four (little|big) endian and (32|64) bit minimal valid ELF files, but
that is not always easy.

Finally I wonder if we cannot integrate the logic in build-fuzzers.sh
in the normal auto* build and create a "make fuzz" target that simply
uses CC=afl-gcc or CC=hfuzz-gcc and runs afl-fuzz or honggfuzz for a
couple of minutes if installed/detected by configure. The
build-fuzzers.sh script seems very specific to a google setup which
most people won't have locally and which seems somewhat tricky to
replicate on other CI builders.



More information about the Elfutils-devel mailing list