I have a sophisticated program for fitting nonlinear functions with the Levenberg-Marquardt's method.
The program uses a solver for a system of linear Equations from the Lapack library, where I have used:
extern "C" ...
To link to external fortran libraries. The program worked on my laptop with no problems (which uses Ubuntu 12.04), and I've been using it for tests for a while.
The problem:
Now I moved to the big fat 64-core computer in order to start doing some real calculations, the computer has a scientific linux 6 on it. It turned out that the big computer doesn't have lapack installed, so I got lapack 3.4.2, compiled it, and followed the instructions from here to build it:
http://matrixprogramming.com/2011/04/using-lapack-from-c/comment-page-1
After that, I changed absolutely nothing in my cmake file which worked before, and just added the linking option:
-L/xdata/Compilers/Sources/lapack-3.4.2
Now I get the error:
/usr/bin/ld: /xdata/Compilers/Sources/lapack-3.4.2/liblapack.a(dsytrf.o): relocation R_X86_64_32 against `.rodata' can not be used when making a shared object; recompile with -fPIC
And just for the record, my cmake script is has -fPIC and -fPIE everywhere... The linking I use it:
target_link_libraries(LibsModule -lgsl)
target_link_libraries(LibsModule -lgslcblas)
target_link_libraries(LibsModule -lrt)
target_link_libraries(LibsModule -lpthread)
target_link_libraries(LibsModule -pie)
target_link_libraries(LibsModule -fPIC)
target_link_libraries(LibsModule -L/xdata/Compilers/Sources/lapack-3.4.2)
target_link_libraries(LibsModule -lgfortran)
target_link_libraries(LibsModule -llapack -fPIC)
target_link_libraries(LibsModule -lblas -fPIC)
What did I do wrong? Please advise.
Thank you.
The solution was to recompile lapack itself with -fPIC. So in your make.inc change to the following:
FORTRAN = gfortran -m64 -fPIC
OPTS = -O2 -m64 -fPIC
DRVOPTS = $(OPTS)
NOOPT = -O0 -m64 -fPIC
LOADER = gfortran -m64 -fPIC
And you may also use -O3
for better optimization, it works fine!
The option -m64
depends whether you wanna use a 64-bit system. Your choice!
Cheers!
If the mkdir build; cd build; cmake ..; make
route is used, use cmake .. -DBUILD_SHARED_LIBS=ON
.
Why would this work? The -fPIC option makes gcc use relative addresses [1]
Comment on accepted answer:
"To be more specific, the shared library is supposed to be shared between processes, but it may not always be possible to load the library at the same address in both. If the code were not position independent, then each process would require its own copy" - Simon Richter
[1] GCC -fPIC option
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With