Skip to content

kalibera/mfuzz

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

1 Commit
 
 
 
 
 
 
 
 
 
 

Repository files navigation

mfuzz

This is a tool for detecting over-sensitivity issues in programs on Unix (only tested on Linux) to accuracy of the C Math library. Some R packages come with tests of numerical results with tolerances set simply on observations on several systems at hand when the tests were written. As there is no formal accuracy requirement on C Math library, the tolerances set that way may be unreasonable and the packages may start failing on some system, when the C Math library there starts trading accuracy for performance. This tool makes the results of C Math library function less precise, it introduces errors of 1 ULP (unit of least precision), so very small errors. This work has been inspired by real problems seen on Windows, while upgrading to mingw-w64 v12 from v11. For more background, see blog posts Sensitivity to C math library and mingw-w64 v12 and Sensitivity to C math library and mingw-w64 v12 - part 2.

This tool provides wrappers of Math library functions, which can be built into a shared library, such as (works on Fedora 43):

gcc -O2 -o libmfuzz.so -shared -fPIC wrappers.c mfuzz.c -I.

The library can be then used with R by providing it to the dynamic linker before the real C Math library, e.g. using LD_PRELOAD (on Fedora):

env LD_PRELOAD=~/mfuzz/libmfuzz.so /usr/local/bin/R

The tool is controlled by environment variables. MFUZZ_FUZZ sets which functions are fuzzed. A common and most reasonable value is MFUZZ_FUZZ=trans, which means that all transcendental functions will be fuzzed - we don't want to fuzz functions that do rounding or extracting of the integer part of a floating point number. It is also possible to enumerate individual functions to fuzz (separated by space), which may be useful when looking for which function a program or R package is over-sensitive to, one might do this using interval division, iteratively. It is also possible to explicitly disable fuzzing via MFUZZ_FUZZ=none.

Variable MFUZZ_LOG sets calls to which functions are recorded in the log file. Functions can be specified the same way as for MFUZZ_FUZZ. The log file path can be set via MFUZZ_LOGFILE, the default is /tmp/mfuzz.log.

To generate wrappers.c, run genwrappers.r.

The tool implementation is based on https://www.github.com/kalibera/mdebug, but unlike mdebug, which is for Windows-only, mfuzz is only for Unix.

The fuzzing in principle means that the result obtained from the Math library in the system is shifted 1 ULP towards positive infinity unless it would turn a negative value to a positive one, in that case, it is shift 1 ULP away from zero. The tool tries to be somewhat permissive and not return "obviously wrong values" (writing very informally here). For example, sin(0) is exactly 0 if the system Math library works that way. Also, sin(-x) is exactly -sin(x). Similar constraints to fuzzing are implemented for other functions (this is encoded in genwrappers.r). The C standard doesn't mandate even these things, but they are implemented in mfuzz to make the fuzzing more acceptable to mathematicians.

About

Fuzzing tool for C Math library on Unix

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors