自 2025 年 3 月 27 日起,我們建議您使用 android-latest-release
而非 aosp-main
建構及貢獻 AOSP。詳情請參閱「Android 開放原始碼計畫變更」。
非 A/B 系統更新
透過集合功能整理內容
你可以依據偏好儲存及分類內容。
非 AB 更新是舊版 Android 裝置 (Android 6 以下版本) 使用的已淘汰的 OTA 方法。這些裝置具有專屬的復原分割區,其中包含解開下載更新套件所需的軟體,並將更新套用至其他分割區。
在沒有 A/B 分割區的舊版 Android 裝置上,快閃記憶體空間通常包含下列分割區:
- 開機
-
包含 Linux 核心和最小根檔案系統 (載入至 RAM 磁碟)。它會掛載系統和其他分區,並啟動位於系統分區的執行階段。
- 系統
-
包含在 Android 開放原始碼計畫 (AOSP) 中提供原始碼的系統應用程式和程式庫。在正常運作期間,這個分割區會以唯讀方式掛載,其內容只會在 OTA 更新期間變更。
- 販賣機
-
包含 Android 開放原始碼計畫 (AOSP) 中「沒有」原始碼的系統應用程式和程式庫。在正常運作期間,這個分割區會以唯讀方式掛載,其內容只會在 OTA 更新期間變更。
- userdata
-
儲存使用者安裝的應用程式等儲存的資料。OTA 更新程序通常不會觸及這個分割區。
- 快取
-
部分應用程式使用的暫時保留區 (存取此分區需要特殊應用程式權限),用於儲存下載的 OTA 更新套件。其他程式會使用這個空間,因為檔案隨時可能會消失。部分 OTA 套件安裝作業可能會導致這個分區完全遭到清除。快取資料也包含 OTA 更新的更新記錄。
- 復原
-
包含第二個完整的 Linux 系統,包括核心和特殊的復原二進位檔,可讀取套件並使用其內容更新其他分區。
- 其他
-
Recovery 使用的 Tiny 分割區,用於儲存一些資訊,以便在裝置在套用 OTA 套件時重新啟動時,儲存相關資訊。
OTA 更新的生命週期
典型的 OTA 更新包含下列步驟:
-
裝置會定期向 OTA 伺服器進行檢查,並收到更新可用性的通知,包括更新套件的網址和顯示給使用者的說明字串。
-
將下載內容更新至快取或資料分割區,並根據
/system/etc/security/otacerts.zip
中的憑證驗證其加密簽名。系統會提示使用者安裝更新。
-
裝置會重新啟動至復原模式,並在該模式中啟動復原分區中的核心和系統,而非啟動分區中的核心。
-
復原二進位檔是由 init 啟動。它會在
/cache/recovery/command
中尋找指向下載套件的指令列引數。
-
復原程序會根據
/res/keys
(復原分割區中 RAM 磁碟的一部分) 中的公開金鑰,驗證套件的加密簽名。
-
系統會從套件中提取資料,並視需要用於更新啟動、系統和/或供應商分區。系統分區中留下的新檔案之一,包含新復原分區的內容。
-
裝置會正常重新啟動。
-
系統會載入新更新的啟動分區,並掛載及開始執行新更新的系統分區中的二進位檔。
-
在正常啟動程序中,系統會檢查復原分區的內容是否與所需內容相符 (先前儲存在
/system
中的檔案)。如果兩者不同,系統會使用所需內容重新刷新復原分區。(在後續啟動時,復原分區已包含新內容,因此不需要重新刷新)。
系統更新完成!您可以在 /cache/recovery/last_log.#
中找到更新記錄。
更新套件
更新套件是包含可執行二進位 META-INF/com/google/android/update-binary
的 .zip
檔案。驗證套件上的簽名後,recovery
會將這個二進位檔案擷取至 /tmp
,並執行二進位檔案,傳遞下列引數:
-
更新二進位 API 版本號碼。如果傳遞至更新二進位檔案的引數有所變更,這個數字就會增加。
-
指令管道的檔案描述元。更新程式可以使用這個管道將指令傳回至復原二進位檔,主要用於 UI 變更,例如向使用者顯示進度。
-
更新套件
.zip
檔案的檔案名稱。
更新套件可以使用任何靜態連結的二進位檔做為更新二進位檔。OTA 套件建構工具會使用更新程式 (bootable/recovery/updater
),後者提供簡單的指令碼語言,可執行許多安裝作業。您可以替換裝置上執行的任何其他二進位檔。
如要進一步瞭解更新程式二進位檔、edify 語法和內建函式,請參閱「OTA 套件內部結構」。
從舊版遷移
從 Android 2.3/3.0/4.0 版本遷移時,主要變更是將所有裝置專屬功能從一組具有預先定義名稱的 C 函式轉換為 C++ 物件。下表列出舊函式和新方法,兩者可用於大致相同的用途:
C 函式 |
C++ 方法 |
device_recovery_start() |
Device::RecoveryStart() |
device_toggle_display()
device_reboot_now()
|
RecoveryUI::CheckKey()
(也包括 RecoveryUI::IsKeyPressed())
|
device_handle_key() |
Device::HandleMenuKey() |
device_perform_action() |
Device::InvokeMenuItem() |
device_wipe_data() |
Device::WipeData() |
device_ui_init() |
ScreenRecoveryUI::Init() |
將舊函式轉換為新方法應該相當簡單。別忘了新增新的 make_device()
函式,以便建立並傳回新的 Device 子類別例項。
這個頁面中的內容和程式碼範例均受《內容授權》中的授權所規範。Java 與 OpenJDK 是 Oracle 和/或其關係企業的商標或註冊商標。
上次更新時間:2025-07-27 (世界標準時間)。
[[["容易理解","easyToUnderstand","thumb-up"],["確實解決了我的問題","solvedMyProblem","thumb-up"],["其他","otherUp","thumb-up"]],[["缺少我需要的資訊","missingTheInformationINeed","thumb-down"],["過於複雜/步驟過多","tooComplicatedTooManySteps","thumb-down"],["過時","outOfDate","thumb-down"],["翻譯問題","translationIssue","thumb-down"],["示例/程式碼問題","samplesCodeIssue","thumb-down"],["其他","otherDown","thumb-down"]],["上次更新時間:2025-07-27 (世界標準時間)。"],[],[],null,["# Non-A/B system updates\n\nNon AB updates are a deprecated OTA methodology used by older Android Devices (Android 6 and\nearlier). These devices have a dedicated recovery partition containing the software needed to\nunpack a downloaded update package and apply the update to the other partitions.\n\n\nOn older Android devices without A/B partitions, the flash space typically contains the\nfollowing partitions:\n\nboot\n:\n Contains the Linux kernel and a minimal root filesystem (loaded into a RAM disk). It mounts\n system and other partitions and starts the runtime located on the system partition.\n\nsystem\n:\n Contains system applications and libraries that have source code available on Android Open\n Source Project (AOSP). During normal operation, this partition is mounted read-only; its\n contents change only during an OTA update.\n\nvendor\n:\n Contains system applications and libraries that do *not* have source code available\n on Android Open Source Project (AOSP). During normal operation, this partition is mounted\n read-only; its contents change only during an OTA update.\n\nuserdata\n:\n Stores the data saved by applications installed by the user, etc. This partition is not\n normally touched by the OTA update process.\n\ncache\n:\n Temporary holding area used by a few applications (accessing this partition requires special\n app permissions) and for storage of downloaded OTA update packages. Other programs use this\n space with the expectation that files can disappear at any time. Some OTA package\n installations may result in this partition being wiped completely. The cache also contains\n the update logs from an OTA update.\n\nrecovery\n:\n Contains a second complete Linux system, including a kernel and the special recovery binary\n that reads a package and uses its contents to update the other partitions.\n\nmisc\n:\n Tiny partition used by recovery to stash some information away about what it is doing in\n case the device is restarted while the OTA package is being applied.\n\nLife of an OTA update\n---------------------\n\nA typical OTA update contains the following steps:\n\n1. Device performs regular check in with OTA servers and is notified of the availability of an update, including the URL of the update package and a description string to show the user.\n2. Update downloads to a cache or data partition, and its cryptographic signature is verified against the certificates in `/system/etc/security/otacerts.zip`. User is prompted to install the update.\n3. Device reboots into recovery mode, in which the kernel and system in the recovery partition are booted instead of the kernel in the boot partition.\n4. Recovery binary is started by init. It finds command-line arguments in `/cache/recovery/command` that point it to the downloaded package.\n5. Recovery verifies the cryptographic signature of the package against the public keys in `/res/keys` (part of the RAM disk contained in the recovery partition).\n6. Data is pulled from the package and used to update the boot, system, and/or vendor partitions as necessary. One of the new files left on the system partition contains the contents of the new recovery partition.\n7. Device reboots normally.\n 1. The newly updated boot partition is loaded, and it mounts and starts executing binaries in the newly updated system partition.\n 2. As part of normal startup, the system checks the contents of the recovery partition against the desired contents (which were previously stored as a file in `/system`). They are different, so the recovery partition is reflashed with the desired contents. (On subsequent boots, the recovery partition already contains the new contents, so no reflash is necessary.)\n\n\nThe system update is complete! The update logs can be found in\n`/cache/recovery/last_log.`\u003cvar translate=\"no\"\u003e#\u003c/var\u003e.\n\nUpdate packages\n---------------\n\n\nAn update package is a `.zip` file that contains the executable binary\n`META-INF/com/google/android/update-binary`. After verifying the signature on the\npackage, `recovery` extracts this binary to `/tmp` and runs the binary,\npassing the following arguments:\n\n- **Update binary API version number**. If the arguments passed to the update binary change, this number increments.\n- **File descriptor of the *command pipe***. The update program can use this pipe to send commands back to the recovery binary, mostly for UI changes, such as indicating progress to the user.\n- **Filename of the update package `.zip` file**.\n\n\nAn update package can use any statically linked binary as the update binary. The OTA package\nconstruction tools use the updater program (`bootable/recovery/updater`), which\nprovides a simple scripting language that can do many installation tasks. You can substitute\nany other binary running on the device.\n\n\nFor details on the updater binary, edify syntax, and builtin functions, see\n[Inside OTA Packages](/docs/core/ota/nonab/inside_packages).\n\nMigrate from previous releases\n------------------------------\n\n\nWhen migrating from Android 2.3/3.0/4.0 release, the major change is the conversion of all the\ndevice-specific functionality from a set of C functions with predefined names to C++ objects.\nThe following table lists the old functions and the new methods that serve a roughly\nequivalent purpose:\n\n| C function | C++ method |\n|---------------------------------------------|----------------------------------------------------------|\n| device_recovery_start() | Device::RecoveryStart() |\n| device_toggle_display() device_reboot_now() | RecoveryUI::CheckKey() (also RecoveryUI::IsKeyPressed()) |\n| device_handle_key() | Device::HandleMenuKey() |\n| device_perform_action() | Device::InvokeMenuItem() |\n| device_wipe_data() | Device::WipeData() |\n| device_ui_init() | ScreenRecoveryUI::Init() |\n\n\nConversion of old functions to new methods should be reasonably straightforward. Don't forget\nto add the new `make_device()`\nfunction to create and return an instance of your new Device subclass."]]