Sie können das APEX-Dateiformat verwenden, um ein Paket zu verpacken und untergeordnete Android-Betriebssystemmodule installieren. Sie ermöglicht unabhängige Erstellung und Installation von Komponenten wie nativen Diensten und Bibliotheken, HAL Implementierungen, Firmware, Konfigurationsdateien usw.
Anbieter-APEX werden vom Build-System automatisch im /vendor
installiert
und zur Laufzeit von apexd
aktiviert werden, genau wie APEXes in anderen
Partitionen.
Anwendungsfälle
Modularisierung von Anbieterbildern
APEX erleichtert die natürliche Bündelung und Modularisierung von Funktionen Implementierungen von Anbieter-Images.
Wenn Anbieter-Images als Kombination aus unabhängigen Anbietern erstellt werden APEX: Gerätehersteller können ganz einfach die gewünschten welche Implementierungen auf ihrem Gerät erwünscht sind. Hersteller können sogar einem neuen Anbieter-APEX, wenn keiner der bereitgestellten APEXs den Anforderungen entspricht oder brandneue Hardware.
Beispielsweise kann ein OEM sein Gerät mit AOSP-WLAN zusammensetzen. APEX-Implementierung, SoC-Bluetooth-Implementierung APEX und ein benutzerdefinierter OEM Telefonieimplementierung APEX.
Eine Implementierung mit so vielen Abhängigkeiten zwischen die Komponenten eines Anbieters erfordern eine sorgfältige Koordination und Nachverfolgung. Durch das Einbinden aller Komponenten (einschließlich Konfigurationsdateien und zusätzlichen Bibliotheken) in APEXes mit klar definierte Schnittstellen an jedem Punkt der funktionsübergreifenden Kommunikation, Komponenten austauschbar werden.
Entwickleriteration
Mit Vendor APEX können Entwickler bei der Entwicklung von Anbietermodulen schneller iterieren, indem sie Bündeln einer vollständigen Funktionsimplementierung wie WLAN-HAL in einem Anbieter Apex. Entwickler können das Anbieter-APEX dann individuell erstellen und per Push zum Testen übertragen. anstatt das gesamte Anbieter-Image neu zu erstellen.
Dies vereinfacht und beschleunigt den Iterationszyklus für Entwickler, die arbeiten hauptsächlich an einem Funktionsbereich und möchten nur diesen iterieren. Bereich.
Die natürliche Bündelung eines Elementbereichs in einem APEX vereinfacht ebenfalls den Prozess. des Erstellens, Übertragens und Testens von Änderungen für diesen Funktionsbereich. Beispiel: Bei der Neuinstallation eines APEX werden alle gebündelten Bibliotheks- oder Konfigurationsdateien automatisch aktualisiert. die im APEX enthalten sind.
Das Bündeln eines Funktionsbereichs in einem APEX vereinfacht außerdem das Debugging oder das Zurücksetzen, wenn wird ein unerwünschtes Geräteverhalten beobachtet. Wenn die Telefoniefunktion in können Entwickler versuchen, eine ältere Telefonielösung zu installieren, Implementierung von APEX auf einem Gerät (ohne einen vollständigen Build flashen zu müssen) und um zu sehen, ob das Verhalten wieder funktioniert.
Beispielworkflow:
# Build the entire device and flash. OR, obtain an already-flashed device.
source build/envsetup.sh && lunch oem_device-userdebug
m
fastboot flashall -w
# Test the device.
... testing ...
# Check previous behavior using a vendor APEX from one week ago, downloaded from
# your continuous integration build.
... download command ...
adb install <path to downloaded APEX>
adb reboot
... testing ...
# Edit and rebuild just the APEX to change and test behavior.
... edit APEX source contents ...
m <apex module name>
adb install out/<path to built APEX>
adb reboot
... testing ...
Beispiele
Grundlegende Informationen
Informationen zu generischem APEX finden Sie auf der Hauptseite des APEX-Dateiformats Informationen, einschließlich Geräteanforderungen, Details zum Dateiformat und Installationsschritten.
Wenn Sie in Android.bp
das Attribut vendor: true
festlegen, wird ein APEX-Modul zu einem
Anbieter APEX.
apex {
..
vendor: true,
..
}
Binärdateien und gemeinsam genutzte Bibliotheken
Ein APEX enthält transitive Abhängigkeiten in der APEX-Nutzlast, es sei denn, sie stabile Oberflächen haben.
Zu den stabilen nativen Schnittstellen für APEX-Abhängigkeiten des Anbieters gehören unter anderem cc_library
mit
stubs
, ndk_library
oder llndk_library
. Diese Abhängigkeiten sind von der
Paketerstellung und Abhängigkeiten werden im APEX-Manifest aufgezeichnet. Das Manifest ist
von linkerconfig
verarbeitet, sodass die externen nativen Abhängigkeiten
zur Laufzeit verfügbar.
Im Gegensatz zu APEX in der Partition /system
sind Anbieter-APEX in der Regel an eine
bestimmte VNDK-Version. VNDK-Bibliotheken garantieren die ABI-Stabilität im
damit wir VNDK-Bibliotheken als stabil behandeln und die Größe des Anbieters
APEXes durch Ausschließen aus den APEXes mithilfe der use_vndk_as_stable
Property.
Im folgenden Snippet enthält das APEX sowohl das Binärprogramm (my_service
) als auch
seine instabilen Abhängigkeiten (*.so
-Dateien). Es enthält keine VNDK-Bibliotheken,
auch wenn my_service
mit VNDK-Bibliotheken wie libbase
erstellt wird. Stattdessen können Sie
Laufzeit my_service
verwendet libbase
aus VNDK-Bibliotheken, die vom
System.
apex {
..
vendor: true,
use_vndk_as_stable: true,
binaries: ["my_service"],
..
}
Im Snippet unten enthält das APEX die gemeinsam genutzte Bibliothek.
my_standalone_lib
und alle zugehörigen instabilen Abhängigkeiten (wie oben beschrieben) werden erkannt.
apex {
..
vendor: true,
use_vndk_as_stable: true,
native_shared_libs: ["my_standalone_lib"],
..
}
HAL-Implementierungen
Um eine HAL-Implementierung zu definieren, stellen Sie die entsprechenden Binärdateien und Bibliotheken bereit in einem Anbieter-APEX ähnlich den folgenden Beispielen:
Um die HAL-Implementierung vollständig zu kapseln, sollte APEX auch alle relevante VINTF-Fragmente und Init-Skripts.
VINTF-Fragmente
VINTF-Fragmente können von einem Anbieter-APEX bereitgestellt werden, wenn sich die Fragmente
etc/vintf
des APEX.
Verwenden Sie die Eigenschaft prebuilts
, um die VINTF-Fragmente in APEX einzubetten.
apex {
..
vendor: true,
prebuilts: ["fragment.xml"],
..
}
prebuilt_etc {
name: "fragment.xml",
src: "fragment.xml",
sub_dir: "vintf",
}
Initialisierungsskripte
APEX-Dateien können init-Skripts auf zwei Arten eingefügt werden: (A) als vordefinierte Textdatei im
APEX-Nutzlast oder (B) ein reguläres Initialisierungsskript in /vendor/etc
. Sie können sowohl
für dasselbe APEX.
Initialisierungsskript in APEX:
prebuilt_etc {
name: "myinit.rc",
src: "myinit.rc"
}
apex {
..
vendor: true,
prebuilts: ["myinit.rc"],
..
}
Init-Skripts in APEX-Dateien dürfen nur service
Definitionen haben. Initialisierungsskripte
in Anbieter-APEXes können auch on <property>
-Anweisungen haben.
Seien Sie vorsichtig bei der Verwendung von on
-Anweisungen. Da INIT-Skripts in APEX-Dateien
nach der Aktivierung von APEXs geparst und ausgeführt werden, einige Ereignisse oder Eigenschaften
können nicht verwendet werden. Verwende apex.all.ready=true
, um Aktionen so früh wie möglich auszulösen.
Firmware
Beispiel:
Betten Sie die Firmware mit dem Modultyp prebuilt_firmware
in ein APEX des Anbieters ein:
folgt.
prebuilt_firmware {
name: "my.bin",
src: "path_to_prebuilt_firmware",
vendor: true,
}
apex {
..
vendor: true,
prebuilts: ["my.bin"], // installed inside APEX as /etc/firmware/my.bin
..
}
prebuilt_firmware
Module sind in <apex name>/etc/firmware
installiert
des APEX-Verzeichnisses. ueventd
scannt /apex/*/etc/firmware
Verzeichnisse nach
Firmware-Module zu finden.
Die file_contexts
des APEX sollte alle Firmware-Nutzlasteinträge kennzeichnen.
um sicherzustellen, dass ueventd
zur Laufzeit auf diese Dateien zugreifen kann;
Normalerweise reicht das Label vendor_file
aus. Beispiel:
(/.*)? u:object_r:vendor_file:s0
Kernelmodule
Betten Sie Kernelmodule wie im Folgenden beschrieben als vordefinierte Module in eine Anbieter-APEX ein.
prebuilt_etc {
name: "my.ko",
src: "my.ko",
vendor: true,
sub_dir: "modules"
}
apex {
..
vendor: true,
prebuilts: ["my.ko"], // installed inside APEX as /etc/modules/my.ko
..
}
Der file_contexts
des APEX sollte alle Nutzlasteinträge des Kernelmoduls mit einem Label versehen
ordnungsgemäß funktioniert. Beispiel:
/etc/modules(/.*)? u:object_r:vendor_kernel_modules:s0
Kernelmodule müssen explizit installiert werden. Beispiel für ein init-Script
in der Anbieterpartition zeigt die Installation über insmod
an:
my_init.rc
:
on early-boot
insmod /apex/myapex/etc/modules/my.ko
..
Laufzeitressourcen-Overlays
Beispiel:
Overlays für Laufzeitressourcen in einen Anbieter-APEX einbetten
mithilfe der Eigenschaft rros
.
runtime_resource_overlay {
name: "my_rro",
soc_specific: true,
}
apex {
..
vendor: true,
rros: ["my_rro"], // installed inside APEX as /overlay/my_rro.apk
..
}
Andere Konfigurationsdateien
Anbieter-APEX unterstützen verschiedene andere Konfigurationsdateien, die in der Regel beim Anbieter zu finden sind als vorgefertigte Daten in Anbieter-APEXs partitionieren und es kommen weitere hinzu.
Beispiele:
- XMLs zur Deklaration von Funktionen
- Sensoren verwenden XMLs als vorinstalliert im Sensor-HAL-Anbieter APEX
- Konfigurationsdateien der Eingabe
- Touchscreen-Konfigurationen als vorkonfiguriert in einem Anbieter-APEX (nur Konfiguration)
Zusätzliche Entwicklungsfunktionen
APEX-Auswahl beim Start
Beispiel:
Entwickler können auch mehrere Versionen von Anbieter-APEX installieren, die den gleichen
denselben APEX-Namen und -Schlüssel und wählen Sie aus, welche Version jeweils aktiviert wird.
mit persistenten Sysprops. Bei bestimmten Anwendungsfällen für Entwickler
einfacher als die Installation einer neuen APEX-Kopie mit adb install
.
Beispiele für Anwendungsfälle:
- 3 Versionen des WLAN-HAL-Anbieters APEX installieren: QA-Teams können manuelle oder automatische Tests mit einer Version, führen Sie einen Neustart mit einer anderen Version durch und die Tests erneut ausführen und die Endergebnisse vergleichen.
- Installieren Sie zwei Versionen des Kamera-HAL-Anbieters APEX, aktuell und experimentell:Dogfooder können die experimentelle Version ohne eine zusätzliche Datei herunterladen und installieren, damit sie einfach zurückwechseln können.
Beim Start sucht apexd
nach Sysprops mit einem bestimmten Format,
die richtige APEX-Version zu aktivieren.
Für den Attributschlüssel werden folgende Formate erwartet:
- Bootconfig
- Wird zum Festlegen des Standardwerts in
BoardConfig.mk
verwendet. androidboot.vendor.apex.<apex name>
- Wird zum Festlegen des Standardwerts in
- Persistente Sysprop
- Wird zum Ändern des Standardwerts auf einem bereits gestarteten Gerät verwendet.
- Überschreibt den bootconfig-Wert, falls vorhanden.
persist.vendor.apex.<apex name>
Der Wert der Eigenschaft sollte der Dateiname des APEX sein. Dieser sollte aktiviert.
// Default version.
apex {
name: "com.oem.camera.hal.my_apex_default",
vendor: true,
..
}
// Non-default version.
apex {
name: "com.oem.camera.hal.my_apex_experimental",
vendor: true,
..
}
Die Standardversion sollte auch mit bootconfig in
BoardConfig.mk
:
# Example for APEX "com.oem.camera.hal" with the default above:
BOARD_BOOTCONFIG += \
androidboot.vendor.apex.com.oem.camera.hal=com.oem.camera.hal.my_apex_default
Ändere nach dem Hochfahren des Geräts die aktivierte Version, indem du die persistentes Sysprop:
$ adb root;
$ adb shell setprop \
persist.vendor.apex.com.oem.camera.hal \
com.oem.camera.hal.my_apex_experimental;
$ adb reboot;
Wenn das Gerät die Aktualisierung von Bootconfig nach dem Flashen unterstützt (z. B. über fastboot
oem
-Befehle), muss das Attribut „bootconfig“ für die Mehrfachinstallation
Außerdem ändert APEX die beim Hochfahren aktivierte Version.
Für virtuelle Referenzgeräte basierend auf Sepia:
können Sie mit dem Befehl --extra_bootconfig_args
das Attribut bootconfig festlegen
direkt während der Markteinführung. Beispiel:
launch_cvd --noresume \
--extra_bootconfig_args "androidboot.vendor.apex.com.oem.camera.hal:=com.oem.camera.hal.my_apex_experimental";