Android 11, Genel Çekirdek Görüntüsü (GKI) kavramını tanıttı. GKI ile rastgele bir cihazın başlatılmasını sağlamak için Android 11 cihazlar, önyükleme görüntüsü başlığı sürüm 3'ü kullanabilir. 3. sürümde, tedarikçiye özgü tüm bilgiler boot
bölümünden çıkarılıp yeni bir vendor_boot
bölümüne taşınır. 5.4 Linux çekirdeğinde Android 11 ile başlatılan bir ARM64 cihaz, GKI ile testi geçmek için vendor_boot
bölümünü ve güncellenmiş boot
bölüm biçimini desteklemelidir.
Android 12 cihazlar, vendor_boot
bölümüne birden fazla tedarikçi ramdiski eklemeyi destekleyen önyükleme görüntüsü başlığı sürüm 4'ü kullanabilir. Birden fazla tedarikçi ramdisk parçası, tedarikçi ramdisk bölümünde art arda birleştirilir. Tedarikçi ramdisk tablosu, tedarikçi ramdisk bölümünün düzenini ve her tedarikçi ramdisk parçasının meta verilerini açıklamak için kullanılır.
Bölüm yapısı
Tedarikçi başlatma bölümü, sanal A/B ile A/B'ye ayrılır ve Android Doğrulanmış Başlatma ile korunur.
Sürüm 3
Bölüm; üstbilgi, tedarikçi ramdiski ve cihaz ağacı blob'undan (DTB) oluşur.
Bölüm | Sayfa sayısı |
---|---|
Tedarikçi başlatma üstbilgisi (n sayfa) | n = (2112 + page_size - 1) / page_size |
Tedarikçi ramdiski (o sayfa) | o = (vendor_ramdisk_size + page_size - 1) / page_size |
DTB (p sayfaları) | p = (dtb_size + page_size - 1) / page_size |
Sürüm 4
Bölüm; başlık, tedarikçi ramdisk bölümü (birleştirilmiş tüm tedarikçi ramdisk parçalarından oluşur), cihaz ağacı blob'u (DTB) ve tedarikçi ramdisk tablosundan oluşur.
Bölüm | Sayfa sayısı |
---|---|
Tedarikçi başlatma üstbilgisi (n sayfa) | n = (2128 + page_size - 1) / page_size |
Tedarikçi ramdisk parçaları (o sayfa) | o = (vendor_ramdisk_size + page_size - 1) / page_size |
DTB (p sayfaları) | p = (dtb_size + page_size - 1) / page_size |
Tedarikçi ramdisk tablosu (q sayfaları) | q = (vendor_ramdisk_table_size + page_size - 1) / page_size |
Bootconfig (r sayfaları) | r = (bootconfig_size + page_size - 1) / page_size |
Tedarikçi başlatma üstbilgisi
Tedarikçi önyükleme bölümü üstbilgisinin içeriği, temel olarak önyükleme görüntüsü üstbilgisinden buraya taşınan verilerden oluşur. Ayrıca, tedarikçi ramdiski hakkında bilgiler de içerir.
Sürüm 3
struct vendor_boot_img_hdr_v3
{
#define VENDOR_BOOT_MAGIC_SIZE 8
uint8_t magic[VENDOR_BOOT_MAGIC_SIZE];
uint32_t header_version;
uint32_t page_size; /* flash page size we assume */
uint32_t kernel_addr; /* physical load addr */
uint32_t ramdisk_addr; /* physical load addr */
uint32_t vendor_ramdisk_size; /* size in bytes */
#define VENDOR_BOOT_ARGS_SIZE 2048
uint8_t cmdline[VENDOR_BOOT_ARGS_SIZE];
uint32_t tags_addr; /* physical addr for kernel tags */
#define VENDOR_BOOT_NAME_SIZE 16
uint8_t name[VENDOR_BOOT_NAME_SIZE]; /* asciiz product name */
uint32_t header_size; /* size of vendor boot image header in
* bytes */
uint32_t dtb_size; /* size of dtb image */
uint64_t dtb_addr; /* physical load address */
};
Sürüm 4
struct vendor_boot_img_hdr_v4
{
#define VENDOR_BOOT_MAGIC_SIZE 8
uint8_t magic[VENDOR_BOOT_MAGIC_SIZE];
uint32_t header_version;
uint32_t page_size; /* flash page size we assume */
uint32_t kernel_addr; /* physical load addr */
uint32_t ramdisk_addr; /* physical load addr */
uint32_t vendor_ramdisk_size; /* size in bytes */
#define VENDOR_BOOT_ARGS_SIZE 2048
uint8_t cmdline[VENDOR_BOOT_ARGS_SIZE];
uint32_t tags_addr; /* physical addr for kernel tags */
#define VENDOR_BOOT_NAME_SIZE 16
uint8_t name[VENDOR_BOOT_NAME_SIZE]; /* asciiz product name */
uint32_t header_size; /* size of vendor boot image header in
* bytes */
uint32_t dtb_size; /* size of dtb image */
uint64_t dtb_addr; /* physical load address */
uint32_t vendor_ramdisk_table_size; /* size in bytes for the vendor ramdisk table */
uint32_t vendor_ramdisk_table_entry_num; /* number of entries in the vendor ramdisk table */
uint32_t vendor_ramdisk_table_entry_size; /* size in bytes for a vendor ramdisk table entry */
uint32_t bootconfig_size; /* size in bytes for the bootconfig section */
};
#define VENDOR_RAMDISK_TYPE_NONE 0
#define VENDOR_RAMDISK_TYPE_PLATFORM 1
#define VENDOR_RAMDISK_TYPE_RECOVERY 2
#define VENDOR_RAMDISK_TYPE_DLKM 3
struct vendor_ramdisk_table_entry_v4
{
uint32_t ramdisk_size; /* size in bytes for the ramdisk image */
uint32_t ramdisk_offset; /* offset to the ramdisk image in vendor ramdisk section */
uint32_t ramdisk_type; /* type of the ramdisk */
#define VENDOR_RAMDISK_NAME_SIZE 32
uint8_t ramdisk_name[VENDOR_RAMDISK_NAME_SIZE]; /* asciiz ramdisk name */
#define VENDOR_RAMDISK_TABLE_ENTRY_BOARD_ID_SIZE 16
// Hardware identifiers describing the board, soc or platform which this
// ramdisk is intended to be loaded on.
uint32_t board_id[VENDOR_RAMDISK_TABLE_ENTRY_BOARD_ID_SIZE];
};
vendor_ramdisk_size
, tüm satıcı ramdisk parçalarının toplam boyutudur.ramdisk_type
, ramdisk'in türünü gösterir. Olası değerler şunlardır:VENDOR_RAMDISK_TYPE_NONE
, değerin belirtilmediğini gösterir.VENDOR_RAMDISK_TYPE_PLATFORM
ramdisk'ler platforma özgü bitler içerir. Bootloader, bunları her zaman belleğe yüklemelidir.VENDOR_RAMDISK_TYPE_RECOVERY
ramdiskler kurtarma kaynakları içerir. Kurtarma moduna önyükleme yapılırken önyükleyici bunları belleğe yüklemelidir.VENDOR_RAMDISK_TYPE_DLKM
ramdisk'ler, dinamik olarak yüklenebilir çekirdek modülleri içeriyor.
ramdisk_name
, ramdisk'in benzersiz adıdır.board_id
, tedarikçi tarafından tanımlanan donanım tanımlayıcılarının bir vektörüdür.
Bootloader desteği
Tedarikçi önyükleme bölümü, daha önce önyükleme bölümünde bulunan bilgileri (ör. flash sayfa boyutu, çekirdek, ramdisk yükleme adresleri, DTB'nin kendisi) içerdiğinden önyükleyicinin önyüklemeyi tamamlamak için yeterli veriye sahip olması için hem önyükleme hem de tedarikçi önyükleme bölümlerine erişmesi gerekir.
Bootloader, satıcı ramdisk'ini (CPIO, Gzip ve lz4 biçimleri bu tür bir birleştirmeyi destekler) takiben hemen genel ramdisk'i belleğe yüklemelidir. Genel ramdisk görüntüsünü sayfa hizalamayın veya bellek içinde satıcı ramdiski ile sonu arasında başka bir alan oluşturmayın. Çekirdek sıkıştırması açıldıktan sonra birleştirilmiş dosyayı initramfs
içine çıkarır. Bu işlem, satıcı ramdisk dosya yapısı üzerine yerleştirilmiş genel bir ramdisk olan bir dosya yapısıyla sonuçlanır.
Genel ramdisk ve tedarikçi ramdisk birleştirildiğinden aynı biçimde olmalıdır. GKI önyükleme görüntüsü, lz4 ile sıkıştırılmış genel bir ramdisk kullandığından GKI uyumlu bir cihazın lz4 ile sıkıştırılmış bir satıcı ramdiski kullanması gerekir. Bununla ilgili yapılandırma aşağıda gösterilmiştir.
Bootconfig'i desteklemek için bootloader gereksinimleri Bootconfig'i Uygulama bölümünde açıklanmıştır.
Birden fazla satıcı ramdiski (sürüm 4)
Önyükleme görüntüsü başlık sürümü 4 ile önyükleyici, önyükleme sırasında initramfs
olarak yüklenecek satıcı ramdisk'lerinin bir alt kümesini veya tamamını seçebilir. Tedarikçi ramdisk tablosu, her ramdiskin meta verilerini içerir ve önyükleyicinin hangi ramdisklerin yükleneceğine karar vermesine yardımcı olabilir. Önyükleyici, genel ramdisk en son yüklendiği sürece seçilen tedarikçi ramdisklerinin yüklenme sırasına karar verebilir.
Örneğin, bootloader, kaynakları korumak için normal başlatma sırasında VENDOR_RAMDISK_TYPE_RECOVERY
türündeki satıcı ramdisklerinin yüklenmesini atlayabilir. Bu durumda, yalnızca VENDOR_RAMDISK_TYPE_PLATFORM
ve VENDOR_RAMDISK_TYPE_DLKM
türündeki satıcı ramdiskleri belleğe yüklenir. Diğer yandan, VENDOR_RAMDISK_TYPE_PLATFORM
, VENDOR_RAMDISK_TYPE_RECOVERY
ve VENDOR_RAMDISK_TYPE_DLKM
türündeki satıcı ramdiskleri, kurtarma modunda başlatılırken belleğe yüklenir.
Alternatif olarak, bootloader, satıcı ramdisk tablosunu yok sayabilir ve satıcı ramdisk bölümünün tamamını yükleyebilir. Bu, vendor_boot
bölümündeki tüm satıcı ramdisk parçalarını yüklemekle aynı etkiye sahiptir.
Destek oluşturma
Bir cihazda satıcı önyükleme desteğini uygulamak için:
BOARD_BOOT_HEADER_VERSION
değerini3
veya daha yüksek bir değere ayarlayın.Cihazınız GKI uyumluysa veya başka bir şekilde lz4 sıkıştırılmış genel bir ramdisk kullanıyorsa
BOARD_RAMDISK_USE_LZ4
değerinitrue
olarak ayarlayın.BOARD_VENDOR_BOOTIMAGE_PARTITION_SIZE
değerini, satıcı ramdisk'ine gitmesi gereken çekirdek modüllerini göz önünde bulundurarak cihazınız için uygun bir boyuta ayarlayın.AB_OTA_PARTITIONS
,vendor_boot
ve cihaza özel OTA bölümleri listelerini içerecek şekilde güncelleyin.Cihazınızı
fstab
,boot
bölümüne değil,vendor_boot
bölümüne kopyalayın./first_stage_ramdisk
Örneğin,$(LOCAL_PATH)/fstab.hardware:$(TARGET_COPY_OUT_VENDOR_RAMDISK)/first_stage_ramdisk/fstab.$(PRODUCT_PLATFORM)
.
vendor_boot
'ya birden fazla tedarikçi ramdiski eklemek için:
BOARD_BOOT_HEADER_VERSION
değerini4
olarak ayarlayın.BOARD_VENDOR_RAMDISK_FRAGMENTS
,vendor_boot
'ye dahil edilecek mantıksal tedarikçi ramdisk parça adlarının listesi olarak ayarlayın.Önceden oluşturulmuş bir satıcı ramdiski eklemek için
BOARD_VENDOR_RAMDISK_FRAGMENT.$(vendor_ramdisk).PREBUILT
değerini önceden oluşturulmuş yola ayarlayın.DLKM tedarikçisi ramdiski eklemek için
BOARD_VENDOR_RAMDISK_FRAGMENT.$(vendor_ramdisk).KERNEL_MODULE_DIRS
değerini eklenecek çekirdek modülü dizinleri listesi olarak ayarlayın.BOARD_VENDOR_RAMDISK_FRAGMENT.$(vendor_ramdisk).MKBOOTIMG_ARGS
öğesinimkbootimg
bağımsız değişkenleri olarak ayarlayın. Bunlar, tedarikçi ramdisk parçası için--board_id[0-15]
ve--ramdisk_type
argümanlarıdır. DLKM satıcı ramdiski için varsayılan--ramdisk_type
, aksi belirtilmediği süreceDLKM
olur.
vendor_boot
içinde bağımsız bir recovery
ramdisk olarak kurtarma kaynakları oluşturmak için:
BOARD_BOOT_HEADER_VERSION
değerini4
olarak ayarlayın.BOARD_MOVE_RECOVERY_RESOURCES_TO_VENDOR_BOOT
değerinitrue
olarak ayarlayın.BOARD_INCLUDE_RECOVERY_RAMDISK_IN_VENDOR_BOOT
değerinitrue
olarak ayarlayın.- Bu,
ramdisk_name
değerirecovery
veramdisk_type
değeriVENDOR_RAMDISK_TYPE_RECOVERY
olan bir satıcı ramdisk parçası ekler. Ramdisk daha sonra$(TARGET_RECOVERY_ROOT_OUT)
altına yüklenen tüm kurtarma dosyalarını içerir.
mkbootimg bağımsız değişkenleri
Bağımsız değişken | Açıklama |
---|---|
--ramdisk_type |
Ramdisk türü; NONE ,
PLATFORM , RECOVERY veya DLKM olabilir.
|
--board_id[0-15] |
board_id vektörünü belirtin. Varsayılan değer 0 'dir. |
Aşağıda örnek bir yapılandırma verilmiştir:
BOARD_KERNEL_MODULE_DIRS := foo bar baz
BOARD_BOOT_HEADER_VERSION := 4
BOARD_VENDOR_RAMDISK_FRAGMENTS := dlkm_foobar
BOARD_VENDOR_RAMDISK_FRAGMENT.dlkm_foobar.KERNEL_MODULE_DIRS := foo bar
BOARD_VENDOR_RAMDISK_FRAGMENT.dlkm_foobar.MKBOOTIMG_ARGS := --board_id0 0xF00BA5 --board_id1 0xC0FFEE
Sonuçtaki vendor_boot
iki tedarikçi ramdisk parçası içerir. Birincisi, DLKM dizinini baz
ve $(TARGET_VENDOR_RAMDISK_OUT)
içindeki diğer dosyaları içeren "varsayılan" ramdisk'tir. İkincisi ise DLKM dizinleri foo
ve bar
'yi içeren dlkm_foobar
ramdisk'tir. --ramdisk_type
varsayılan olarak DLKM
'dir.