כדי להטמיע A/B וירטואלי במכשיר חדש, או להתאים מחדש מכשיר שהושק, עליך לבצע שינויים בקוד ספציפי למכשיר.
לבנות דגלים
התקנים המשתמשים ב-A/B וירטואלי חייבים להיות מוגדרים כהתקן A/B וחייבים להפעיל אותם עם מחיצות דינמיות .
עבור מכשירים המופעלים עם A/B וירטואלי, הגדר אותם כך שיורש את תצורת בסיס התקן A/B וירטואלי:
$(call inherit-product, \
$(SRC_TARGET_DIR)/product/virtual_ab_ota.mk)
מכשירים המופעלים עם A/B וירטואלי זקוקים רק לחצי מגודל הלוח עבור BOARD_SUPER_PARTITION_SIZE
כי חריצי B אינם נמצאים עוד בסופר. כלומר, BOARD_SUPER_PARTITION_SIZE
חייב להיות גדול או שווה לסכום (גודל של קבוצות עדכון) + תקורה , שבתורו, חייב להיות גדול או שווה לסכום (גודל מחיצות) + תקורה .
כדי לאפשר צילומי מצב דחוסים עם Virtual A/B, ירשו במקום זאת את תצורת הבסיס הבאה:
$(call inherit-product, \
$(SRC_TARGET_DIR)/product/virtual_ab_ota/compression.mk)
בקרת אתחול HAL
בקרת האתחול HAL מספקת ממשק עבור לקוחות OTA לשליטה בחריצי אתחול. Virtual A/B דורש שדרוג גרסה מינורי של HAL בקרת האתחול מכיוון שנדרשים ממשקי API נוספים כדי להבטיח שהמטען האתחול מוגן במהלך מהבהב/איפוס להגדרות היצרן. ראה IBootControl.hal ו- types.hal לגרסה העדכנית ביותר של הגדרת 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
}
שינויים ב-Fstab
השלמות של מחיצת המטא נתונים חיונית לתהליך האתחול, במיוחד מיד לאחר החלת עדכון OTA. אז יש לבדוק את מחיצת המטא נתונים לפני first_stage_init
מעלה אותה. כדי להבטיח שזה יקרה, הוסף את הדגל check
fs_mgr לערך עבור /metadata
. להלן דוגמה:
/dev/block/by-name/metadata /metadata ext4 noatime,nosuid,nodev,discard,sync wait,formattable,first_stage_mount,check
דרישות הליבה
כדי לאפשר צילום מצב, הגדר את CONFIG_DM_SNAPSHOT
ל- true
.
עבור מכשירים המשתמשים ב-F2FS, כלול את הדגל f2fs: ייצוא FS_NOCOW_FL לתיקון ליבת המשתמש כדי לתקן הצמדת קבצים. כלול את ה- f2fs: תומך גם בתיקון ליבת קבצים מוצמדים .
A/B וירטואלי מסתמך על תכונות שנוספו בגרסת ליבה 4.3: סיבית מצב הגלישה במטרות snapshot
snapshot-merge
. לכל המכשירים המופעלים עם אנדרואיד 9 ואילך כבר אמורה להיות גרסת ליבה 4.4 ואילך.
כדי לאפשר צילומי מצב דחוסים, גרסת הליבה המינימלית הנתמכת היא 4.19. הגדר CONFIG_DM_USER=m
או CONFIG_DM_USER=y
. אם משתמשים בקודם (מודול), יש לטעון את המודול ב-ramdisk של השלב הראשון. ניתן להשיג זאת על ידי הוספת השורה הבאה למכשיר Makefile:
BOARD_GENERIC_RAMDISK_KERNEL_MODULES_LOAD := dm-user.ko
התאמה מחדש במכשירים המשדרגים לאנדרואיד 11
בעת שדרוג לאנדרואיד 11, מכשירים שהושקו עם מחיצות דינמיות יכולים, אופציונלית, להתאים A/B וירטואלי מחדש. תהליך העדכון זהה לרוב למכשירים המופעלים עם A/B וירטואלי, עם כמה הבדלים קלים:
מיקום קבצי COW - עבור התקני הפעלה, לקוח OTA משתמש בכל השטח הריק הזמין במחיצת העל לפני השימוש בשטח ב-
/data
. עבור התקני תיקון, תמיד יש מספיק מקום במחיצת העל כך שקובץ COW לעולם לא ייווצר ב-/data
.דגלים של תכונה בזמן בנייה — במכשירים שמבצעים התאמה מחדש של A/B וירטואלית, הן
PRODUCT_VIRTUAL_AB_OTA
והןPRODUCT_VIRTUAL_AB_OTA_RETROFIT
מוגדרות כ-true
, כפי שמוצג להלן:(call inherit-product, \
(SRC_TARGET_DIR)/product/virtual_ab_ota_retrofit.mk)
גודל מחיצה סופר - מכשירים המופעלים עם A/B וירטואלי יכולים לחתוך
BOARD_SUPER_PARTITION_SIZE
לשניים מכיוון שחריצי B אינם נמצאים במחיצת העל. התקנים שמתאמים מחדש A/B וירטואלי שומרים על גודל מחיצת העל הישנה, כךBOARD_SUPER_PARTITION_SIZE
גדול או שווה ל -2 * סכום (גודל קבוצות עדכון) + תקורה , שבתורו גדול או שווה ל -2 * סכום (גודל מחיצות) + תקורה .
שינויים במטען האתחול
במהלך שלב המיזוג של עדכון, /data
מחזיק את המופע השלם היחיד של מערכת ההפעלה אנדרואיד. ברגע שההגירה מתחילה, המחיצות של system
המקורית, vendor
של product
אינם שלמים עד לסיום ההעתקה. אם המכשיר מאופס להגדרות היצרן במהלך תהליך זה, או על ידי שחזור או דרך תיבת הדו-שיח של הגדרות מערכות, אזי ההתקן לא יהיה ניתן לאתחול.
לפני מחיקת /data
, סיים את המיזוג בשחזור או החזרה לאחור בהתאם למצב המכשיר:
- אם המבנה החדש עלה בהצלחה בעבר, סיים את ההעברה.
- אחרת, חזור למשבצת הישנה:
- עבור מחיצות דינמיות, חזור למצב הקודם.
- עבור מחיצות סטטיות, הגדר את החריץ הפעיל לחריץ הישן.
גם טוען האתחול וגם fastbootd
יכולים למחוק את מחיצת /data
אם המכשיר אינו נעול. בעוד fastbootd
יכול לאלץ את ההעברה להסתיים, טוען האתחול לא יכול. טוען האתחול לא יודע אם מיזוג מתבצע או לא, או אילו בלוקים ב- /data
מהווים את מחיצות מערכת ההפעלה. התקנים חייבים למנוע מהמשתמש שלא ביודעין להפוך את המכשיר לבלתי פעיל (לבנה) על ידי ביצוע הפעולות הבאות:
- הטמיע את בקרת האתחול HAL כך שמטען האתחול יוכל לקרוא את הערך שהוגדר בשיטת
setSnapshotMergeStatus()
. - אם סטטוס המיזוג הוא
MERGING
, או אם סטטוס המיזוג הואSNAPSHOTTED
השתנה למשבצת המעודכנת לאחרונה, יש לדחות בקשות למחיקתuserdata
,metadata
או המחיצה המאחסנת את סטטוס המיזוג במטען האתחול. - הטמע את הפקודה
fastboot snapshot-update cancel
כך שמשתמשים יוכלו לאותת למטען האתחול שהם רוצים לעקוף את מנגנון ההגנה הזה. - שנה כלים או סקריפטים מהבהבים מותאמים אישית כדי להנפיק
fastboot snapshot-update cancel
בעת הבהוב של המכשיר כולו. זה בטוח להנפקה מכיוון שהבהוב של המכשיר כולו מסירה את ה-OTA. כלי עבודה יכולים לזהות פקודה זו בזמן ריצה על ידי הטמעתfastboot getvar snapshot-update-status
. פקודה זו עוזרת להבדיל בין מצבי שגיאה.
דוגמא
struct VirtualAbState {
uint8_t StructVersion;
uint8_t MergeStatus;
uint8_t SourceSlot;
};
bool ShouldPreventUserdataWipe() {
VirtualAbState state;
if (!ReadVirtualAbState(&state)) ...
return state.MergeStatus == MergeStatus::MERGING ||
(state.MergeStatus == MergeStatus::SNAPSHOTTED &&
state.SourceSlot != CurrentSlot()));
}
שינויים בכלי Fastboot
אנדרואיד 11 מבצעת את השינויים הבאים בפרוטוקול fastboot:
-
getvar snapshot-update-status
- מחזירה את הערך שבקרת האתחול HAL מסר למטען האתחול:- אם המצב הוא
MERGING
, על טוען האתחול להחזיר אתmerging
. - אם המצב הוא
SNAPSHOTTED
, טוען האתחול חייב להחזירsnapshotted
. - אחרת, טוען האתחול חייב להחזיר
none
.
- אם המצב הוא
-
snapshot-update merge
- משלים פעולת מיזוג, אתחול לשחזור/fastbootd במידת הצורך. פקודה זו תקפה רק אםsnapshot-update-status
merging
, והיא נתמכת רק ב-fastbootd. -
snapshot-update cancel
— מגדיר את מצב המיזוג של בקרת האתחול HAL ל-CANCELLED
. פקודה זו אינה חוקית כאשר המכשיר נעול. -
erase
אוwipe
-erase
אוwipe
שלmetadata
,userdata
משתמש או מחיצה שמחזיקה בסטטוס המיזוג עבור בקרת האתחול HAL אמורה לבדוק את סטטוס המיזוג של תמונת המצב. אם המצב הואSNAPSHOTTED
MERGING
המכשיר אמור לבטל את הפעולה. -
set_active
— פקודתset_active
שמשנה את המשבצת הפעילה צריכה לבדוק את מצב המיזוג של תמונת המצב. אם המצב הואMERGING
, המכשיר אמור לבטל את הפעולה. ניתן לשנות את החריץ בבטחה במצבSNAPSHOTTED
.
השינויים הללו נועדו למנוע בטעות להפוך את המכשיר לבלתי ניתן לאתחול, אך הם עלולים להפריע לכלי עבודה אוטומטיים. כאשר הפקודות משמשות כרכיב של הבהוב של כל המחיצות, כגון הפעלת fastboot flashall
, מומלץ להשתמש בזרימה הבאה:
- שאילתה
getvar snapshot-update-status
. - אם
merging
אוsnapshotted
, הנפקsnapshot-update cancel
. - המשך בצעדים מהבהבים.
צמצום דרישות האחסון
למכשירים שאין להם אחסון A/B מלא שהוקצה בסופר, והם מצפים להשתמש ב- /data
לפי הצורך, מומלץ מאוד להשתמש בכלי מיפוי בלוקים. כלי מיפוי הבלוקים שומר על הקצאת בלוקים עקבית בין הבנייה, ומפחית כתיבה מיותרת לתמונת המצב. זה מתועד תחת הפחתת גודל OTA .