Method to determine whether a binary contains Bitc

2019-08-12 17:02发布

问题:

In my search for a method to determine if a iOS binary was build with Bitcode, I found the following post:

How to check if a framework is BITCODE supported for Xcode7

Here, the following method was suggested to determine if bitcode is present in a binary:

$ otool -l libName.o | grep __LLVM

However, I have tried this on several binaries with no success. One of them is a library I know has bitcode since after I changed the flag on its project a build error went away. Another one of them is a binary for a file extension, build using Archive. And another is for apple watch.

I believe all of the above binaries should have Bitcode, and yet I always get no results from the above command.

Does anyone know any other method that works with the latest binaries?

I'm using XCode 7.2 and 10.10.5 in case it matters.

UPDATE: Here is an example of a file which is supposed to have bitcode but the above command doesn't return anything. It is a binary from a test File Provider. I generated it via Archive and Deploy as Ad Hoc, and made sure the setting for bitcode was on for the target.

https://www.dropbox.com/s/eyuzs5j1t7nsq6t/CustomDocumentProviderFileProvider?dl=0

回答1:

This seems to be a problem with otool as reported here. Use file to get a list of architectures and then supply the architecture to otool. Given a fat binary with Bitcode for armv7, arm64, i386 and x86_64:

$ file lib.a 
lib.a: Mach-O universal binary with 4 architectures
lib.a (for architecture armv7): current ar archive random library
lib.a (for architecture i386):  current ar archive random library
lib.a (for architecture x86_64):    current ar archive random library
lib.a (for architecture arm64): current ar archive random library

$ otool -arch armv7 -l lib.a | grep bitcode
sectname __bitcode

According to this question, otool does not report Bitcode for x86_64 and i368.

CustomDocumentProviderFileProvider does not seem to contain Bitcode:

$ file CustomDocumentProviderFileProvider
CustomDocumentProviderFileProvider: Mach-O universal binary with 2 architectures
CustomDocumentProviderFileProvider (for architecture armv7):    Mach-O executable arm
CustomDocumentProviderFileProvider (for architecture arm64):    Mach-O 64-bit executable

$ otool -arch armv7 -l CustomDocumentProviderFileProvider | grep bit
$


回答2:

Disclaimer: I'm the author of LibEBC.

You can use ebcutil to determine whether bitcode is present in any binary (Mach-O, ELF) or library (.a/.dylib/.so).

https://github.com/JDevlieghere/LibEBC



回答3:

As of today, the technique which works for me is the one mentioned in this answer from another SO thread. Specifically, for a (dynamic) framework named MyLib and containing those two device architectures:

otool -arch armv7 MyLib.framework/MyLib | grep LLVM
otool -arch arm64 MyLib.framework/MyLib | grep LLVM


回答4:

If you have a fat binary, then you need to run otool -l on a specific slice. For instance, in the following example I chose arm64:

otool -arch arm64 -l MyFramework.framework/MyFramework | grep -a4 __LLVM

In the output you should check:

  1. if there is at least one section named __LLVM
  2. if the size is greater than zero