oss-fuzz: Incorrect coverage report
The zstd coverage report is not correct. For example, in src/zstd/lib/compress/zstd_fast.c
, ZSTD_compressBlock_fast_generic()
is shown as never executed, I’m certain that it is executed in some of the fuzzers. To be extra sure I ran the simple_round_trip
fuzzer locally with an assert(0);
in the function and it crashed as expected.
About this issue
- Original URL
- State: closed
- Created 5 years ago
- Comments: 15 (15 by maintainers)
Sorry, I couldn’t get to this in a while. Also, there was a relevant discussion on llvm-dev mailing list a month ago: https://groups.google.com/d/msg/llvm-dev/Wp0pVlJmhqQ/qT5X_ap7BQAJ
So, what actually collides is probably
function’s structural hash
mentioned in https://llvm.org/docs/CoverageMappingFormat.html#function-recordIt’s also referenced in https://github.com/llvm-mirror/llvm/blob/6b547686c5410b7528212e898fe30fc7ee7a70a3/include/llvm/ProfileData/Coverage/CoverageMapping.h#L714
Which I believe is lower 64 bits of a MD5 hash, but the hash input is the functions profile data rather than a function name.
Haha, nice, thanks for the fix @terrelln! Sorry I was out on Friday. I still want to refresh in my memory what exactly is being hashed, so I’ll leave this issue open for a little while.
The problem is that some function(s) seem to have different binary code in different fuzz targets. That confuses llvm-cov when merging the coverage across binaries (e.g. if the same function has different structure, how we can merge it). The tool prints the warning and aborts the merge process after observing a modified function. If I exclude such cases, everything works fine, e.g.:
and
without these two targets, I’m getting a correct report.
Usually this happens when different binaries with the same dependencies are compiled with different flags / options.
The most obvious thing to blame in zstd case is
ZSTD_STATIC_LINKING_ONLY
define which is declared in some targets, but not in all of them. I’ve tried adding#define ZSTD_STATIC_LINKING_ONLY
to the following targets as well:But still got the error. Do you know if there are any other differences that may lead to the different binary code produced for the same function(s)?
Looks like this has regressed between
https://storage.googleapis.com/oss-fuzz-coverage/zstd/reports/20190411/linux/src/zstd/tests/fuzz/report.html
and
https://storage.googleapis.com/oss-fuzz-coverage/zstd/reports/20190412/linux/src/zstd/tests/fuzz/report.html
i.e. Apr 11-12th. We had a couple changes on that day (#2311 and #2316), but I don’t really suspect either of those is a culprit (though it might be).
Thanks for your report. There is definitely something wrong with the merging of the reports. If I check results for the individual fuzz targets, I see some coverage for all of them, e.g.
https://storage.googleapis.com/oss-fuzz-coverage/zstd/fuzzer_stats/20190417/simple_round_trip.json
shows that
simple_round_trip.c
has 100% coverage, which is totally reasonable for the target function.However, this directory clearly lacks coverage for some fuzz targets: https://storage.googleapis.com/oss-fuzz-coverage/zstd/reports/20190417/linux/src/zstd/tests/fuzz/report.html
Sadly, I don’t see any issues reported in the logs. Will have to reproduce it and dig deeper. Thanks again!