Android ABI
- 不同的 Android 设备使用不同的 CPU,而不同的 CPU 支持不同的指令集。CPU 与指令集的每种组合都有专属的应用二进制接口 (ABI)。ABI 包含以下信息:
- 可使用的 CPU 指令集(和扩展指令集)。
- 运行时内存存储和加载的字节顺序。Android 始终是 little-endian。
- 在应用和系统之间传递数据的规范(包括对齐限制),以及系统调用函数时如何使用堆栈和寄存器。
- 可执行二进制文件(例如程序和共享库)的格式,以及它们支持的内容类型。Android 始终使用 ELF。
- 如何重整 C++ 名称。
NDK 支持的 ABI:armeabi-v7a/arm64-v8a/x86/x86_64
# 简单的了解:
armeabi-v7a: 第7代及以上的 ARM 处理器。2011年15月以后的生产的大部分Android设备都使用它.
arm64-v8a: 第8代、64位ARM处理器,很少设备,三星 Galaxy S6是其中之一。
armeabi: 第5代、第6代的ARM处理器,早期的手机用的比较多。
x86: 平板、模拟器用得比较多。
x86_64: 64位的平板。
# 默认情况下,Gradle(无论是通过 Android Studio 使用,还是从命令行使用)会针对所有非弃用 ABI 进行构建。这也就将每个 ABI 的二进制文件包括在单个 APK,与仅包含单个 ABI 的二进制文件的 APK 相比,默认生成的 APK 的体积要大得多。
如果需要限制应用支持的 ABI 集,请使用
abiFilters
。例如,要仅针对 64 位 ABI 进行构建,请在
build.gradle
中设置以下配置:
android {
defaultConfig {
ndk {
abiFilters 'arm64-v8a', 'x86_64'
}
}
}
当然这里要权衡的是:兼容性更广, APK 的体积也就更大。
补充: Android 目前强烈建议利用
app bundle
和
APK 拆分
减小 APK 的大小,同时仍保持最大限度的设备兼容性。
补充:
⚠️ 在使用ABI的时候,我们需要当心,因为很容易运行报错。
如果如果需要限制应用支持的 ABI 集,请把每个ABI 集文件夹里都放置上对应的文件,以免出现不同机型在用到对应文件时,在对应文件夹找不到而出现运行报错的情况。
比如 :
当支持 armeabi 当手机运行需要用到 libjcore270.so 文件时,发现找不到文件,就会报错。
所以解决方案如下图:
还一种方式:直接将 armeabi 删掉,并在Gradle中不限制应用支持的 ABI 集,这样就会只存在一个 armeabi-v7a,当支持 armeabi 当手机运行需要用到 libjcore270.so 文件时,这时因为找不到 armeabi 文件夹,就会去找 armeabi-v7a里面的 libjcore270.so 文件。这也是可行的。