ভার্চুয়াল A/B বাস্তবায়ন করা

একটি নতুন ডিভাইসে ভার্চুয়াল 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 অবশ্যই যোগফলের (আপডেট গোষ্ঠীর আকার) + ওভারহেডের চেয়ে বেশি বা সমান হতে হবে, যা অবশ্যই যোগফলের (পার্টিশনের আকার) + ওভারহেডের চেয়ে বেশি বা সমান হতে হবে।

ভার্চুয়াল A/B এর সাথে সংকুচিত স্ন্যাপশটগুলি সক্ষম করতে, পরিবর্তে নিম্নলিখিত বেস কনফিগারেশনটি ইনহেরিট করুন:

$(call inherit-product, \
    $(SRC_TARGET_DIR)/product/virtual_ab_ota/compression.mk)

বুট কন্ট্রোল HAL

বুট কন্ট্রোল HAL OTA ক্লায়েন্টদের বুট স্লট নিয়ন্ত্রণ করার জন্য একটি ইন্টারফেস প্রদান করে। ভার্চুয়াল A/B-এর জন্য বুট কন্ট্রোল HAL-এর একটি ছোট সংস্করণ আপগ্রেড প্রয়োজন কারণ ফ্ল্যাশিং/ফ্যাক্টরি রিসেট করার সময় বুটলোডার সুরক্ষিত আছে তা নিশ্চিত করার জন্য অতিরিক্ত APIs প্রয়োজন। HAL সংজ্ঞার সর্বশেষ সংস্করণের জন্য IBootControl.hal এবং type.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 মাউন্ট করার আগে মেটাডেটা পার্টিশনটি অবশ্যই পরীক্ষা করা উচিত। এটি নিশ্চিত করতে, /metadata এর জন্য এন্ট্রিতে fs_mgr check পতাকা যোগ করুন। নিম্নলিখিত একটি উদাহরণ প্রদান করে:

/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 সেট করুন। পূর্বের (একটি মডিউল) ব্যবহার করলে, মডিউলটি অবশ্যই প্রথম পর্যায়ের রামডিস্কে লোড করতে হবে। ডিভাইস মেকফাইলে নিম্নলিখিত লাইন যোগ করে এটি অর্জন করা যেতে পারে:

BOARD_GENERIC_RAMDISK_KERNEL_MODULES_LOAD := dm-user.ko

Android 11-এ আপগ্রেড করা ডিভাইসগুলিতে রেট্রোফিটিং

অ্যান্ড্রয়েড 11-এ আপগ্রেড করার সময়, গতিশীল পার্টিশনের সাথে চালু হওয়া ডিভাইসগুলি ঐচ্ছিকভাবে ভার্চুয়াল A/B রিট্রোফিট করতে পারে। হালনাগাদ প্রক্রিয়াটি ভার্চুয়াল A/B এর সাথে লঞ্চ হওয়া ডিভাইসগুলির মতোই, কিছু ছোটখাটো পার্থক্য সহ:

  • COW ফাইলের অবস্থান — লঞ্চ ডিভাইসের জন্য, OTA ক্লায়েন্ট /data data-এ স্পেস ব্যবহার করার আগে সুপার পার্টিশনের সমস্ত উপলব্ধ খালি স্থান ব্যবহার করে। রেট্রোফিট ডিভাইসের জন্য, সুপার পার্টিশনে সর্বদা পর্যাপ্ত জায়গা থাকে যাতে COW ফাইল কখনই /data 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 Android OS-এর একমাত্র সম্পূর্ণ উদাহরণ ধারণ করে। একবার মাইগ্রেশন শুরু হলে, কপি শেষ না হওয়া পর্যন্ত নেটিভ system , vendor এবং product পার্টিশনগুলি অসম্পূর্ণ থাকে। এই প্রক্রিয়া চলাকালীন যদি ডিভাইসটি ফ্যাক্টরি-রিসেট হয়, হয় পুনরুদ্ধারের মাধ্যমে বা সিস্টেম সেটিংস ডায়ালগের মাধ্যমে, তাহলে ডিভাইসটি আনবুট করা যাবে না।

/data মুছে ফেলার আগে, ডিভাইসের অবস্থার উপর নির্ভর করে পুনরুদ্ধার বা রোলব্যাকে মার্জ শেষ করুন:

  • নতুন বিল্ড আগে সফলভাবে বুট হলে, মাইগ্রেশন শেষ করুন।
  • অন্যথায়, পুরানো স্লটে রোলব্যাক করুন:
    • গতিশীল পার্টিশনের জন্য, আগের অবস্থায় ফিরে যান।
    • স্ট্যাটিক পার্টিশনের জন্য, সক্রিয় স্লটটিকে পুরানো স্লটে সেট করুন।

ডিভাইসটি আনলক করা থাকলে বুটলোডার এবং fastbootd উভয়ই /data পার্টিশন মুছে ফেলতে পারে। যদিও fastbootd মাইগ্রেশন সম্পূর্ণ করতে বাধ্য করতে পারে, বুটলোডার পারে না। বুটলোডার জানে না একটি মার্জ চলছে কি না, বা /data data-এ কোন ব্লকগুলি OS পার্টিশন গঠন করে। ডিভাইসগুলিকে অবশ্যই ব্যবহারকারীকে অজান্তে নিম্নলিখিতগুলি করে ডিভাইসটিকে অকার্যকর (ব্রিকিং) করা থেকে বিরত রাখতে হবে:

  1. বুট কন্ট্রোল HAL প্রয়োগ করুন যাতে বুটলোডার setSnapshotMergeStatus() পদ্ধতি দ্বারা সেট করা মান পড়তে পারে।
  2. যদি মার্জ স্ট্যাটাস MERGING হয়, অথবা যদি মার্জ স্ট্যাটাস SNAPSHOTTED করা হয় এবং স্লটটি নতুন আপডেট করা স্লটে পরিবর্তিত হয়, তাহলে userdata , metadata বা পার্টিশন মুছে ফেলার অনুরোধ বুটলোডারে প্রত্যাখ্যান করতে হবে।
  3. fastboot snapshot-update cancel কমান্ডটি প্রয়োগ করুন যাতে ব্যবহারকারীরা বুটলোডারকে সংকেত দিতে পারে যে তারা এই সুরক্ষা ব্যবস্থাকে বাইপাস করতে চায়।
  4. সম্পূর্ণ ডিভাইস ফ্ল্যাশ করার সময় 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()));
}

ফাস্টবুট টুলিং পরিবর্তন

Android 11 ফাস্টবুট প্রোটোকলে নিম্নলিখিত পরিবর্তনগুলি করে:

  • getvar snapshot-update-status — বুট কন্ট্রোল HAL বুটলোডারের সাথে যোগাযোগ করে এমন মান প্রদান করে:
    • যদি রাজ্য merging MERGING আসবে।
    • যদি SNAPSHOTTED স্ন্যাপশট করা হয়, বুটলোডারকে অবশ্যই snapshotted নিয়ে ফিরতে হবে।
    • অন্যথায়, বুটলোডার অবশ্যই none ফেরত দেবে না।
  • snapshot-update merge — একটি মার্জ অপারেশন সম্পূর্ণ করে, প্রয়োজনে পুনরুদ্ধার/ফাস্টবুট-এ বুট করা হয়। এই কমান্ডটি তখনই বৈধ যদি snapshot-update-status merging হয় এবং শুধুমাত্র fastbootd-এ সমর্থিত হয়।
  • snapshot-update cancel — বুট কন্ট্রোল HAL-এর মার্জ স্ট্যাটাস CANCELLED এ সেট করে। ডিভাইসটি লক থাকা অবস্থায় এই কমান্ডটি অবৈধ।
  • erase ফেলুন বা userdatametadata , wipe , বা বুট কন্ট্রোল HAL-এর জন্য মার্জ স্ট্যাটাস ধারণ করা একটি পার্টিশন মুছে ফেলা বা wipe erase জন্য স্ন্যাপশট মার্জ স্ট্যাটাস পরীক্ষা করা উচিত। স্থিতিটি MERGING বা SNAPSHOTTED করা হলে, ডিভাইসটির অপারেশন বাতিল করা উচিত।
  • set_active — একটি set_active কমান্ড যা সক্রিয় স্লট পরিবর্তন করে স্ন্যাপশট মার্জ অবস্থা পরীক্ষা করা উচিত। স্ট্যাটাস MERGING হলে, ডিভাইসটির অপারেশন বাতিল করা উচিত। স্লট নিরাপদে SNAPSHOTTED অবস্থায় পরিবর্তন করা যেতে পারে।

এই পরিবর্তনগুলি দুর্ঘটনাবশত একটি ডিভাইসকে বুট করার অযোগ্য করে তোলা প্রতিরোধ করার জন্য ডিজাইন করা হয়েছে, তবে সেগুলি স্বয়ংক্রিয় টুলিংয়ের জন্য ব্যাহত হতে পারে। যখন কমান্ডগুলি সমস্ত পার্টিশনকে ফ্ল্যাশ করার একটি উপাদান হিসাবে ব্যবহার করা হয়, যেমন fastboot flashall চালানো, তখন নিম্নলিখিত প্রবাহটি ব্যবহার করার পরামর্শ দেওয়া হয়:

  1. getvar snapshot-update-status জিজ্ঞাসা করুন।
  2. merging বা snapshotted করা হলে, snapshot-update cancel ইস্যু করুন।
  3. ঝলকানি পদক্ষেপ নিয়ে এগিয়ে যান।

স্টোরেজ প্রয়োজনীয়তা হ্রাস

যে ডিভাইসগুলিতে সুপারে সম্পূর্ণ A/B স্টোরেজ বরাদ্দ নেই, এবং প্রয়োজনে /data ব্যবহার করার আশা করছেন, তাদের ব্লক ম্যাপিং টুল ব্যবহার করার জন্য দৃঢ়ভাবে সুপারিশ করা হয়। ব্লক ম্যাপিং টুল বিল্ডগুলির মধ্যে ব্লক বরাদ্দকে সামঞ্জস্যপূর্ণ রাখে, স্ন্যাপশটে অপ্রয়োজনীয় লেখাগুলি হ্রাস করে। এটি ওটিএ আকার হ্রাস করার অধীনে নথিভুক্ত করা হয়েছে।