Lapack 链接错误,使用 -fPIC 重新编译

Lapack linking error, recompile with -fPIC

本文关键字:新编译 编译 -fPIC 链接 错误 使用 Lapack      更新时间:2023-10-16

我有一个复杂的程序,用于用Levenberg-Marquardt方法拟合非线性函数。

该程序使用来自Lapack库的线性方程组的求解器,我在其中使用了:

extern "C" ...

链接到外部 Fortran 库。该程序在我的笔记本电脑上运行没有任何问题(使用 Ubuntu 12.04),我已经使用它进行测试一段时间了。

问题:

现在我搬到了大胖的64核计算机,以便开始做一些真正的计算,计算机上有一个科学的linux 6。事实证明,大型计算机没有安装 lapack,所以我得到了 lapack 3.4.2,对其进行了编译,并按照此处的说明构建了它:

http://matrixprogramming.com/2011/04/using-lapack-from-c/comment-page-1

在那之后,我在我的 cmake 文件中绝对没有更改以前有效的任何内容,只是添加了链接选项:

-L/xdata/Compilers/Sources/lapack-3.4.2

现在我收到错误:

/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

只是为了记录,我的 cmake 脚本到处都有 -fPIC 和 -fPIE......我使用它的链接:

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)

我做错了什么?请指教。

谢谢。

解决方案是用 -fPIC 重新编译 lapack 本身。因此,在您的make.inc中更改为以下内容:

FORTRAN  = gfortran -m64 -fPIC
OPTS     = -O2 -m64 -fPIC
DRVOPTS  = $(OPTS)
NOOPT    = -O0 -m64 -fPIC
LOADER   = gfortran -m64 -fPIC

您也可以使用 -O3 进行更好的优化,它工作正常!

选项-m64取决于您是否要使用 64 位系统。您的选择!

干杯!

如果使用mkdir build; cd build; cmake ..; make路由,请使用 cmake .. -DBUILD_SHARED_LIBS=ON

为什么会这样?-fPIC 选项使 gcc 使用相对地址 [1]
对接受的答案的评论:"更具体地说,共享库应该在进程之间共享,但可能并不总是可以在两个进程的同一地址加载库。如果代码不是独立于位置的,那么每个进程都需要自己的副本" - Simon Richter
[1] GCC -fPIC 选项