Virtuelles A/B implementieren

Wenn Sie virtuelle A/B-Tests auf einem neuen Gerät implementieren oder ein eingeführtes Gerät nachrüsten möchten, müssen Sie Änderungen am gerätespezifischen Code vornehmen.

Build-Flags

Geräte mit virtuellem A/B-System müssen als A/B-Gerät konfiguriert und mit dynamischen Partitionen gestartet werden.

Legen Sie für Geräte, die mit virtuellem A/B gestartet werden, fest, dass die Basiskonfiguration des virtuellen A/B-Geräts übernommen werden soll:

$(call inherit-product, \
    $(SRC_TARGET_DIR)/product/virtual_ab_ota.mk)

Geräte, die mit virtuellem A/B eingeführt werden, benötigen nur halb so viel Boardgröße für BOARD_SUPER_PARTITION_SIZE, da B-Slots nicht mehr im Super sind. Das heißt, BOARD_SUPER_PARTITION_SIZE muss größer oder gleich Summe(Größe der Updategruppen) + Overhead sein, die wiederum größer oder gleich Summe(Größe der Partitionen) + Overhead sein muss.

Wenn Sie unter Android 13 und höher komprimierte Snapshots mit virtuellem A/B-Verzeichnis aktivieren möchten, übernehmen Sie die folgende Basiskonfiguration:

$(call inherit-product, $(SRC_TARGET_DIR)/product/generic_ramdisk.mk)
$(call inherit-product, \
    $(SRC_TARGET_DIR)/product/virtual_ab_ota/vabc_features.mk)

Dadurch werden Nutzerbereichs-Snapshots mit virtuellem A/B-Modus bei Verwendung einer operativen Komprimierungsmethode aktiviert. Sie können dann die Komprimierungsmethode auf eine der unterstützten Methoden, zstd und lz4, konfigurieren. Unter Android 15 kann die Komprimierung weiter an die Anforderungen des Geräts angepasst werden. Weitere Informationen finden Sie unter Komprimierung der Feinabstimmung.

PRODUCT_VIRTUAL_AB_COMPRESSION_METHOD := lz4
PRODUCT_VIRTUAL_AB_COMPRESSION_FACTOR := 65536

Wenn Sie für Android 12 komprimierte Snapshots mit Virtual A/B aktivieren möchten, übernehmen Sie die folgende Basiskonfiguration:

$(call inherit-product, $(SRC_TARGET_DIR)/product/generic_ramdisk.mk)
$(call inherit-product, \
    $(SRC_TARGET_DIR)/product/virtual_ab_ota/compression.mk)

XOR-Komprimierung

Bei Geräten, die auf Android 13 und höher upgraden, ist die XOR-Komprimierungsfunktion standardmäßig nicht aktiviert. Fügen Sie der Datei .mk des Geräts Folgendes hinzu, um die XOR-Komprimierung zu aktivieren.

PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.compression.xor.enabled=true

Die XOR-Komprimierung ist standardmäßig für Geräte aktiviert, die von android_t_baseline.mk abgeleitet sind.

Zusammenführung von Userspaces

In der modernen Version von Virtual A/B (Android T und höher) erfolgt die Snapshot-Zusammenführung ausschließlich im Nutzerbereich. Diese Änderung wird durch „snapuserd“ und „dm-user“ ermöglicht. Auf Geräten, die mit Android 13 oder höher ausgeliefert werden, ist die Zusammenführung des Nutzerbereichs standardmäßig aktiviert. Bei älteren Geräten, die auf diese Version aktualisiert werden, kann diese Eigenschaft so festgelegt werden:

PRODUCT_VENDOR_PROPERTIES += ro.virtual_ab.userspace.snapshots.enabled=true

Bootsteuerungs-HAL

Die Boot Control HAL bietet eine Schnittstelle für OTA-Clients zum Steuern von Boot-Slots. Für virtuelle A/B-Partitionen ist ein Minor-Version-Upgrade der Boot Control HAL erforderlich, da zusätzliche APIs erforderlich sind, um den Bootloader während des Flashens oder Zurücksetzens auf die Werkseinstellungen zu schützen. Die neueste Version der HAL-Definition finden Sie unter IBootControl.hal und types.hal.

// hardware/interfaces/boot/1.1/types.hal
enum MergeStatus : uint8_t {
    NONE, UNKNOWN, SNAPSHOTTED, MERGING, CANCELLED };

// hardware/interfaces/boot/1.1/IBootControl.hal
package android.hardware.boot@1.1;
interface IBootControl extends @1.0::IBootControl {
    setSnapshotMergeStatus(MergeStatus status)
        generates (bool success);
    getSnapshotMergeStatus()
        generates (MergeStatus status);
}
// Recommended implementation

Return<bool> BootControl::setSnapshotMergeStatus(MergeStatus v) {
    // Write value to persistent storage
    // e.g. misc partition (using libbootloader_message)
    // bootloader rejects wipe when status is SNAPSHOTTED
    // or MERGING
}

Änderungen an der Datei „/etc/fstab“

Die Integrität der Metadatenpartition ist für den Bootvorgang unerlässlich, insbesondere direkt nach der Anwendung eines OTA-Updates. Die Metadatenpartition muss also geprüft werden, bevor first_stage_init sie bereitstellt. Fügen Sie dazu dem Eintrag für /metadata das Flag check fs_mgr hinzu. Hier ein Beispiel:

/dev/block/by-name/metadata /metadata ext4 noatime,nosuid,nodev,discard,sync wait,formattable,first_stage_mount,check

Kernelanforderungen

Wenn Sie Snapshots aktivieren möchten, setzen Sie CONFIG_DM_SNAPSHOT auf true.

Fügen Sie für Geräte mit F2FS den Kernel-Patch f2fs: export FS_NOCOW_FL flag to user hinzu, um die Dateianpinning zu korrigieren. Fügen Sie außerdem den Kernel-Patch f2fs: support ausgerichtete angepinnte Datei ein.

Virtual A/B setzt auf Funktionen, die in der Kernelversion 4.3 hinzugefügt wurden: das Overflow-Statusbit in den Zielen snapshot und snapshot-merge. Alle Geräte, die mit Android 9 oder höher auf den Markt kommen, sollten bereits die Kernelversion 4.4 oder höher haben.

Zum Aktivieren komprimierter Snapshots ist die Kernelversion 4.19 erforderlich. Legen Sie CONFIG_DM_USER=m oder CONFIG_DM_USER=y fest. Bei der ersten Option (Modul) muss das Modul in das RAM-Disk der ersten Stufe geladen werden. Dazu fügen Sie dem Makefile des Geräts die folgende Zeile hinzu:

BOARD_GENERIC_RAMDISK_KERNEL_MODULES_LOAD := dm-user.ko

Änderungen an Fastboot-Tools

Android 11 nimmt folgende Änderungen am Fastboot-Protokoll vor:

  • getvar snapshot-update-status: gibt den Wert zurück, den der HAL der Bootsteuerung an den Bootloader übermittelt hat:
    • Wenn der Status MERGING ist, muss der Bootloader merging zurückgeben.
    • Wenn der Status SNAPSHOTTED ist, muss der Bootloader snapshotted zurückgeben.
    • Andernfalls muss der Bootloader none zurückgeben.
  • snapshot-update merge: Führt einen Zusammenführungsvorgang aus und startet bei Bedarf in die Wiederherstellung/fastbootd. Dieser Befehl ist nur gültig, wenn snapshot-update-status merging ist, und wird nur in fastbootd unterstützt.
  • snapshot-update cancel – Legt den Zusammenführungsstatus der HAL für die Bootsteuerung auf CANCELLED fest. Dieser Befehl ist ungültig, wenn das Gerät gesperrt ist.
  • erase oder wipe: Eine erase oder wipe von metadata, userdata oder eine Partition, die den Zusammenführungsstatus für die Boot Control HAL enthält, sollte den Snapshot-Zusammenführungsstatus prüfen. Wenn der Status MERGING oder SNAPSHOTTED lautet, sollte das Gerät den Vorgang abbrechen.
  • set_active: Bei einem set_active-Befehl, mit dem der aktive Slot geändert wird, sollte der Status der Snapshot-Datenzusammenführung geprüft werden. Wenn der Status MERGING lautet, sollte das Gerät den Vorgang abbrechen. Der Slot kann im Status SNAPSHOTTED sicher geändert werden.

Diese Änderungen sollen verhindern, dass ein Gerät versehentlich nicht mehr bootfähig ist, sie können jedoch automatisierte Tools stören. Wenn die Befehle zum Flashen aller Partitionen verwendet werden, z. B. fastboot flashall, wird die folgende Vorgehensweise empfohlen:

  1. Abfrage getvar snapshot-update-status
  2. Wenn merging oder snapshotted, geben Sie snapshot-update cancel ein.
  3. Fahren Sie mit den Schritten zum Flashen fort.

Speicheranforderungen reduzieren

Für Geräte, denen nicht der gesamte A/B-Speicherplatz in super zugewiesen ist und die bei Bedarf /data verwenden sollen, wird dringend empfohlen, das Blockzuordnungstool zu verwenden. Das Blockzuordnungstool sorgt für eine einheitliche Blockzuweisung zwischen Builds, wodurch unnötige Schreibvorgänge auf den Snapshot reduziert werden. Weitere Informationen finden Sie unter Größe der Over-the-air-Aktualisierung reduzieren.

OTA-Komprimierungsalgorithmen

OTA-Pakete können für verschiedene Leistungsmesswerte optimiert werden. Android bietet mehrere unterstützte Komprimierungsmethoden (lz4, zstd und none), die Kompromisse zwischen Installationszeit, COW-Speicherplatznutzung, Bootzeit und Snapshot-Merge-Zeit erfordern. Die Standardoption für virtuelle Abs mit Komprimierung ist lz4 compression method.

Komprimierung für Feinabstimmung

Komprimierungsalgorithmen können mit zwei Methoden weiter angepasst werden: (Komprimierungsstufe) (der auf Kosten der Geschwindigkeit erzielte Komprimierungsgrad) und (Komprimierungsfaktor) (maximale komprimierbare Fenstergröße). Die Komprimierungsstufe ist für bestimmte Algorithmen wie zstd verfügbar. Wenn Sie die Stufe ändern, müssen Sie einen Kompromiss zwischen Geschwindigkeit und Komprimierungsverhältnis erzielen. Der Komprimierungsfaktor beschreibt die maximale Größe des Komprimierungsfensters, die bei der OTA-Installation verwendet wird. Standardmäßig ist 64 kB festgelegt. Diese Einstellung kann jedoch überschrieben werden, indem der Build-Parameter PRODUCT_VIRTUAL_AB_COMPRESSION_FACTOR angepasst wird. Unterstützte Komprimierungsfaktoren: 4k, 8k, 16k, 32k, 64k, 128k und 256k.

PRODUCT_VIRTUAL_AB_COMPRESSION_FACTOR := 65536

Inkrementelle OTA-Updates auf Google Pixel 8 Pro

Installationszeit ohne Phase nach der Installation COW-Speicherplatznutzung Bootzeit nach OTA-Update Zeitpunkt der Snapshot-Zusammenführung
lz4 18 Min. 15 Sek. 2,5 GB 32,7 Sek. 98,6 Sek.
zstd 24 Min. 49 Sek. 2,05 GB 36,3 Sek. 133,2 Sek.
Keine 16 Min. 42 Sek. 4,76 GB 28,7 Sek. 76,6 Sek.

Vollständiges OTA-Update auf Pixel 8 Pro

Installationszeit ohne Phase nach der Installation COW-Speicherplatznutzung Bootzeit nach OTA-Update Zeitpunkt der Snapshot-Zusammenführung
lz4 15 Min. 11 Sek. 4,16 GB 17,6 Sek. 82,2 Sek.
zstd 16 Min. 19 Sek. 3,46 GB 21,0 Sek. 106,3 Sek.
Keine 13 Min. 33 Sek. 6,39 GB 18,5 Sek. 92,5 Sek.