我有一个很大的静态库,我想打包成一个 iOS 静态框架以便于使用。该库实际上是几个 .a
文件,每个库的逻辑模块一个。
我有为设备编译的.a
文件(带有armv7
、armv7s
、arm64
的胖文件>) 和模拟器(i386
、x86_64
的胖文件)。
现在,AFAIK,我需要将所有这些文件合并到一个大文件中以构建一个合适的框架。
使用此处描述的技术 (Combine static libraries),我可以做到:
libtool -static -o new.a old1.a old2.a
但显然 old1.a
和 old2.a
都包含相同的符号。因此,在针对我的框架进行链接时,我收到链接器错误(出于正当理由)duplicate symbols
。
一个更正确的方法(从而避免重复的符号)似乎是解压 .o
文件,并将它们组合成一个大的 .a
文件( How to pack multiple library archives (.a) into one archive file? )
ar x old1.a
ar x old2.a
ar rcs new.a *.o
现在,请记住,old1.a
和 old2.a
是胖文件,因此我需要根据架构将其分开。
我的做法是:
lipo old1.a -thin armv7 -output armv7/old1.a
cd armv7; ar x old1.a; cd ..
...
lipo old1.a -thin x86_64 -output x86_64/old1.a
cd x86_64; ar x old1.a; cd ..
// Same goes for old2.a ...
// Then,
libtool -static -o new.a armv7/*.o armv7s/*.o arm64/*.o // ... etc
但由于某些原因,当链接到如此创建的框架时,链接器找不到任何符号(即使 nm
显示了所有符号)。
知道如何构建静态框架吗?
最佳答案
您可以将您的静态库对象预链接为一个,也可以将其他静态库预链接为一个。它实际上会将对象与链接器链接起来(几乎就像在动态库中一样)。
- 在您的单个库(主要库)中,转到“build设置”并在“链接”部分中找到“执行单对象预链接”。将其切换为是
- 在 Prelink 库中,您可以指定要包含的其他库。在那里您不仅需要输入名称,还需要输入完整的文件名。如果其他库也来自您的项目,那么您可以使用 $(CONFIGURATION_BUILD_DIR) 变量。所以如果你有库 foo,那么它将是 $(CONFIGURATION_BUILD_DIR)/libfoo.a
- 您可以在 Single-Object Prelink Flags 中添加额外的标志
- 如果您想去除本地符号,请确保将“部署后处理”设置为"is",因为默认情况下不会去除静态库。
如果你的库有重复的符号,那么你的模块结构有问题。
- 如果它们是相同的函数,则将它们分离到一个单独的静态库中,并从其他地方重用。
- 如果这些符号实际上不同并且只是名称相同,那么考虑将它们声明为静态的(如果它是 ANSI C)。你也可以
- 您可以通过设置可见性隐藏一些局部符号(http://llvm.org/docs/LangRef.html#visibility-styles、http://gcc.gnu.org/wiki/Visibility)
关于ios - 将多个静态库编译成一个 iOS Framework,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/21099749/