好吧,这很令人困惑;但我认为这libtool -o $(PROJECT) -static $(OBJECTS)
条线(也在objective c - Combine static libraries中提到)来自Mac;显然与Linuxlibtool
上的不一样:
libtool 或 ar & ranlib - idevgames 论坛:
我正在使用 libtool 在 OS X 上创建一个静态库,因为这就是 Xcode 正在做的事情,这似乎工作正常。然后我转到 Linux,它被我的 libtool 命令阻塞,说“libtool:无法识别的选项'-o'”。看着它们,似乎 OS X 上的 libtool 和 Linux 上的 libtool 是两个完全不同的程序。...
跟进:是的,Linux 上的 libtool 似乎确实是 OS X 上的 glibtool。在 OS X 上执行“ glibtool --help
”时,我得到的输出libtool --help
与 Linux 上的“”基本相同。
-o
好的,这解释了差异 - 但是当我刚刚看到它从 Linux 上的 Makefile 运行时,仍然没有解释如何成为一个无法识别的选项!所以我发现了这个:
bug-libtool 邮件列表 (2001): Re: libtool 中的错误?
您需要在模式选项之前设置模式:
$ libtool --mode=link --help
用法:libtool [选项]... --mode=link LINK-COMMAND...
哦,天哪……现在特别令人困惑的是,这个注释是libtool --mode=link --help
:
$ libtool --mode=link --help
Usage: libtool [OPTION]... --mode=link LINK-COMMAND...
...
LINK-COMMAND is a command using the C compiler that you would use to create
a program from several object files.
The following components of LINK-COMMAND are treated specially: ...
-all-static do not do any dynamic linking at all ...
-o OUTPUT-FILE create OUTPUT-FILE from the specified objects ...
-static do not do any dynamic linking of uninstalled libtool libraries
...
All other options (arguments beginning with `-') are ignored.
Every other argument is treated as a filename. Files ending in `.la' are
treated as uninstalled libtool libraries, other files are standard or library
object files.
...
If OUTPUT-FILE ends in `.a' or `.lib', then a standard library is created
using `ar' and `ranlib', or on Windows using `lib'.
所以 - 如果我必须指定一个LINK-COMMAND
-同时,我指定一个以;OUTPUT-FILE
结尾的 .a
然后应该运行哪个命令,LINK-COMMAND
- 或扩展指定的ar
+ ?好吧 - 这是一个终端片段,只是测试 - 没有任何编译的脚本逻辑(尽管确实创建了一个空存档):ranlib
.a
bash
libtool
$ libtool -o test.a
libtool: unrecognized option `-o'
libtool: Try `libtool --help' for more information.
$ libtool --mode=link -o test.a
libtool: link: unrecognized option `-o'
libtool: link: Try `libtool --help' for more information.
$ libtool --mode=link gcc -o test.a
libtool: link: ar cru test.a
libtool: link: ranlib test.a
$ libtool --mode=link ar -o test.a
libtool: link: unable to infer tagged configuration
libtool: link: specify a tag with `--tag'
$ cat $(which libtool) | grep "^# ### BEGIN LIBTOOL TAG CONFIG:"
# ### BEGIN LIBTOOL TAG CONFIG: disable-shared
# ### BEGIN LIBTOOL TAG CONFIG: disable-static
# ### BEGIN LIBTOOL TAG CONFIG: CXX
# ### BEGIN LIBTOOL TAG CONFIG: F77
# ### BEGIN LIBTOOL TAG CONFIG: FC
# ### BEGIN LIBTOOL TAG CONFIG: GCJ
# ### BEGIN LIBTOOL TAG CONFIG: RC
# ### BEGIN LIBTOOL TAG CONFIG: BINCC
# ### BEGIN LIBTOOL TAG CONFIG: BINCXX
## CC tag is not listed, but it will (eventually) be accepted:
$ libtool --mode=link ar --tag CC -o test.a
libtool: link: unable to infer tagged configuration
libtool: link: specify a tag with `--tag'
$ libtool --mode=link --tag CC ar -o test.a
libtool: link: ar cru test.a
libtool: link: ranlib test.a
$ libtool --tag=CC --mode=link ar -o test.a
libtool: link: ar cru test.a
libtool: link: ranlib test.a
$ libtool --tag=XX --mode=link ar -o test.a
libtool: ignoring unknown tag XX
libtool: link: ar cru test.a
libtool: link: ranlib test.a
$ libtool --tag=XX --mode=link whatevar -o test.a
libtool: ignoring unknown tag XX
libtool: link: ar cru test.a
libtool: link: ranlib test.a
$ ls -la test.a
-rw-r--r-- 1 user user 8 2013-04-17 23:12 test.a
所以 - 你不仅必须指定 a --mode
,而且如果这个模式是link
,你必须指定某种引用工具的参数(LINK-COMMAND);但是那个 LINK-COMMAND 参数甚至不需要作为一个真正的程序存在——因为无论如何你都必须指定一个输出文件;如果该输出文件以 结束.a
,它将强制使用ar
/ranlib
无论如何。
此外,如果您对标签有问题 - 只需将参数移到--tag
LINK-COMMAND 参数之前 - 您可以强制libtool
使用不存在的标签和不存在的 LINK-COMMAND 运行(其操作仅由输出文件的扩展名.a
)——只要以正确的libtool
语法顺序输入参数;我必须承认,脚本本身并没有真正记录这一点。
但是回到 Maclibtool -o $(PROJECT) -static $(OBJECTS)
系列,它将结合静态库;如果您尝试对适当的静态库.a
文件执行相同的操作,您会注意到在输出存档中libtool
推送.a
存档,而不是它们的组成对象文件 - 因此此输出不再是有效的 ELF 对象;这是一个相应的 Linuxlibtool
行的示例,其中包含我生成的两个适当的库文件:
$ readelf --syms libmy1.a
File: libmy1.a(my1.o)
Symbol table '.symtab' contains 11 entries:
...
$ readelf --syms libmy2.a
File: libmy2.a(my2.o)
Symbol table '.symtab' contains 12 entries:
...
$ libtool --mode=link --tag=CC ar -o libtest.a -static libmy1.a libmy2.a
libtool: link: ar cru libtest.a libmy1.a libmy2.a
libtool: link: ranlib libtest.a
$ readelf --syms libtest.a
readelf: Error: Not an ELF file - it has the wrong magic bytes at the start
readelf: Error: libtest.a(libmy1.a): Failed to read file header
readelf: Error: Not an ELF file - it has the wrong magic bytes at the start
readelf: Error: libtest.a(libmy2.a): Failed to read file header
因此,正如公认的答案所说 - 在 Linux 上,ar
手动使用解包并再次打包,以组合静态库。
希望这对某人有帮助,
干杯!