Le librerie condivise Android si evolvono di volta in volta. Mantenere aggiornati i file binari precompilati richiede uno sforzo considerevole. In Android 9 o versioni precedenti, i file binari predefiniti che dipendono da librerie o ABI rimosse non riescono a collegarsi solo in fase di esecuzione. Gli sviluppatori devono tracciare i log per trovare i file binari precompilati obsoleti. In Android 10 viene introdotto un controllo degli utilizzi ABI basato su simboli. Il controllo può rilevare i file binari precompilati obsoleti in fase di compilazione, in modo che gli sviluppatori di librerie condivise possano sapere quali file binari precompilati potrebbero essere danneggiati dalla modifica e quali file binari precompilati devono essere ricompilati.
Controllo degli utilizzi ABI basato su simboli
Il controllo degli utilizzi ABI basato su simboli emula il linker dinamico Android sull'host. Il controllo collega il binario precostruito con le dipendenze del binario precostruito e controlla se tutti i simboli non definiti sono risolti.
Innanzitutto, il controllo controlla l'architettura di destinazione del binario precompilato. Se il file binario precostruito non è destinato all'architettura ARM, AArch64, x86 o x86-64, il controllo ignora il file binario precostruito.
In secondo luogo, le dipendenze del binario precompilato devono essere elencate in LOCAL_SHARED_LIBRARIES
o shared_libs
. Il sistema di compilazione risolve i nomi dei moduli nella variante corrispondente (cioè core
vs. vendor
) delle librerie condivise.
In terzo luogo, il controllo confronta le voci DT_NEEDED
con LOCAL_SHARED_LIBRARIES
o shared_libs
. In particolare, il controllo estrae la voce DT_SONAME
da ciascuna libreria condivisa e confronta queste DT_SONAME
con le voci DT_NEEDED
registrate nel binario precostruito. Se c'è una mancata corrispondenza, viene emesso un messaggio di errore.
In quarto luogo, il controllo risolve i simboli non definiti nel binario precostruito. Quei simboli non definiti devono essere definiti in una delle dipendenze e il legame del simbolo deve essere GLOBAL
o WEAK
. Se non è possibile risolvere un simbolo non definito, viene emesso un messaggio di errore.
Proprietà del modulo predefinite
Le dipendenze del binario predefinito devono essere specificate in uno dei seguenti:
- Android.bp:
shared_libs: ["libc", "libdl", "libm"],
- Android.mk:
LOCAL_SHARED_LIBRARIES := libc libdl libm
Se il file binario predefinito è progettato per avere alcuni simboli non definiti irrisolvibili , specificare uno dei seguenti:
- Android.bp:
allow_undefined_symbols: true,
- Android.mk:
LOCAL_ALLOW_UNDEFINED_SYMBOLS := true
Per fare in modo che il binario predefinito ignori il controllo del file ELF, specificare una delle seguenti opzioni:
- Android.bp:
check_elf_files: false,
- Android.mk:
LOCAL_CHECK_ELF_FILES := false
Esegui il controllo
Il controllo copre tutti i moduli ELF predefiniti durante il processo di creazione di Android.
Per eseguire il controllo da solo per tempi di consegna più rapidi:
m check-elf-files
Riparatore di errori ABI
Il correttore automatico può aiutare a risolvere gli errori di controllo ABI. È sufficiente eseguire il fissatore con Android.bp/Android.mk come input e il fissatore stamperà la correzione suggerita su stdout. Facoltativamente, esegui il correttore con l'opzione --in-place
per aggiornare direttamente Android.bp/Android.mk con la correzione suggerita.
Per Android.bp,
m fix_android_bp_prebuilt
# Print the fixed Android.bp to stdout.
fix_android_bp_prebuilt <path-to-Android.bp>
# Update the Android.bp in place.
fix_android_bp_prebuilt --in-place <path-to-Android.bp>
Per Android.mk,
m fix_android_mk_prebuilt
# Print the fixed Android.mk to stdout.
fix_android_mk_prebuilt <path-to-Android.mk>
# Update the Android.mk in place.
fix_android_mk_prebuilt --in-place <path-to-Android.mk>