为 Ada 构建共享库
Building shared libraries for Ada
我在不使用 GPR 的情况下从 Ada 包构建共享库时遇到了一些问题。
我在文件 "numerics.ads" 和 "numerics.adb" 中有一个包 Numerics。他们没有依赖关系。有一个小型构建脚本可以执行以下操作:
gnatmake -Os numerics.ad[bs] -cargs -fPIC
gcc -shared numerics.o -o libnumerics.so -Wl,-soname,libnumerics.so
.so和.ali文件安装在/usr/lib,.ads文件安装在/usr/include。
gnatls -v 输出以下相关部分:
Source Search Path:
<Current_Directory>
/usr/include
/usr/lib/gcc/x86_64-unknown-linux-gnu/5.1.0/adainclude
Object Search Path:
<Current_Directory>
/usr/lib
/usr/lib/gcc/x86_64-unknown-linux-gnu/5.1.0/adalib
所以 GNAT 应该没有问题找到这些文件。
然后,尝试编译依赖于 Numerics 的包:
gnatmake -O2 mathematics.ad[bs] -cargs -fPIC
输出:
gcc -c -fPIC mathematics.adb
gcc -c -I./ -fPIC -I- /usr/include/numerics.ads
cannot generate code for file numerics.ads (package spec)
gnatmake: "/usr/include/numerics.ads" compilation error
这个错误让我认为 GNAT 无法识别共享库,并且正在尝试重建 Numerics。
我想构建共享库,并且只提供用于 reference/documentation 目的的规范。
编辑:
所以,看起来 gprbuild 做了两件我没有做的事情。首先,还将 -lnumerics 传递给编译器。第二个应该无关紧要,因为 libnumerics.so 无论如何都在标准目录中,它是 -L«ProjectDirectory»。 GPRbuild 显然也没有执行所需的行为,即使它正在构建依赖项目。它应该使用安装的库 /usr/lib/libnumerics.so,而是使用 «path»/Numerics/build/libnumerics.so。此外,在使用 GPRbuild 构建 Numerics,然后重命名主体以使其好像主体不存在一样(就像安装的文件一样),当使用 GPRbuild 构建 Mathematics 时,它会抱怨完全相同的问题。就好像库甚至没有共享,GPRBuild 只是让它们看起来像那样(除了 readelf 报告库内的正确依赖项)。
在构建脚本中添加 -lnumerics 没有任何作用;构建错误完全相同。在这一点上我完全迷路了。
编辑:
在 Simon 的 link 之后,构建脚本已更改为:
gnatmake -O2 mathematics.ad[bs] \
-aI/usr/include \
-aO/usr/lib \
-cargs -fPIC \
-largs -lnumerics
错误基本相同:
gcc -c -O2 -I/usr/include/ -fPIC mathematics.adb
gcc -c -I./ -O2 -I/usr/include/ -fPIC -I- /usr/include/numerics.ads
cannot generate code for file numerics.ads (package spec)
gnatmake: "/usr/include/numerics.ads" compilation error
我想检查 libnumerics.so 实际上是一个正确的共享库。 ldd 报告:
linux-vdso.so.1 (0x00007ffd944c1000)
libc.so.6 => /usr/lib/libc.so.6 (0x00007f50d3927000)
/usr/lib64/ld-linux-x86-64.so.2 (0x00007f50d3ed4000)
所以我想是的,库很好,但 gnatmake 仍然无法识别它。
通常,您还需要安装包的主体(numerics.adb 在您的情况下)。另外,我怀疑你想设置 ALI 文件
(numerics.ali) 为只读,因此 gnatmake 不会尝试重新编译它们。
我在不使用 GPR 的情况下从 Ada 包构建共享库时遇到了一些问题。
我在文件 "numerics.ads" 和 "numerics.adb" 中有一个包 Numerics。他们没有依赖关系。有一个小型构建脚本可以执行以下操作:
gnatmake -Os numerics.ad[bs] -cargs -fPIC
gcc -shared numerics.o -o libnumerics.so -Wl,-soname,libnumerics.so
.so和.ali文件安装在/usr/lib,.ads文件安装在/usr/include。
gnatls -v 输出以下相关部分:
Source Search Path:
<Current_Directory>
/usr/include
/usr/lib/gcc/x86_64-unknown-linux-gnu/5.1.0/adainclude
Object Search Path:
<Current_Directory>
/usr/lib
/usr/lib/gcc/x86_64-unknown-linux-gnu/5.1.0/adalib
所以 GNAT 应该没有问题找到这些文件。
然后,尝试编译依赖于 Numerics 的包:
gnatmake -O2 mathematics.ad[bs] -cargs -fPIC
输出:
gcc -c -fPIC mathematics.adb
gcc -c -I./ -fPIC -I- /usr/include/numerics.ads
cannot generate code for file numerics.ads (package spec)
gnatmake: "/usr/include/numerics.ads" compilation error
这个错误让我认为 GNAT 无法识别共享库,并且正在尝试重建 Numerics。
我想构建共享库,并且只提供用于 reference/documentation 目的的规范。
编辑: 所以,看起来 gprbuild 做了两件我没有做的事情。首先,还将 -lnumerics 传递给编译器。第二个应该无关紧要,因为 libnumerics.so 无论如何都在标准目录中,它是 -L«ProjectDirectory»。 GPRbuild 显然也没有执行所需的行为,即使它正在构建依赖项目。它应该使用安装的库 /usr/lib/libnumerics.so,而是使用 «path»/Numerics/build/libnumerics.so。此外,在使用 GPRbuild 构建 Numerics,然后重命名主体以使其好像主体不存在一样(就像安装的文件一样),当使用 GPRbuild 构建 Mathematics 时,它会抱怨完全相同的问题。就好像库甚至没有共享,GPRBuild 只是让它们看起来像那样(除了 readelf 报告库内的正确依赖项)。
在构建脚本中添加 -lnumerics 没有任何作用;构建错误完全相同。在这一点上我完全迷路了。
编辑: 在 Simon 的 link 之后,构建脚本已更改为:
gnatmake -O2 mathematics.ad[bs] \
-aI/usr/include \
-aO/usr/lib \
-cargs -fPIC \
-largs -lnumerics
错误基本相同:
gcc -c -O2 -I/usr/include/ -fPIC mathematics.adb
gcc -c -I./ -O2 -I/usr/include/ -fPIC -I- /usr/include/numerics.ads
cannot generate code for file numerics.ads (package spec)
gnatmake: "/usr/include/numerics.ads" compilation error
我想检查 libnumerics.so 实际上是一个正确的共享库。 ldd 报告:
linux-vdso.so.1 (0x00007ffd944c1000)
libc.so.6 => /usr/lib/libc.so.6 (0x00007f50d3927000)
/usr/lib64/ld-linux-x86-64.so.2 (0x00007f50d3ed4000)
所以我想是的,库很好,但 gnatmake 仍然无法识别它。
通常,您还需要安装包的主体(numerics.adb 在您的情况下)。另外,我怀疑你想设置 ALI 文件 (numerics.ali) 为只读,因此 gnatmake 不会尝试重新编译它们。