ビルド システムは、同じビルドで 2 つのターゲット CPU アーキテクチャ (64 ビットと 32 ビット) のバイナリのビルドをサポートしています。これはmultilib buildとして知られています。
ネイティブの静的ライブラリと共有ライブラリの場合、ビルド システムは、両方のアーキテクチャのバイナリをビルドするためのルールを設定します。製品構成 ( PRODUCT_PACKAGES
) は、依存関係グラフと共に、ビルドされてシステム イメージにインストールされるバイナリを決定します。
実行可能ファイルとアプリの場合、ビルド システムはデフォルトで 64 ビット バージョンのみをビルドしますが、この設定はグローバルなBoardConfig.mk
変数またはモジュール スコープの変数でオーバーライドできます。
製品構成
BoardConfig.mk
には、2 番目の CPU アーキテクチャと ABI を構成するための次の変数が含まれています。
-
TARGET_2ND_ARCH
-
TARGET_2ND_ARCH_VARIANT
-
TARGET_2ND_CPU_VARIANT
-
TARGET_2ND_CPU_ABI
-
TARGET_2ND_CPU_ABI2
build/target/board/generic_arm64/BoardConfig.mk
で例を確認できます。
multilib ビルドでは、 PRODUCT_PACKAGES
のモジュール名は、ビルド システムによって定義されている限り、32 ビットと 64 ビットの両方のバイナリをカバーします。依存関係によって取り込まれたライブラリの場合、32 ビット ライブラリは、別の 32 ビット ライブラリまたは実行可能ファイルで必要な場合にのみインストールされます。同じことが 64 ビット ライブラリにも当てはまります。
ただし、 make
コマンド ラインのモジュール名は 64 ビット バージョンのみを対象としています。たとえば、 lunch aosp_arm64-eng
を実行した後、 make libc
は 64 ビットの libc のみをビルドします。 32 ビットの libc をビルドするには、 make libc_32
を実行する必要があります。
Android.mk のモジュール定義
LOCAL_MULTILIB
変数を使用してビルドを 32 ビット/64 ビット用に構成し、グローバルTARGET_PREFER_32_BIT
変数をオーバーライドできます。
LOCAL_MULTILIB
を次のいずれかに設定します。
-
"both"
は、32 ビットと 64 ビットの両方をビルドします。 -
"32"
は 32 ビットのみをビルドします。 -
"64"
は 64 ビットのみをビルドします。 -
"first"
は、最初のアーキテクチャ (32 ビット デバイスでは 32 ビット、64 ビット デバイスでは 64 ビット) のみをビルドします。 -
""
がデフォルトです。ビルド システムは、モジュール クラスと、LOCAL_MODULE_TARGET_ARCH
やLOCAL_32_BIT_ONLY
などの他のLOCAL_
変数に基づいて、ビルドするアーキテクチャを決定します。
特定のアーキテクチャ用にモジュールをビルドする場合は、次の変数を使用します。
-
LOCAL_MODULE_TARGET_ARCH
この変数をarm x86 arm64
などのアーキテクチャのリストに設定します。ビルド中のアーキテクチャがそのリストに含まれている場合、現在のモジュールがビルド システムに含まれます。 -
LOCAL_MODULE_UNSUPPORTED_TARGET_ARCH
この変数はLOCAL_MODULE_TARGET_ARCH
の反対です。ビルド中のアーキテクチャがそのリストにない場合、現在のモジュールがビルド システムに含まれます。
これら 2 つの変数にはマイナーなバリエーションがあります。
-
LOCAL_MODULE_TARGET_ARCH_WARN
-
LOCAL_MODULE_UNSUPPORTED_TARGET_ARCH_WARN
ビルド システムは、リストされているアーキテクチャが原因で現在のモジュールがスキップされた場合に警告します。
特定のアーキテクチャのビルド フラグを設定するには、アーキテクチャ固有のLOCAL_
変数を使用します。アーキテクチャ固有のLOCAL_
変数は、アーキテクチャ サフィックスが付いた通常のLOCAL_
変数です。次に例を示します。
-
LOCAL_SRC_FILES_arm, LOCAL_SRC_FILES_x86,
-
LOCAL_CFLAGS_arm, LOCAL_CFLAGS_arm64,
-
LOCAL_LDFLAGS_arm, LOCAL_LDFLAGS_arm64,
これらの変数は、バイナリが現在そのアーキテクチャ用にビルドされている場合にのみ適用されます。
バイナリが現在 32 ビットまたは 64 ビット用にビルドされているかどうかに基づいてフラグを設定する方が簡単な場合があります。 LOCAL_
変数に_32
または_64
サフィックスを付けて使用します。次に例を示します。
-
LOCAL_SRC_FILES_32, LOCAL_SRC_FILES_64,
-
LOCAL_CFLAGS_32, LOCAL_CFLAGS_64,
-
LOCAL_LDFLAGS_32, LOCAL_LDFLAGS_64,
パスのインストール
以前は、 LOCAL_MODULE_PATH
を使用して、ライブラリをデフォルト以外の場所にインストールできました。たとえば、 LOCAL_MODULE_PATH := $(TARGET_OUT_SHARED_LIBRARIES)/hw
です。
multilib ビルドでは、代わりにLOCAL_MODULE_RELATIVE_PATH
を使用します。
LOCAL_MODULE_RELATIVE_PATH := hw
この形式では、64 ビット ライブラリと 32 ビット ライブラリの両方が正しい場所にインストールされます。
実行可能ファイルを 32 ビットと 64 ビットの両方でビルドする場合は、次の変数のいずれかを使用してインストール パスを区別します。
-
LOCAL_MODULE_STEM_32, LOCAL_MODULE_STEM_64
インストールされたファイル名を指定します。 -
LOCAL_MODULE_PATH_32, LOCAL_MODULE_PATH_64
インストール パスを指定します。
生成されたソース
マルチライブラリ ビルドで、ソース ファイルを$(local-intermediates-dir)
(または明示的な変数を指定$(intermediates-dir-for)
に生成すると、確実に動作しません。これは、中間で生成されたソースが 32 ビットと 64 ビットの両方のビルドで必要とされるためですが、 $(local-intermediates-dir)
は 2 つの中間ディレクトリのうちの 1 つしか指していません。
ビルド システムは、ソースを生成するための専用の multilib フレンドリーな中間ディレクトリを提供します。 $(local-generated-sources-dir)
または$(generated-sources-dir-for)
を呼び出して、ディレクトリのパスを取得できます。それらの使用法は、 $(local-intermediates-dir)
および$(intermediates-dir-for)
に似ています。
ソース ファイルがこの専用ディレクトリに生成され、 LOCAL_GENERATED_SOURCES
によって取得される場合、multilib ビルドで 32 ビットと 64 ビットの両方にビルドされます。
事前構築済み
multilib ビルドでは、 TARGET_ARCH
を (またはTARGET_2ND_ARCH
と一緒に) 使用して、ビルド済みのバイナリがターゲットとするアーキテクチャをビルド システムに伝えることはできません。代わりに、 LOCAL_
変数LOCAL_MODULE_TARGET_ARCH
またはLOCAL_MODULE_UNSUPPORTED_TARGET_ARCH
を使用してください。
これらの変数を使用すると、ビルド システムは、64 ビットの multilib ビルドで動作している場合でも、対応する 32 ビットのビルド済みバイナリを選択できます。
選択したアーキテクチャを使用してビルド済みバイナリのソース パスを計算する場合は、 $(get-prebuilt-src-arch)
呼び出します。
ODEX ファイルの生成
64 ビット デバイスの場合、デフォルトで、ブート イメージと Java ライブラリ用に 32 ビットと 64 ビットの両方の ODEX ファイルが生成されます。 APK の場合、デフォルトでは、主要な 64 ビット アーキテクチャに対してのみ ODEX を生成します。アプリが 32 ビットと 64 ビットの両方のプロセスで起動される場合は、 LOCAL_MULTILIB := both
を使用して、32 ビットと 64 ビットの両方の ODEX ファイルが生成されるようにします。アプリに 32 ビットまたは 64 ビットの JNI ライブラリがある場合、そのフラグはビルド システムにそれらを含めるように指示します。