Google is committed to advancing racial equity for Black communities. See how.
本頁面由 Cloud Translation API 翻譯而成。
Switch to English

分區佈局

在Android 10中,根文件系統不再包含在ramdisk.img ,而是合併到system.img (也就是說,始終像設置BOARD_BUILD_SYSTEM_ROOT_IMAGE一樣創建system.img )。使用Android 10啟動的設備:

  • 使用系統root分區佈局(由構建自動執行,沒有選項可更改行為)。
  • 必須使用ramdisk,這對於dm-linear是必需的。
  • 必須將BOARD_BUILD_SYSTEM_ROOT_IMAGE設置為false 。此設置僅用於區分使用ramdisk的設備和不使用ramdisk的設備(而是直接掛載system.img )。

在Android 9和Android 10之間,“以系統為根”配置的含義有所不同。在Android 9的“以系統為根”配置中, BOARD_BUILD_SYSTEM_ROOT_IMAGE設置為true ,這會強制構建將根文件系統合併到system.imgsystem.img掛載為根文件系統(rootfs)。對於使用Android 9啟動的設備,此配置是必需的,但對於升級到Android 9的設備和運行較低版本Android的設備,此配置是可選的。在Android 10以root用戶身份進行的系統配置中,構建始終將$TARGET_SYSTEM_OUT$TARGET_ROOT_OUT合併到system.img ;此配置是所有運行Android 10的設備的默認行為。

Android 10進行了進一步的更改以支持動態分區動態分區是一種用戶空間分區系統,可通過空中(OTA)更新來創建,調整大小或銷毀分區。作為此更改的一部分,Linux內核無法再在運行Android 10的設備上掛載邏輯系統分區,因此此操作由第一階段初始化處理。

以下各節描述了僅系統OTA的“以系統為根”要求,並提供了有關更新設備以使用“以系統為根”的指南(包括分區佈局更改和dm-verity內核要求)。有關更改ramdisk的詳細信息,請參閱ramdisk分區

關於純係統OTA

僅限系統的OTA(使Android版本可以更新system.imgproduct.img而不更改其他分區)需要係統根目錄分區佈局。所有運行Android 10的設備都必須使用“系統根目錄”分區佈局來啟用僅系統的OTA。

  • system分區安裝為rootfs的A / B設備已經使用root用戶身份,不需要更改即可支持系統OTA。
  • 必須將在/system掛載system分區的非A / B設備更新為使用“ root用戶”分區佈局來支持系統OTA。

有關A / B和非A / B設備的詳細信息,請參閱A / B(無縫)系統更新

使用供應商覆蓋

供應商覆蓋可讓您在設備啟動時將更改覆蓋到vendor分區。供應商覆蓋是product分區中的一組供應商模塊,當設備啟動,替換並添加到現有模塊時,這些vendor商模塊會覆蓋在vendor分區上。

設備啟動時, init過程將完成第一階段的安裝並讀取默認屬性。然後,如果滿足以下條件,它將搜索/product/vendor_overlay/<target_vendor_version>並將每個子目錄安裝在其相應的vendor分區目錄上:

  • /vendor/<overlay_dir>存在。
  • /product/vendor_overlay/<target_vendor_version>/<overlay_dir>/vendor/<overlay_dir>具有相同的文件上下文。
  • 允許init安裝在/vendor/<overlay_dir>的文件上下文中。

實施供應商覆蓋

/product/vendor_overlay/<target_vendor_version>安裝供應商覆蓋文件。設備啟動時,這些文件將覆蓋vendor分區,從而替換相同名稱的文件並添加任何新文件。供應商覆蓋無法從vendor分區中刪除文件。

供應商覆蓋文件必須與它們在vendor分區中替換的目標文件具有相同的文件上下文。默認情況下, /product/vendor_overlay/<target_vendor_version>目錄中的文件具有vendor_file上下文。如果供應商覆蓋文件與其替換的文件之間存在文件上下文不匹配的情況,請在設備特定的分隔符中進行指定。文件上下文在目錄級別設置。如果供應商覆蓋目錄的文件上下文與目標目錄不匹配,並且在特定於設備的分隔符中未指定正確的文件上下文,則該供應商覆蓋目錄不會覆蓋在目標目錄上。

要使用供應商覆蓋,內核必須通過設置CONFIG_OVERLAY_FS=y來啟用OverlayFS。另外,必須從通用內核4.4或更高版本中合併內核,或使用"overlayfs: override_creds=off option bypass creator_cred"修補。

供應商覆蓋實現示例

此過程演示瞭如何實現供應商覆蓋,該覆蓋將目錄/vendor/lib/*/vendor/etc/*/vendor/app/*覆蓋。

  1. device/<vendor>/<target>/vendor_overlay/<target_vendor_version>/添加預構建的供應商文件:

    device/google/device/vendor_overlay/28/lib/libfoo.so
    device/google/device/vendor_overlay/28/lib/libbar.so
    device/google/device/vendor_overlay/28/etc/baz.xml
    device/google/device/vendor_overlay/28/app/qux.apk
    
  2. 將預構建的供應商文件安裝到device/google/device/device.mk product/vendor_overlay

    PRODUCT_COPY_FILES += \
        $(call find-copy-subdir-files,*,device/google/device/vendor_overlay,$(TARGET_COPY_OUT_PRODUCT)/vendor_overlay)
    
  3. 如果目標vendor分區文件具有除vendor_file其他上下文,請定義文件上下文。因為/vendor/lib/*使用vendor_file上下文,所以此示例不包含該目錄。

    將以下內容添加到device/google/device-sepolicy/private/file_contexts

    /(product|system/product)/vendor_overlay/[0-9]+/etc(/.*)?   u:object_r:vendor_configs_file:s0
    /(product|system/product)/vendor_overlay/[0-9]+/app(/.*)?   u:object_r:vendor_app_file:s0
    
  4. 允許init進程在除vendor_file之外的文件上下文上裝載供應商覆蓋。由於init進程已經具有在vendor_file上下文中掛載的權限,因此該示例未定義vendor_file的策略。

    將以下內容添加到device/google/device-sepolicy/public/init.te

    allow init vendor_configs_file:dir mounton;
    allow init vendor_app_file:dir mounton;
    

驗證供應商覆蓋

要驗證供應商覆蓋配置,請在/product/vendor_overlay/<target_vendor_version>/<overlay_dir>添加文件,並檢查文件是否覆蓋在/vendor/<overlay_dir>的文件上。

對於userdebug構建,有一個用於Atest的測試模塊:

$ atest -v fs_mgr_vendor_overlay_test

更新為根系統

要更新非A / B設備以使用root用戶身份,必須更新boot.imgsystem.img的分區方案,設置dm-verity,並刪除設備特定的根文件夾上的所有引導依賴項。

更新分區

與將/boot用作恢復分區的A / B設備不同非A / B設備必須將/recovery分區分開,因為它們沒有後備插槽分區(例如,從boot_aboot_b )。如果在非A / B設備上刪除了/recovery並使其類似於A / B方案,則在對/boot分區更新失敗時恢復模式可能會中斷。因此,對於非A / B設備, /recovery分區必須是與/boot分開的單獨分區,這意味著恢復映像將繼續以延遲方式進行更新(即與運行Android的設備相同) 8.1.0或更低版本)。

下表列出了Android 9之前和之後的非A / B設備的圖像分區差異。

圖片Ramdisk(9之前)根系統(9之後)
boot.img包含一個內核和一個ramdisk.img
ramdisk.img
  -/
    - init.rc
    - init
    - etc -> /system/etc
    - system/ (mount point)
    - vendor/ (mount point)
    - odm/ (mount point)
    ...
僅包含普通的啟動內核。
recovery.img包含一個恢復內核和一個恢復ramdisk.img
system.img包含以下內容:
system.img
  -/
    - bin/
    - etc
    - vendor -> /vendor
    - ...
包含原始system.imgramdisk.img的合併內容:
system.img
  -/
    - init.rc
    - init
    - etc -> /system/etc
    - system/
      - bin/
      - etc/
      - vendor -> /vendor
      - ...
    - vendor/ (mount point)
    - odm/ (mount point)
    ...

分區本身不變。 ramdisk和system-as-root均使用以下分區方案:

  • /boot
  • /system
  • /system
  • /recovery
  • /vendor

設置dm-verity

在system-as-root中,內核必須使用dm-veritysystem.img掛載在/ (掛載點)下。 AOSP支持system.img的以下dm-verity實現。

vboot 1.0

對於vboot 1.0 ,內核必須在/system上解析特定於Android的元數據,然後轉換為dm-verity參數以設置dm-verity(需要這些內核補丁)。以下示例顯示了內核命令行中system-as-root的dm-verity相關設置:

ro root=/dev/dm-0 rootwait skip_initramfs init=/init
dm="system none ro,0 1 android-verity /dev/sda34"
veritykeyid=id:7e4333f9bba00adfe0ede979e28ed1920492b40f

vboot 2.0

對於vboot 2.0( AVB ),引導加載程序必須集成external / avb / libavb ,然後解析/system哈希樹描述符,將其轉換為dm-verity參數,最後通過內核命令行將這些參數傳遞給內核。 ( /system哈希樹描述符可能在/vbmeta/system本身上。)

vboot 2.0需要以下內核修補程序:

以下示例顯示了內核命令行中system-as-root的dm-verity相關設置:

ro root=/dev/dm-0 rootwait  skip_initramfs init=/init

dm="1 vroot none ro 1,0 5159992 verity 1
PARTUUID=00000016-0000-0000-0000-000000000000
PARTUUID=00000016-0000-0000-0000-000000000000 4096 4096 644999 644999
sha1 d80b4a8be3b58a8ab86fad1b498640892d4843a2
8d08feed2f55c418fb63447fec0d32b1b107e42c 10 restart_on_corruption
ignore_zero_blocks use_fec_from_device
PARTUUID=00000016-0000-0000-0000-000000000000 fec_roots 2 fec_blocks
650080 fec_start 650080"

使用設備專用的根文件夾

使用root用戶身份,在將通用系統映像(GSI) BOARD_ROOT_EXTRA_FOLDERS到設備上之後(並且在運行Vendor Test Suite測試之前),添加了BOARD_ROOT_EXTRA_FOLDERS所有設備特定的根文件夾都將消失,因為已替換了整個根目錄內容由系統管理員GSI負責。如果存在對特定於設備的根文件夾的依賴關係(例如,將它們用作安裝點),則刪除這些文件夾可能會導致設備無法啟動。

為避免此問題,請勿使用BOARD_ROOT_EXTRA_FOLDERS添加設備特定的根文件夾。如果需要指定特定於設備的安裝點,請使用/mnt/vendor/<mount point> (已添加到這些變更列表中)。這些特定於供應商的安裝點可以直接在fstab設備樹(用於第一階段安裝)和/vendor/etc/fstab.{ro.hardware}文件中指定,而無需進行其他設置(因為fs_mgr/mnt/vendor/*下創建它們) /mnt/vendor/*自動)。