Description
On FreeBSD AArch64, exp10(::BigFloat)
is inaccurate unless:
- Julia is run with its own bundled
libmpfr.so
LD_PRELOAD
ed, or - Julia is invoked from C with
-lmpfr
passed when compiling, even if MPFR is not used at all in the C code.
Example of case 1:
$ ./usr/bin/julia -e 'show(exp10(BigFloat(-100.0)))'
8.572405434617062366618376612290057195889324961170989959113443824207244769300536e-101
$ LD_PRELOAD="./usr/lib/libmpfr.so" ./usr/bin/julia -e 'show(exp10(BigFloat(-100.0)))'
9.999999999999999999999999999999999999999999999999999999999999999999999999999955e-101
The latter value is correct. The former is not and causes some math tests to fail.
Example of case 2:
// call this test.c
#include "julia.h"
int main(void) {
jl_init();
jl_eval_string("show(exp10(BigFloat(-100.0)))");
jl_atexit_hook(0);
return 0;
}
$ cc test.c -o test1 -std=gnu11 -I/root/julia/usr/include/julia -I/root/julia/usr/include -L/root/julia/usr/lib -L/root/julia/usr/lib/julia -fPIC -Wl,--export-dynamic -Wl,-rpath,/root/julia/usr/lib -Wl,-rpath,/root/julia/usr/lib/julia -ljulia
$ ./test1
8.572405434617062366618376612290057195889324961170989959113443824207244769300536e-101
$ cc test.c -o test2 -std=gnu11 -I/root/julia/usr/include/julia -I/root/julia/usr/include -L/root/julia/usr/lib -L/root/julia/usr/lib/julia -fPIC -Wl,--export-dynamic -Wl,-rpath,/root/julia/usr/lib -Wl,-rpath,/root/julia/usr/lib/julia -ljulia -lmpfr
$ ./test2
9.999999999999999999999999999999999999999999999999999999999999999999999999999955e-101
I've attempted quite a bit of debugging, none of which has been particularly fruitful, but I did notice something odd. jl_dlfind
can't find mpfr_exp10
(unless MPFR is preloaded) but we still end up calling it:
$ ./usr/bin/julia -E 'ccall(:jl_dlfind, Ptr{UInt8}, (Ptr{UInt8},), "mpfr_exp10")'
Ptr{UInt8}(0x0000000000000000)
$ LD_PRELOAD="./usr/lib/libmpfr.so" ./usr/bin/julia -E 'ccall(:jl_dlfind, Ptr{UInt8}, (Ptr{UInt8},), "mpfr_exp10")'
Ptr{UInt8}(0x0000000000000001)
The latter corresponds to JL_EXE_LIBNAME
, and is the result I get on macOS AArch64. The former means we couldn't find the symbol in libjulia-internal
, libjulia
, or the executable (searched in that order). I would have assumed this means we couldn't find it at all—however, running under LLDB with a breakpoint on mpfr_exp10
, we do actually call it.
I'm pretty stumped; this is among the stranger things I've encountered in my time spent using computers. Does anybody know what the issue could be, or have any suggestions for further debugging?