האחסון החיצוני מנוהל על ידי שילוב של שירות ה-init vold
ושירות המערכת StorageManagerService
. המערכת vold
מטפלת בהתקנה של נפחי אחסון חיצוניים פיזיים, ומבצעת פעולות של שלב ההכנה כדי להכין את המדיה לפני שהיא נחשפת לאפליקציות.
הערה: ב-Android 8.0, השם של הכיתה MountService
השתנה ל-StorageManagerService
.
מיפויים של קבצים
ב-Android 4.2.2 ובגרסאות קודמות, קובץ התצורה vold.fstab
הספציפי למכשיר מגדיר מיפויים ממכשירי sysfs לנקודות קיבוע של מערכת הקבצים, וכל שורה עומדת בפורמט הזה:
dev_mount <label> <mount_point> <partition> <sysfs_path> [flags]
label
: תווית של האחסון.mount_point
: נתיב מערכת הקבצים שבו צריך לטעון את נפח האחסון.partition
: מספר המחיצה (מתחיל ב-1), או 'auto' למחיצה הראשונה שאפשר להשתמש בה.sysfs_path
: נתיב sysfs אחד או יותר למכשירים שיכולים לספק את נקודת הטעינה הזו. הפרמטרים מופרדים ברווחים, וכל אחד מהם חייב להתחיל ב-/
.flags
: רשימה אופציונלית של דגלים מופרדים בפסיקים, אסור לכלול את/
. הערכים האפשריים הםnonremovable
ו-encryptable
.
במהדורות Android 4.3 ואילך, קבצי ה-fstab השונים שבהם משתמשים init, vold ו-recovery אוחדו בקובץ /fstab.<device>
. בנפח אחסון חיצוני שמנוהל על ידי vold
, הפורמט של הרשומות צריך להיות:
<src> <mnt_point> <type> <mnt_flags> <fs_mgr_flags>
src
: נתיב ב-sysfs (בדרך כלל מוצמד ב-/sys) למכשיר שיכול לספק את נקודת הטעינה. הנתיב חייב להתחיל ב-/
.mount_point
: נתיב מערכת הקבצים שבו צריך לטעון את נפח האחסון.type
: סוג מערכת הקבצים בנפח האחסון. בכרטיסים חיצוניים, זה בדרך כללvfat
.mnt_flags
:Vold
מתעלם מהשדה הזה וצריך להגדיר אותו לערךdefaults
fs_mgr_flags
:Vold
מתעלם משורות בקובץ fstab המאוחד שלא כוללות את הדגלvoldmanaged=
בשדה הזה. אחרי הדגל הזה צריך להופיע תווית שמתארת את הכרטיס ומספר מחיצה או המילהauto
. לדוגמה:voldmanaged=sdcard:auto
. דגלים אפשריים אחרים הםnonremovable
,encryptable=sdcard
,noemulatedsd
ו-encryptable=userdata
.
פרטי ההגדרות האישיות
אינטראקציות עם אחסון חיצוני ברמה של המסגרת וברמה שמעליה מטופלות באמצעות StorageManagerService
. בגלל שינויים בהגדרות ב-Android 6.0 (כמו הסרת שכבת-העל של המשאב storage_list.xml), פרטי ההגדרה מחולקים לשתי קטגוריות.
Android מגרסה 5.x ואילך
קובץ התצורה storage_list.xml
הספציפי למכשיר, שמסופק בדרך כלל באמצעות שכבת-על של frameworks/base
, מגדיר את המאפיינים והאילוצים של התקני האחסון. הרכיב <StorageList>
מכיל רכיב <storage>
אחד או יותר, ורק אחד מהם צריך להיות מסומן כראשי. המאפיינים של <storage>
כוללים:
mountPoint
: הנתיב במערכת הקבצים של ההתקנה.storageDescription
: משאב מחרוזת שמתאר את הטעינה.primary
: הערך true אם ההתקנה הזו היא האחסון החיצוני הראשי.removable
: true אם במתקן הזה יש מדיה נשלפת, כמו כרטיס SD פיזי.emulated
: הערך true אם הטעינה הזו היא הדמיה ומגובת על ידי אחסון פנימי, אולי באמצעות דימון FUSE.mtp-reserve
: מספר מגה-בייט של אחסון ש-MTP צריך להקצות לאחסון בחינם. משמש רק כשהחיבור מסומן כמעולב.allowMassStorage
: הערך true אם אפשר לשתף את ההתקנה הזו באמצעות אחסון בנפח גדול ב-USB.maxFileSize
: גודל הקובץ המקסימלי ב-MB.
מכשירים יכולים לספק אחסון חיצוני על ידי הדמיה של מערכת קבצים ללא הרשאות ותמיכה באחסון פנימי, ללא קשר לרישיון. אפשרות אחת להטמעה היא באמצעות הדימון של FUSE ב-system/core/sdcard
, שאפשר להוסיף כשירות init.rc
ספציפי למכשיר:
# virtual sdcard daemon running as media_rw (1023) service sdcard /system/bin/sdcard <source_path> <dest_path> 1023 1023 class late_start
כאשר source_path
הוא האחסון הפנימי לגיבוי ו-dest_path
הוא נקודת הטעינה של היעד.
כשמגדירים סקריפט init.rc
ספציפי למכשיר, צריך להגדיר את משתנה הסביבה EXTERNAL_STORAGE
כנתיב לאחסון החיצוני הראשי. גם הנתיב /sdcard
צריך להוביל לאותו מיקום, אולי דרך קישור סימלי. אם המיקום של האחסון החיצוני במכשיר משתנה בין עדכוני הפלטפורמה, צריך ליצור קישורי סימון כדי שהנתיבים הישנים ימשיכו לפעול.
Android 6.0
הגדרת מערכת המשנה של האחסון מרוכזת עכשיו בקובץ fstab
הספציפי למכשיר, והוסרו כמה משתנים או קובצי תצורה סטטיים היסטוריים כדי לתמוך בהתנהגות דינמית יותר:
- שכבת-העל של המשאב
storage_list.xml
הוסרה והיא לא בשימוש יותר במסגרת. מכשירי אחסון מוגדרים עכשיו באופן דינמי כשהם מזוהים על ידיvold
. - משתני הסביבה
EMULATED_STORAGE_SOURCE/TARGET
הוסרו, ו-Zygote כבר לא משתמש בהם כדי להגדיר נקודות קישור ספציפיות למשתמש. במקום זאת, ההפרדה בין משתמשים נאכפת עכשיו באמצעות מזהי GID ספציפיים למשתמש, והאחסון המשותף הראשי מצורף על ידיvold
במהלך זמן הריצה.- מפתחים יכולים להמשיך ליצור נתיבים באופן דינמי או סטטי, בהתאם לתרחיש לדוגמה שלהם. הוספת ה-UUID לנתיב מאפשרת לזהות כל כרטיס כדי שהמפתחים יוכלו לזהות את המיקום בצורה ברורה יותר. (לדוגמה, ברור שקובץ
/storage/ABCD-1234/report.txt
שונה מקובץ/storage/DCBA-4321/report.txt
).
- מפתחים יכולים להמשיך ליצור נתיבים באופן דינמי או סטטי, בהתאם לתרחיש לדוגמה שלהם. הוספת ה-UUID לנתיב מאפשרת לזהות כל כרטיס כדי שהמפתחים יוכלו לזהות את המיקום בצורה ברורה יותר. (לדוגמה, ברור שקובץ
- שירותי FUSE שהוגדרו בקוד הוסרו מקובצי
init.rc
ספציפיים למכשיר, ובמקום זאת הם מתפצלים באופן דינמי מ-vold
לפי הצורך.
בנוסף לשינויים בהגדרות, ב-Android 6.0 יש את המושג של אחסון מתאים. במכשירי Android 6.0, כל מדיה פיזית שלא אומצה נחשבת לניידת.
אחסון שניתן להתאמה
כדי לציין מכשיר אחסון מתאים ב-fstab
, משתמשים במאפיין encryptable=userdata
בשדה fs_mgr_flags
. זוהי הגדרה טיפוסית:
/devices/platform/mtk-msdc.1/mmc_host* auto auto defaults voldmanaged=sdcard1:auto,encryptable=userdata
כשמכשיר אחסון מצורף, הפלטפורמה מוחקת את התוכן שלו וכותבת טבלת מחיצות של GUID שמגדירה שתי מחיצות:
- מחיצה קטנה וריקה של
android_meta
ששמורה לשימוש עתידי. ה-GUID של סוג המחיצה הוא 19A710A2-B3CA-11E4-B026-10604B889DCF. - מחיצה גדולה מסוג
android_ext
מוצפנת באמצעות dm-crypt ופורמטית באמצעותext4
אוf2fs
, בהתאם ליכולות הליבה. ה-GUID של סוג המחיצה הוא 193D1EA4-B3CA-11E4-B075-10604B889DCF.
אחסון נייד
ב-fstab
, מכשירי אחסון עם המאפיין voldmanaged
נחשבים לניידים כברירת מחדל, אלא אם מוגדר מאפיין אחר כמו encryptable=userdata
. לדוגמה, זוהי הגדרה טיפוסית למכשירי USB OTG:
/devices/*/xhci-hcd.0.auto/usb* auto auto defaults voldmanaged=usb:auto
הפלטפורמה משתמשת ב-blkid
כדי לזהות סוגי מערכות קבצים לפני הרכבה, והמשתמשים יכולים לבחור לפרמט את המדיה אם מערכת הקבצים לא נתמכת.