Utilizzare le librerie predefinite

L'NDK supporta l'utilizzo di librerie predefinite, sia statiche che condivise. Esistono due casi d'uso principali per questa funzionalità:

  • Distribuzione delle tue librerie a sviluppatori NDK di terze parti senza distribuire le tue origini.
  • Utilizzo di una versione predefinita delle tue librerie per velocizzare la build.

Questa pagina spiega come utilizzare le librerie predefinite.

Dichiarare una libreria predefinita

Devi dichiarare ogni libreria predefinita che utilizzi come modulo indipendente. Per farlo, segui questi passaggi:

  1. Assegna un nome al modulo. Questo nome non deve necessariamente essere uguale a quello della libreria predefinita.
  2. Nel file Android.mk del modulo, assegna a LOCAL_SRC_FILES il percorso della libreria predefinita che fornisci. Specifica il percorso relativo al valore della variabile LOCAL_PATH.

  3. Includi PREBUILT_SHARED_LIBRARY o PREBUILT_STATIC_LIBRARY, a seconda che utilizzi una libreria condivisa (.so) o statica (.a).

Ecco un esempio banale che presuppone che la libreria predefinita libfoo.so si trovi nella stessa directory del file Android.mk che la descrive.

LOCAL_PATH := $(call my-dir)

include $(CLEAR_VARS)
LOCAL_MODULE := foo-prebuilt
LOCAL_SRC_FILES := libfoo.so
include $(PREBUILT_SHARED_LIBRARY)

In questo esempio, il nome del modulo è uguale a quello della libreria predefinita.

Il sistema di build memorizza una copia della tua libreria condivisa predefinita in $PROJECT/obj/local e un'altra copia, priva delle informazioni di debug, in $PROJECT/libs/<abi>. Qui, $PROJECT è la directory principale del progetto.

Fare riferimento alla libreria predefinita da altri moduli

Per fare riferimento a una libreria predefinita di altri moduli, specificane il nome come valore della variabile LOCAL_STATIC_LIBRARIES o LOCAL_SHARED_LIBRARIES nei file Android.mk associati a questi altri moduli.

Ad esempio, la descrizione di un modulo che utilizza libfoo.so potrebbe essere la seguente:

include $(CLEAR_VARS)
LOCAL_MODULE := foo-user
LOCAL_SRC_FILES := foo-user.c
LOCAL_SHARED_LIBRARIES := foo-prebuilt
include $(BUILD_SHARED_LIBRARY)

Qui LOCAL_MODULE è il nome del modulo che fa riferimento al modulo predefinito; LOCAL_SHARED_LIBRARIES è il nome del modulo predefinito.

Esporta intestazioni per librerie predefinite

Il codice in foo-user.c dipende da dichiarazioni specifiche che normalmente risiedono in un file di intestazione, come foo.h, distribuite con la libreria predefinita. Ad esempio, foo-user.c potrebbe avere una riga simile alla seguente:

#include <foo.h>

In tal caso, devi fornire al compilatore l'intestazione e il relativo percorso di inclusione quando crei il modulo foo-user. Un modo semplice per eseguire questa operazione è utilizzare le esportazioni nella definizione del modulo predefinito. Ad esempio, se l'intestazione foo.h si trova nella directory include associata al modulo predefinito, puoi dichiararla come segue:

include $(CLEAR_VARS)
LOCAL_MODULE := foo-prebuilt
LOCAL_SRC_FILES := libfoo.so
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/include
include $(PREBUILT_SHARED_LIBRARY)

La definizione di LOCAL_EXPORT_C_INCLUDES qui assicura che il sistema di compilazione esporti il percorso nella directory include della libreria predefinita, precedendo tale percorso sul valore dell'elemento LOCAL_C_INCLUDES per il modulo che dipende da quest'ultimo.

Questa operazione consente al sistema di compilazione di trovare le intestazioni necessarie.

Esegui il debug delle librerie predefinite

Ti consigliamo di fornire librerie condivise predefinite contenenti simboli di debug. Il sistema di compilazione NDK rimuove sempre i simboli dalla versione della libreria in cui viene installato in $PROJECT/libs/<abi>/, ma puoi utilizzare la versione di debug per eseguire il debug con ndk-gdb.

Seleziona ABI per le librerie predefinite

Devi assicurarti di selezionare la versione corretta della libreria condivisa predefinita per l'ABI scelta come target. La variabile TARGET_ARCH_ABI nel file Android.mk può indirizzare il sistema di build alla versione appropriata della libreria.

Ad esempio, supponiamo che il progetto contenga due versioni della libreria libfoo.so:

armeabi/libfoo.so
x86/libfoo.so

Lo snippet seguente mostra come utilizzare TARGET_ARCH_ABI in modo che il sistema di build selezioni la versione appropriata della libreria:

include $(CLEAR_VARS)
LOCAL_MODULE := foo-prebuilt
LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/libfoo.so
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/include
include $(PREBUILT_SHARED_LIBRARY)

Se hai specificato armeabi come valore di TARGET_ARCH_ABI, il sistema di build utilizza la versione di libfoo.so che si trova nella directory armeabi. Se hai specificato x86 come valore TARGET_ARCH_ABI, il sistema di build utilizza la versione presente nella directory x86.