即使系统映像和供应商映像是基于不同版本的 Android 构建的,系统映像也可以使用 VNDK 快照为供应商映像提供正确的 VNDK 库。创建 VNDK 快照需要以快照形式捕获 VNDK 库,并使用版本号标记它们。供应商映像可以与特定的 VNDK 版本相关联,由此版本为供应商映像中的模块提供所需 ABI。但是,在同一 VNDK 版本中,VNDK 库必须具有稳定的 ABI。
VNDK 快照设计包括用于执行以下两项操作的方法:从当前系统映像生成预构建的 VNDK 快照以及将这些预构建的库安装到更高 Android 版本的系统分区。
VNDK 库简介
Android 8.0 中引入的 HIDL-HAL 支持单独升级系统分区和供应商分区。VNDK 定义了可与供应商代码关联的多个库集(VNDK-core、VNDK-SP 和 LL-NDK),并阻止供应商使用不在 VNDK 库集内的库。因此,如果将系统映像中合适的 VNDK 库集提供给供应商映像,就可以构建并运行供应商映像。
VNDK-core
VNDK-core 库集安装在 /system/lib[64]/vndk-${VER}
中,仅适用于 API 级别为 ${VER}
的供应商进程。系统进程不得使用这些库,而必须使用安装在 /system/lib[64]
中的库。由于每个进程都具有严格的命名空间限制,因此不会造成重复加载 VNDK-core 库。
如需在 VNDK-core 中添加库,请将以下内容添加到 Android.bp
中:
vendor_available: true, vndk: { enabled: true, },
VNDK-SP
VNDK-SP 库安装在 /system/lib[64]/vndk-sp-${VER}
中,适用于供应商进程和系统进程(通过安装在供应商分区中的 SP-HAL 库)。VNDK-SP 库可以重复加载。
如需在 VNDK-SP 中添加库,请将以下内容添加到 Android.bp
中:
vendor_available: true, vndk: { enabled: true, support_system_process: true, },
LL-NDK
LL-NDK 库安装在 /system/lib[64]
中。供应商模块可以使用 LL-NDK 存根库访问 LL-NDK 库的预选符号。LL-NDK 库必须支持向后兼容且具有 ABI 稳定性,以便旧版供应商模块使用新版 LL-NDK 库。由于 LL-NDK 具有 ABI 稳定特性,VNDK 快照无需包含旧版供应商映像的 LL-NDK 库。
VNDK 快照简介
Android 8.1 包含根据源代码构建的 VNDK 库。但是,对于更高版本的 Android,必须以快照形式捕获每个 VNDK 版本,并作为预构建版本提供,以便关联到旧版本的供应商映像。
从 Android 9 开始,新版 Android 将在 Android 源代码中至少包含旧版本 VNDK-core 和 VNDK-SP 目录的其中一个快照。在构建时,所需快照将安装到 /system/lib[64]/vndk-${VER}
和 /system/lib[64]/vndk-sp-${VER}
(供应商分区可以使用的目录),其中 ${VER}
是表示 VNDK 快照版本名称的字符串变量。
由于每个 VNDK 版本的 VNDK 快照库可能各不相同,因此 VNDK 快照还包含按以下格式安装的链接器命名空间配置:etc/ld.config.${VER}.txt
、/etc/llndk.libraries.${VER}.txt
和 /etc/vndksp.libraries.${VER}.txt
。
示例:升级系统映像和供应商映像
无需快照;无需针对 VNDK 快照进行其他配置即可构建。
示例:仅升级系统映像
必须在系统映像中包含供应商映像的 VNDK 快照和链接器命名空间配置文件。系统会自动配置链接器命名空间配置文件,以在 /system/lib[64]/vndk-${VER}
和 /system/lib[64]/vndk-sp-${VER}
中搜索 VNDK 库。
示例:升级系统映像,少量更改供应商映像
目前尚不支持根据 VNDK 快照构建供应商映像,因此您必须使用原始源代码单独构建供应商映像,然后按上一示例中所述升级系统映像。
VNDK 快照架构
为了让 Android 9 系统映像与 Android 8.1 供应商映像兼容,必须为 Android 9 系统映像提供与 Android 8.1 供应商映像匹配的 VNDK 快照,如下所示:
VNDK 快照设计包括以下方法:
- 为 VNDK-core 和 VNDK-SP 库生成快照。Android 9 包含一个脚本,您可以使用它来制作当前 VNDK build 的快照。此脚本将
/system/lib[64]/vndk-28
和/system/lib[64]/vndk-sp-28
中的所有库组合在一起,这些库是采用当前源代码以 VNDK 快照形式构建的,其中28
是 Android 9 的 VNDK 版本。快照还包含链接器命名空间配置文件/etc/ld.config.28.txt
、/etc/llndk.libraries.28.txt
和/etc/vndksp.libraries.28.txt
。生成的快照将用于较新的 Android 版本(高于 Android 9 的版本)。 - 从快照安装预构建的 VNDK-core 和 VNDK-SP 库。在 Android 9 中,VNDK 快照具有一组预构建的 VNDK-core 库和一组 VNDK-SP 库,以及链接器命名空间配置文件。如果您提供了要安装的 VNDK 快照版本列表,系统映像会在构建时将 VNDK 快照库安装到
/system/lib[64]/vndk-${VER}
和/system/lib[64]/vndk-sp-${VER}
目录,并将这些 VNDK 快照的链接器命名空间配置文件安装到/etc
目录。
VNDK 版本控制
每个 Android 版本都只有一个 VNDK 快照,并且 SDK 版本用作 VNDK 版本(这意味着 VNDK 版本必须采用整数,例如 Android 8.1 的 VNDK 版本为 27)。在 Android 版本发布时,VNDK 版本已确定。供应商分区使用的 VNDK 版本自动存储在 ro.vndk.version
属性中,可在运行时读取。然后,此版本可用于识别一些库的供应商 VNDK 版本及命名空间配置的 VNDK 快照版本。
构建 VNDK 库
make vndk
命令可用于构建具有 vndk:
{ enabled: true, … }
的库,包括依赖项和命名空间配置文件。如果设置了 BOARD_VNDK_VERSION := current
,则可使用 make
命令构建这些库。
由于这种构建方法不会从快照安装 VNDK 库,因此安装的 VNDK 库不具有 ABI 稳定性。但是,在 Android 版本发布时,当前 VNDK 版本的 ABI 已确定。此时,任何 ABI 损坏都属于构建错误,因此 Android 版本的补丁不得更改 VNDK 库的 ABI。