“-fembed-bitcode”和“BITCODE_GENERATION_MODE”有什么区别?它们都与位码生成相关。

46

我一直在更新一个静态库以支持位码(bitcode),从我的研究中我发现有两种实现方法:

  • 在项目构建设置的其他C标志选项中添加fembed-bitcode标记(链接
  • 添加一个用户定义的设置,键为BITCODE_GENERATION_MODE,值为bitcode链接

这两个选项之间有什么区别吗?

我注意到的唯一区别是使用fembed-bitcode,生成的iPhone模拟器静态库将启用完整位码(在我的情况下,二进制文件大小从5MB变为13MB,并且我可以使用otool检查位码支持),但似乎在使用上没有任何区别。

1个回答

65

当您正常构建库时,使用ENABLE_BITCODE=YES,Xcode会向任何clang调用添加构建标志-fembed-bitcode-marker,将一个“空”位代码放入最终的o文件中。

因此,如果您查看构建阶段的编译操作,它将看起来像这样:

CompileC {build_path}/StaticBitcode/StaticLogger.o StaticBitcode/StaticLogger.m normal armv7 objective-c com.apple.compilers.llvm.clang.1_0.compiler cd {path}/StaticBitcode export LANG=en_US.US-ASCII export PATH="/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/usr/bin:/Applications/Xcode.app/Contents/Developer/usr/bin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin" /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/clang -x objective-c -arch armv7 -fmessage-length=0 -fdiagnostics-show-note-include-stack -fmacro-backtrace-limit=0 -std=gnu99 -fobjc-arc -fmodules -gmodules -fmodules-cache- [...] -fembed-bitcode-marker [...]

这适用于构建操作(与目标无关)。

当您执行Build & Archive时,-fembed标志将被-fembed-bitcode替换,这确实构建了一个启用位代码的二进制文件:

CompileC {build_path}/StaticBitcode/StaticLogger.o StaticBitcode/StaticLogger.m normal armv7 objective-c com.apple.compilers.llvm.clang.1_0.compiler cd {path}/StaticBitcode export LANG=en_US.US-ASCII export PATH="/Applications/Xcode.app/Contents/Developer/Platforms/iPhoneOS.platform/Developer/usr/bin:/Applications/Xcode.app/Contents/Developer/usr/bin:/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin" -fembed-bitcode /Applications/Xcode.app/Contents/Developer/Toolchains/XcodeDefault.xctoolchain/usr/bin/clang -x objective-c -arch armv7 -fmessage-length=0 -fdiagnostics-show-note-include-stack -fmacro-backtrace-limit=0 -std=gnu99 -fobjc-arc -fmodules -gmodules -fmodules-cache- [...]

fembed-bitcode标志

如果在其他C标志中添加-fembed-bitcode标志,则编译时将向编译器发送两个标志。这可能会消除在另一个项目上链接的库中接收到的某些警告,但需要检查是否获得了预期的行为。 :)

(当我在其他C标志上测试使用-fembed-bitcode时,Xcode会发出警告clang:warning:argument unused during compilation:'-fembed-bitcode-marker'

BITCODE_GENERATION_MODE

另一方面,

如果您在User-defined Setting中设置BITCODE_GENERATION_MODE=bitcode,即使在构建阶段,文件也将使用标志-fembed-bitcode进行编译。

而且,如果您设置BITCODE_GENERATION_MODE=marker,则文件将使用标志-fembed-bitcode-marker进行编译,与操作阶段无关。

因此,如果要在每个操作(构建和存档)中启用位码,则最好使用BITCODE_GENERATION_MODE设置。

资源
  • SO: iOS库转换为BitCode

  • 1
    所以,最终,它们确实只是两种不同的实现方式,强制Xcode在不使用存档操作的情况下支持位码构建?只是显然“fembed-bitcode”将会与之一起抛出一个警告。 - heitortsergent
    3
    基本上是这样的。但是,如果您真的想将位码启用到所有操作中,我建议您使用BITCODE_GENERATION_MODE。重复的标志可能会导致更多的警告。 - Igor Castañeda Ferreira
    对于那些不太熟悉如何添加用户定义设置的人,请参考以下链接:https://developer.apple.com/library/ios/recipes/xcode_help-project_editor/Articles/AddingUserDefinedSetting.html - Jalakoo
    1
    编译后是否可以删除位码?例如,一个框架有位码,但使用者没有启用位码支持进行编译的情况下,需要在使用者能够成功编译之前删除位码。如果框架没有使用位码进行编译,而使用者启用了位码,则他们也无法编译自己的项目。因此,基本上问题是如何从二进制文件中剥离位码 :) - Avba
    @IgorCastañedaFerreira 这对我来说是完美的解决方案。我的情况是两个标志都被设置了,在Xcode 8.3.2(可能更早)中,这不再在输出中生成位码。谢谢! - Joe Steele
    显示剩余3条评论

    网页内容由stack overflow 提供, 点击上面的
    可以查看英文原文,
    原文链接