Closed evverx closed 2 years ago
Please try with https://github.com/google/honggfuzz/commit/03a377b02525c3658cf9486b975e4dcf9e063833 - it might work, just a guess
Looks like the fuzz target still crashes
PID 2078288 - core
TID 2078288:
#0 0x00007fffe517d7b2 __GI___dl_iterate_phdr - libc.so.6
/usr/src/debug/glibc-2.34-34.fc35.x86_64/elf/dl-iteratephdr.c:34:1
#1 0x00007fffeeea7299 - 1 __wrap_memcmp - libsystemd-core-251.so
#2 0x0000000000432b16 - 1 instrumentAddConstMem - /home/vagrant/systemd/build/fuzz-unit-file
#3 0x00007fffeeea7318 - 1 __wrap_memcmp - libsystemd-core-251.so
#4 0x0000000000432b7e - 1 instrumentAddConstMem - /home/vagrant/systemd/build/fuzz-unit-file
#5 0x00007fffeeea7318 - 1 __wrap_memcmp - libsystemd-core-251.so
#6 0x0000000000432b16 - 1 instrumentAddConstMem - /home/vagrant/systemd/build/fuzz-unit-file
#7 0x00007fffeeea7318 - 1 __wrap_memcmp - libsystemd-core-251.so
#8 0x0000000000432b16 - 1 instrumentAddConstMem - /home/vagrant/systemd/build/fuzz-unit-file
...
#116371 0x00007fffeeea7318 - 1 __wrap_memcmp - libsystemd-core-251.so
#116372 0x0000000000432b7e - 1 instrumentAddConstMem - /home/vagrant/systemd/build/fuzz-unit-file
#116373 0x00007fffeeea7318 - 1 __wrap_memcmp - libsystemd-core-251.so
#116374 0x0000000000433059 - 1 instrumentAddConstStr - /home/vagrant/systemd/build/fuzz-unit-file
#116375 0x0000000000433849 - 1 __wrap_strcmp - /home/vagrant/systemd/build/fuzz-unit-file
#116376 0x00007fffe57f23f0 - 1 bus_error_name_to_errno - libsystemd-shared-251.so
#116377 0x00007fffe57f27a5 - 1 bus_error_setfv - libsystemd-shared-251.so
#116378 0x00007fffe57f29ba - 1 sd_bus_error_setf - libsystemd-shared-251.so
#116379 0x00007fffeed55b9f - 1 manager_load_unit_prepare - libsystemd-core-251.so
#116380 0x00007fffeed54443 - 1 manager_load_unit - libsystemd-core-251.so
#116381 0x00007fffeee730b9 - 1 unit_add_dependency_by_name - libsystemd-core-251.so
#116382 0x00007fffeed09aa2 - 1 config_parse_unit_deps - libsystemd-core-251.so
#116383 0x00007fffe5435569 - 1 next_assignment - libsystemd-shared-251.so
#116384 0x00007fffe542688f - 1 parse_line - libsystemd-shared-251.so
#116385 0x00007fffe5424fee - 1 config_parse - libsystemd-shared-251.so
#116386 0x000000000042f0e7 - 1 LLVMFuzzerTestOneInput - /home/vagrant/systemd/build/fuzz-unit-file
#116387 0x000000000042fb13 - 1 main - /home/vagrant/systemd/build/fuzz-unit-file
#116388 0x00007fffe5028440 - 1 __libc_start_call_main - libc.so.6
../sysdeps/nptl/libc_start_call_main.h:58:16
#116389 0x00007fffe50284f0 - 1 __libc_start_main_impl - libc.so.6
../csu/libc-start.c:389:3
#116390 0x0000000000406785 - 1 _start - /home/vagrant/systemd/build/fuzz-unit-file
If you run honggfuzz with -d -l /tmp/log
then you should see something like
[2022-06-09T09:44:23+0200][D][27121] initializeLibcFunctions():93 libc_memcmp=0x7ffff7d744c0, (_memcmp=0xa26f70, memcmp=0xa2c430, __wrap_memcmp=0xa2c430)
in /tmp/log
I can't seem to find initializeLibcFunctions
anywhere. I rebuilt honggfuzz
with the following patch:
diff --git a/libhfcommon/log.c b/libhfcommon/log.c
index 27b3e444..489156b4 100644
--- a/libhfcommon/log.c
+++ b/libhfcommon/log.c
@@ -50,7 +50,7 @@
static int hf_log_fd = STDERR_FILENO;
static bool hf_log_fd_isatty = false;
-enum llevel_t hf_log_level = INFO;
+enum llevel_t hf_log_level = DEBUG;
static pthread_mutex_t log_mutex = PTHREAD_MUTEX_INITIALIZER;
__attribute__((constructor)) static void log_init(void) {
and compiled a simple C program where main
just calls memcpy
with hfuzz-clang
. When it's run without honggfuzz
it shows something like
./a.out
[2022-06-09T13:09:19+0000][D][2104750] initializeInstrument():186 Initializing pid=2104750
[2022-06-09T13:09:19+0000][D][2104750] initializeInstrument():190 The 'HFUZZ_THREAD_NO' envvar is not set
[2022-06-09T13:09:19+0000][D][2104750] __sanitizer_cov_trace_pc_guard_init():588 PC-Guard module initialization: 0x458e08-0x458e0c (count:1) at 1
abc
but with honggfuzz
all those logs disappear somehow.
Looks like the logs are shown in persistent mode only.
[2022-06-09T13:59:20+0000][D][2108553] initializeInstrument():186 Initializing pid=2108553
[2022-06-09T13:59:20+0000][D][2108553] initializeLibcFunctions():93 libc_memcmp=0x7ffff7d88180, (_memcmp=0x42f870, memcmp=0x434dc0, __wrap_memcmp=0x434dc0)
[2022-06-09T13:59:20+0000][D][2108553] __sanitizer_cov_trace_pc_guard_init():588 PC-Guard module initialization: 0x459e30-0x459e34 (count:1) at 1
[2022-06-09T13:59:20+0000][D][2108553] fetchIsInputAvailable():90 Current module: ^A_LIBHFUZZ_PERSISTENT_BINARY_SIGNATURE_^Bÿ
I should have probably mentioned that the fuzz target is run in default mode . LLVMFuzzerTestOneInput
is probably misleading because it's wrapped into main
reading files and passing them to LLVMFuzzerTestOneInput
.
Looks like it crashes in persistent mode as well:
[2022-06-09T23:46:00+0000][D][2328799] subproc_New():420 Launched new process, pid=2328882, thread: 0 (concurrency: 1)
[2022-06-09T23:46:00+0000][D][2328882] subproc_New():407 Launching './build/fuzz-unit-file' on file 'PERSISTENT_MODE' (file mode)
[2022-06-09T23:46:00+0000][D][2328882] files_writeBufToFile():86 Written '4' bytes to '/proc/self/oom_score_adj'
[2022-06-09T23:46:00+0000][D][2328799] arch_traceAttach():1055 Attached to PID: 2328882
Persistent mode: Launched new persistent pid=2328882
[2022-06-09T23:46:00+0000][D][2328882] initializeInstrument():186 Initializing pid=2328882
[2022-06-09T23:46:00+0000][D][2328882] initializeLibcFunctions():93 libc_memcmp=0x7fffeeea7250, (_memcmp=0x42f810, memcmp=0x434d60, __wrap_memcmp=0x434d60)
[2022-06-09T23:46:00+0000][D][2328882] __sanitizer_cov_trace_pc_guard_init():588 PC-Guard module initialization: 0x7fffe5af3288-0x7fffe5b45bd0 (count:84562) at 1
[2022-06-09T23:46:00+0000][D][2328882] __sanitizer_cov_trace_pc_guard_init():588 PC-Guard module initialization: 0x7fffeef8c068-0x7fffeefb0854 (count:37371) at 84563
[2022-06-09T23:46:00+0000][D][2328882] __sanitizer_cov_trace_pc_guard_init():588 PC-Guard module initialization: 0x454aa8-0x454b5c (count:45) at 121934
[2022-06-09T23:46:00+0000][D][2328882] fetchIsInputAvailable():90 Current module: ^A_LIBHFUZZ_PERSISTENT_BINARY_SIGNATURE_^Bÿ
Sz:523 Tm:17,022us (i/b/h/e/p/c) New:0/0/0/0/0/120, Cur:0/0/0/1328/0/8289
...
[2022-06-09T23:46:21+0000][D][2328799] arch_checkWait():230 pid=2328882 returned with status: STOPPED with signal: 11 (Segmentation fault)
[2022-06-09T23:46:21+0000][D][2328799] sanitizers_PidForTid():120 Tid 2328882 has Pid 2328882
[2022-06-09T23:46:21+0000][D][2328799] sanitizers_parseReport():139 fopen('/home/vagrant/systemd/HF.sanitizer.log.2328882', 'rb'): No such file or directory
[2022-06-09T23:46:21+0000][D][2328799] arch_traceSaveData():690 Pid: 2328882, signo: 11, errno: 0, code: 1, addr: 0x7fffff7fefe0, pc: 7fffe517d7b2, crashAddr: 7fffff7fefe0 instr: 'mov____%rdi,(%rsp)'
Crash (dup): '/home/vagrant/systemd/SIGSEGV.PC.7fffe517d7b2.STACK.cbf6ad010.CODE.1.ADDR.7fffff7fefe0.INSTR.mov____%rdi,(%rsp).fuzz' already exists, skipping
[2022-06-09T23:46:25+0000][D][2328799] arch_checkWait():230 pid=2328882 returned with status: SIGNALED, signal: 11 (Segmentation fault)
[2022-06-09T23:46:25+0000][W][2328799] arch_checkWait():237 Persistent mode: pid=2328882 exited with status: SIGNALED, signal: 11 (Segmentation fault)
Sz:588 Tm:24,786,273us (i/b/h/e/p/c) New:0/0/0/0/0/213, Cur:0/0/0/615/0/1274
I wonder if this is related: https://github.com/google/oss-fuzz/issues/7435
@jonathanmetzman I think that issue is different. As far as I understand OSS-Fuzz doesn't build fuzz targets with hfuzz-clang/hfuzz-clang++
so "-Wl,--wrap=strncmp"
(which I suspect causes this particular issue) is never passed there. I'm not 100% sure though.
libhfuzz/memorycmp.o exports e.g. strncmp as a weak symbol, so it can be used w/o --wrap, depending on the static linker used and particulars.
With https://github.com/google/honggfuzz/commit/03a377b02525c3658cf9486b975e4dcf9e063833 I added an additional check, so it makes sure that the memcmp() used inside the library itself, is never the one exported by itself (as a weak symbol), but comparing it to the __wrap_memcmp symbol address.
You're talking about OSS, I suppose we need to upgrade honggfuzz version in oss-fuzz? I haven't done that in a long time, and probably lost the git setup for that. @jonathanmetzman is this something (upgrading honggfuzz to the current HEAD) that you could do given your fluency with oss-code, or would you rather leave it to me?
PS: Updating to whatever current HEAD points to - eg this https://github.com/google/honggfuzz/commit/6efe0eeef8182885ae4b7b1c49b071851bc37b16 - should be fine.
PPS: Ah.. I performed the procedure so long ago, that I've forgotten, that it's now just tag update on the honggfuzz side. Please hold on, I'll try to fix it
PPPS: Ok, done, if this is indeed about oss-fuzz, then this release - https://github.com/google/honggfuzz/releases/tag/oss-fuzz - fetched hopefully automatically by oss-fuzz, should help.
I think we always download from: https://github.com/google/honggfuzz/archive/oss-fuzz.tar.gz so your update should be picked up soon. I'll just test things in our CI to make sure it didn't break anything
if this is indeed about oss-fuzz
It's great honggfuzz got updated on OSS-Fuzz :-) Thanks! But as far as I can tell the original issue is still reproducible locally with the tip of the master branch. I switched to -V
everywhere to verify crashes though so I just kind of ignore crashes like that.
The updated honggfuzz didn't break anything. There were test failures but all due to sourceware.org being down.
@jonathanmetzman speaking of OSS-Fuzz I wonder if it would be possible to switch to hfuzz-clang/hfuzz-clang++
there optionally. The compiler flags honggfuzz
passes are helpful when it comes to catching a certain kind of issues like https://github.com/systemd/systemd/issues/23646 even without fuzzing :-) Other than that it would make it easier to reproduce issues locally (where hfuzz-clang
is usually used) reliably.
I can look the other way if you get it working but I probably wont recommend it. And i don't know if I will make it the default given how it went when AFL did this (it made programs crash at arbitrary/noreproducible times during production fuzzing and not test fuzzing)
i don't know if I will make it the default
I agree the honggfuzz wrappers shouldn't be rolled out by default. It took me a while to get for example systemd
and elfutils
to even compile so I suspect some projects would just fail to build.
given how it went when AFL did this (it made programs crash at arbitrary/noreproducible times during production fuzzing and not test fuzzing)
I just turned it off at the time as far as I can remember :-) On the bright side all issues I personally ran into were fixed and AFL was brought back.
I can look the other way if you get it working but I probably wont recommend it
Got it
I'll try to repro this today. Shall I simply run it for some time (1h enough?) with compile options/setup taken from oss-fuzz?
Locally the fuzz target crashes in about 5 minutes. It can be reproduced with
git clone --depth=1 https://github.com/systemd/systemd
cd systemd
CC=hfuzz-clang CXX=hfuzz-clang++ meson -Dskip-deps=true build
ninja -C ./build/ fuzz-unit-file
cp test/fuzz/fuzz-unit-file/*.service INPUT/
honggfuzz -i INPUT/ -o OUTPUT -t30 -- ./build/fuzz-unit-file ___FILE___
-Dskip-deps
turns off almost all the build dependencies so only meson
, ninja
, jinja2
, libmount-dev
and libcap-dev
should be installed to get it to compile.
I'm not sure how to reproduce https://github.com/google/oss-fuzz/issues/7435
Changing libc_memcmp to _memcmp here https://github.com/google/honggfuzz/blob/0b47bfdd0df92b332884a83624360ed582eb4aed/libhfuzz/instrument.c#L266 solves it, so it's some kind of circular invocation of memcmp, let me do some debugging then.
The problem was interesting. When two (or more) instrumented by honggfuzz modules (binaries, libraries) end up in one address space, then libc_memcmp will be resolved to the other's module's memcmp (which will in turn call into the original one).
I fixed it temporarily with - https://github.com/google/honggfuzz/commit/a338c5322dea64c468a4419d00daebd635f7ac8b - but I need to think how to do it "for good", as the fix is not pretty.
I updated the oss-fuzz tag too.
PS: I'm not sure how oss-fuzz fuzzes systemd under honggfuzz, but it seems that systemd's fuzzing implements its own main()
. This prevents using honggfuzz's main
, which in turn disabled the persistent mode. In effect the fuzzing is ~20x as slow as it could be.
If that's the case, maybe we could do something about it. E.g. surrounding systemd's fuzzing main() with e.g.
#ifndef HFND_FUZZING_ENTRY_FUNCTION
int main(...) {
}
#endif /* HFND_FUZZING_ENTRY_FUNCTION */
or somesuch.
systemd
can be fuzzed in a few modes and on OSS-Fuzz LLVMFuzzerTestOneInput
isn't wrapped into main
. There it's linked with hongfuzz
and run in persistent mode. The "main" wrapper is mostly used to run the fuzz targets with corpora accumulated over time under Valgrind or as unit tests or on architectures where ASan doesn't work for various reasons.
I think it would make sense to skip the "main" wrapper when HFND_FUZZING_ENTRY_FUNCTION
is defined locally as well. Right now only libFuzzer
is supported "natively" by the build script and the other fuzzing engines are slow. Thanks for the pointer!
Thanks for the info. I'll go ahead and close this report, but please re-open if you'd like still to work on that.
I haven't figured out what's going on yet but it appears some fuzz targets segfault from time to time when they are run with
honggfuzz
and don't crash when they are run directly. The verifier can't reproduce those crashes eitherI'm not sure if it helps but backtraces look like
That particular fuzz target was built with
hfuzz-clang/hfuzz-clang++
on Fedora 35 withclang version 13.0.0 (Fedora 13.0.0-3.fc35)
with no sanitizers.