Xcode 6.1版本在新建一个工程的时候,会给我们做一些默认的Build Settings,其中有一种很重要的就是Architecture的设置,先来看一张图片,如下所示:
在第二行的Architectures中,设置的是标准的架构,里面包括armv7,arm64.这个编译选项指定了工程将被编译成支持哪些指令集,支持指令集是通过编译生成对应的二进制数据包实现的,如果支持的指令集数目有多个,就会编译出包含多个指令集代码的数据包,造成最终编译的包很大。
最下面一行蓝色显示的Valid Architectures 这个列表指定的可支持的指令集和Architectures中的指令集的交集,将是xcode最终生成的二进制的包所支持的指令集。
上面结果的指令集交集是arm64和armv7,因此生产的最终二进制包能够支持的指令集就是这两种。
还有一个Build Active Architecture Only 这里是个bool值。这个编译用于设置是否编译当前使用的设备对应的arm指令集。比如你在调试的时候用的设备是iPhone5,那么编译生成的就会是iPhone5所支持的arm指令集,也就是arm64.前提是你xcode成功连接设备,并且该值设为YES的情况,如果你没连接上设备,那么就算这个值设置为YES,生成的二进制所支持的arm指令集,还是那两者之间的交集。通常情况下你在Debug版本时候可以设置YES,Release版本的时候设置为NO。因为Release版本是用来发布的,编译器会给我门做一些优化。Debug版本一般是我们用来测试的。跟随设备的arm指令集是很有必要的。
注意一点:指令集是向下兼容的。比如你的设备是armv7s指令集,那么它也可以兼容运行比armv7s版本更低的指令集:armv7,armv64等。
再来看看各种设备所对应的arm指令集(1G代表一代,2G代表二代)吧:
armv6:iPhone 2G/3G ,iPod 1G/2G
armv7: iPhone 3GS/4/4S ,iPod 3G/4G,iPad 1G/2G/3G,iPad Mini 1
armv7s: iPhone5 ,iPhone5C,iPad4
armv8/arm64:iPhone 5S,iPad5 iPad Mini 2
在以前xcode 5编译的ios7程序包,包含了32位和64位两套二进制代码,在32位的ios系统上会调用32位的二进制代码,在64位系统上会调用64位二进制代码,以此来解决向后兼容问题,那么32位的app在没有重新编译的时候能否在64位os中运行呢,答案是肯定的,在64位os中,系统它带有两套Farmework,一套是32位的,一套是64位的。当64位系统运行原来32的app时候,它会调用32的的framework作为底层支持。
在我做公司的项目的时候,用到了第三方社交分享静态库它并没有支持64位的架构,发现如果加进来,会编译失败,先来看看下图:
看,它忽略了那个静态库文件导致链接失败了,然后我查看了静态库所支持的架构, 打开终端输入查看命令 lipo -info xxx.a,结果如下:
发现了这个静态库只支持armv7 armv7s i386 .而在我的工程中Valid Architectures和Architectures中均包含了arm64的指令集,这就是说明我需要编译的app最终要支持arm64的,而程序中用到的静态库并没有arm64,所以才导致了出错,因此在Valid Architectures中把arm64去掉,那么就可以正常编译通过了。