วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

ยกระดับการพัฒนาเฟิร์มแวร์ด้วย OTA พร้อมเรียนรู้หลักการทำงานและแนวทางการนำไปใช้

วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

การอัปเดตเฟิร์มแวร์แบบไร้สาย (OTA) ช่วยให้สามารถแก้ไขซอฟต์แวร์ของอุปกรณ์ฝังตัวจากระยะไกลได้โดยไม่ต้องเข้าถึงตัวอุปกรณ์ และกลายเป็นสิ่งจำเป็นสำหรับการรักษาความปลอดภัย แก้ไขข้อผิดพลาด และเพิ่มคุณสมบัติใหม่ให้กับอุปกรณ์ IoT ที่ใช้งานอยู่ตลอดอายุการใช้งาน ระบบ OTA ประกอบด้วยส่วนประกอบหลายอย่าง ได้แก่ กระบวนการสร้างและลงนามเฟิร์มแวร์ เซิร์ฟเวอร์กระจายหรือ CDN ตัวแทนการอัปเดตฝั่งอุปกรณ์ บูตโหลดเดอร์ที่สามารถจัดการช่องเฟิร์มแวร์หลายช่อง และกลไกการรายงานสถานะการอัปเดต สถาปัตยกรรมที่พบมากที่สุดคือการแบ่งพาร์ติชันแบบ A/B (dual-bank) โดยเฟิร์มแวร์ใหม่จะถูกดาวน์โหลดไปยังช่องที่ไม่ได้ใช้งานในขณะที่เฟิร์มแวร์ปัจจุบันยังคงทำงานอยู่ จากนั้นบูตโหลดเดอร์จะสลับไปยังช่องที่ใช้งานอยู่เมื่อรีบูตหลังจากตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจใหม่แล้ว วิธีนี้ช่วยให้มั่นใจได้ว่าอุปกรณ์จะมีระบบสำรองที่ใช้งานได้ดีเสมอหากการอัปเดตล้มเหลว การอัปเดตแบบเดลต้า (differential) ช่วยลดขนาดการดาวน์โหลดโดยการส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่มีแบนด์วิดท์จำกัดที่ใช้ LoRaWAN หรือ NB-IoT ซึ่งการถ่ายโอนอิมเมจแบบเต็มจะใช้เวลาหลายชั่วโมง

การอัปเดต OTA แบบแบ่งพาร์ติชั่น A/B ทำงานอย่างไร?

ในระบบแบ่งพาร์ติชั่นแบบ A/B หน่วยความจำแฟลชของอุปกรณ์จะถูกแบ่งออกเป็นพื้นที่บูตโหลดเดอร์ สล็อต 0 (หลัก/ใช้งาน) และสล็อต 1 (รอง/เตรียมการ) เมื่อมีการอัปเดต โปรแกรมอัปเดตจะดาวน์โหลดอิมเมจเฟิร์มแวร์ที่ลงนามแล้วใหม่ลงในสล็อต 1 ในขณะที่แอปพลิเคชันในสล็อต 0 ยังคงทำงานตามปกติ เมื่อการดาวน์โหลดเสร็จสมบูรณ์และตรวจสอบความถูกต้องของส่วนหัวของอิมเมจแล้ว อุปกรณ์จะตั้งค่าสถานะสล็อต 1 เป็นรอการดำเนินการและรีบูต บูตโหลดเดอร์ (โดยทั่วไปคือ MCUboot) จะอ่านสถานะรอการดำเนินการ ตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจในสล็อต 1 และสลับสล็อตทั้งสองหรือบูตจากสล็อตใหม่โดยตรง หลังจากบูตครั้งแรก แอปพลิเคชันจะต้องยืนยันการอัปเดตโดยการตั้งค่าสถานะ "ยืนยันแล้ว" มิฉะนั้น บูตโหลดเดอร์จะย้อนกลับไปใช้อิมเมจก่อนหน้าในการรีบูตครั้งถัดไป ซึ่งเป็นการป้องกันการย้อนกลับอัตโนมัติ

/* MCUboot swap states and OTA flow */

// Device flash layout
// ┌──────────────────┐ 0x00000
// │    MCUboot       │ (32 KB)
// ├──────────────────┤ 0x08000
// │  Slot 0 (Active) │ (384 KB)
// ├──────────────────┤ 0x68000
// │  Slot 1 (Staging)│ (384 KB)
// ├──────────────────┤ 0xC8000
// │  Scratch Area    │ (16 KB)
// └──────────────────┘

// OTA update agent pseudocode
void ota_update_task(void) {
    fw_image_t *image = ota_check_for_update();
    if (image == NULL) return;
    
    // Download to Slot 1
    ota_download_to_slot1(image->url, image->size);
    
    // Verify checksum before requesting swap
    if (verify_sha256(SLOT1_ADDR, image->size, image->hash)) {
        boot_request_upgrade();
        NVIC_SystemReset();
    }
}

// After boot, confirm update succeeded
void app_init(void) {
    if (boot_is_img_confirmed() == false) {
        if (self_test_passed()) {
            boot_write_img_confirmed();
        }
        // If not confirmed, MCUboot will revert on next reboot
    }
}

การอัปเดต Delta คืออะไร และคุณควรใช้งานเมื่อใด?

การอัปเดตแบบเดลต้า (ดิฟเฟอเรนเชียล) จะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งช่วยลดขนาดการดาวน์โหลดได้อย่างมาก เครื่องมืออย่าง jdiff, bsdiff หรือโมดูลการอัปเดตแบบเดลต้าของ Mender สามารถบีบอัดส่วนต่างของเฟิร์มแวร์ให้เหลือเพียง 10-30% ของขนาดอิมเมจเต็ม ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่เชื่อมต่อ LPWAN เนื่องจากอิมเมจเฟิร์มแวร์ขนาด 256 KB ที่อัตราการส่งข้อมูล LoRaWAN อาจใช้เวลาดาวน์โหลดมากกว่า 30 นาทีหากเป็นอิมเมจเต็ม แต่ใช้เวลาน้อยกว่า 5 นาทีหากเป็นการอัปเดตแบบเดลต้า ข้อเสียคือการอัปเดตแบบเดลต้าต้องการให้อุปกรณ์มี RAM หรือแฟลชชั่วคราวเพียงพอในการสร้างอิมเมจเต็มขึ้นมาใหม่ และต้องสร้างการอัปเดตแบบเดลต้าสำหรับแต่ละการเปลี่ยนจากเวอร์ชันต้นทางไปยังเวอร์ชันเป้าหมายโดยเฉพาะ

แพลตฟอร์มคลาวด์ใดบ้างที่รองรับการอัปเดต OTA สำหรับอุปกรณ์ IoT?

แพลตฟอร์มการอัปเดต OTA หลักๆ และจุดแข็งของแต่ละแพลตฟอร์ม:

  • AWS IoT Jobs + S3: การส่งมอบการอัปเดตที่ปรับขนาดได้ พร้อมการจัดการกลุ่มอุปกรณ์ การแจ้งเตือนงานแบบ MQTT และการผสานรวมกับไลบรารี FreeRTOS OTA
  • Azure Device Update สำหรับ IoT Hub: รองรับการอัปเดตแบบ A/B และการอัปเดตแบบเดลต้าด้วยกลุ่มอุปกรณ์และการทยอยเปิดใช้งาน
  • Mender.io: แพลตฟอร์ม OTA แบบโอเพนซอร์ส พร้อมรองรับ MCU, การอัปเดตแบบเดลต้า และตัวเลือก SaaS แบบโฮสต์ ได้รับความนิยมในกลุ่มผู้ใช้งานระบบฝังตัว
  • Memfault: ผสานรวมการอัปเดต OTA เข้ากับการตรวจสอบอุปกรณ์ การรายงานข้อผิดพลาด และเมตริกของกลุ่มอุปกรณ์ รองรับ MCUboot และบูตโหลดเดอร์แบบกำหนดเอง
  • Golioth: แพลตฟอร์มคลาวด์ที่ออกแบบมาโดยเฉพาะสำหรับอุปกรณ์ IoT ที่ใช้ MCU พร้อมระบบอัปเดตแบบไร้สาย (OTA) การบันทึกข้อมูล และการจัดการการตั้งค่าในตัว

วิธีป้องกันความล้มเหลวในการอัปเดต OTA คืออะไร?

ความน่าเชื่อถือของการอัปเดตแบบไร้สาย (OTA) ต้องอาศัยการออกแบบทางวิศวกรรมที่รอบคอบ ควรใช้การตรวจสอบความถูกต้องของข้อมูล (checksum) ในหลายระดับ ได้แก่ ความสมบูรณ์ของเลเยอร์การขนส่ง (TLS), แฮช SHA-256 ระดับอิมเมจ และการตรวจสอบลายเซ็น ใช้ตัวจับเวลาเฝ้าระวัง (watchdog timer) เพื่อตรวจจับการวนลูปการบูตและเรียกใช้การย้อนกลับอัตโนมัติ ทดสอบการอัปเดตกับฮาร์ดแวร์ทุกเวอร์ชันในอุปกรณ์ของคุณก่อนที่จะใช้งานในวงกว้าง ดำเนินการทดสอบแบบเป็นขั้นตอน (canary deployments) โดยเริ่มจากการอัปเดต 1%, 10% และ 100% ของอุปกรณ์ และตรวจสอบอัตราข้อผิดพลาดในแต่ละขั้นตอน เก็บรักษาบันทึกสถานะการอัปเดตอย่างถาวรเพื่อให้ระบบคลาวด์สามารถติดตามได้ว่าอุปกรณ์ใดอัปเดตสำเร็จ อุปกรณ์ใดล้มเหลว และเพราะเหตุใด สำหรับอุปกรณ์ที่ใช้แบตเตอรี่ ควรตรวจสอบระดับแบตเตอรี่ก่อนเริ่มการอัปเดต การอัปเดตที่ล้มเหลวระหว่างการเขียนเนื่องจากการสูญเสียพลังงานอาจทำให้อุปกรณ์เสียหายได้

ประเด็นสำคัญ: การอัปเดตเฟิร์มแวร์แบบ OTA จำเป็นต้องมีการแบ่งพาร์ติชั่นแฟลชแบบ A/B เพื่อการย้อนกลับที่ปลอดภัย การตรวจสอบลายเซ็นเข้ารหัสลับ (ECDSA P-256 หรือ Ed25519) เพื่อป้องกันการเรียกใช้โค้ดโดยไม่ได้รับอนุญาต ตัวนับเวอร์ชันแบบโมโนโทนิกเพื่อป้องกันการย้อนกลับ และการติดตั้งใช้งานในกลุ่มอุปกรณ์แบบเป็นขั้นตอน การอัปเดตแบบเดลต้าช่วยลดขนาดการดาวน์โหลดลง 70-90% สำหรับอุปกรณ์ LPWAN ที่มีแบนด์วิดท์จำกัด

เราจัดการกับการอัปเดต OTA สำหรับอุปกรณ์จำนวน 10,000 เครื่องได้อย่างไร?

ที่ EmbedCrest เราได้ออกแบบและติดตั้งโครงสร้างพื้นฐาน OTA สำหรับบริษัทมิเตอร์อัจฉริยะที่มีมิเตอร์น้ำเชื่อมต่อ LoRaWAN จำนวน 10,000 เครื่องทั่วพื้นที่เมืองใหญ่ มิเตอร์แต่ละเครื่องใช้ไมโครคอนโทรลเลอร์ STM32L4 ที่มีหน่วยความจำแฟลช 1 MB แบ่งเป็น MCUboot ขนาด 32 KB, Slot 0 (ใช้งานอยู่) ขนาด 448 KB, Slot 1 (เตรียมการ) ขนาด 448 KB และพื้นที่ชั่วคราวขนาด 16 KB เนื่องจากข้อจำกัดด้านแบนด์วิดท์ของ LoRaWAN (ประมาณ 50 ไบต์ต่อลิงก์อัปที่ SF10) การถ่ายโอนภาพเฟิร์มแวร์ขนาด 200 KB เต็มรูปแบบจะใช้แพ็กเก็ตมากกว่า 4,000 แพ็กเก็ตและใช้เวลานานกว่า 40 ชั่วโมง เราจึงนำการอัปเดตแบบเดลต้าโดยใช้ bsdiff มาใช้ ซึ่งบีบอัดการเปลี่ยนแปลงเฟิร์มแวร์ทั่วไปให้เหลือเพียง 15-30 KB ลดเวลาการถ่ายโอนเหลือ 3-6 ชั่วโมงต่ออุปกรณ์ กระบวนการอัปเดตใช้โหมดมัลติแคสต์คลาส C: มิเตอร์จะเปลี่ยนจากคลาส A (พลังงานต่ำสุด) ไปเป็นคลาส C (รับฟังอย่างต่อเนื่อง) ชั่วคราวในช่วงเวลาการบำรุงรักษาตามกำหนดการ รับข้อมูลส่วนต่างผ่านลิงก์ดาวน์ลิงก์มัลติแคสต์ และเปลี่ยนกลับไปเป็นคลาส A หลังจากได้รับการยืนยัน เราดำเนินการติดตั้งใน 5 ขั้นตอน: กลุ่มทดสอบ 1%, 10%, 25%, 50% และ 100% โดยตรวจสอบอัตราความสำเร็จ การตรวจจับลูปการบูต และความผิดปกติของการใช้พลังงานในแต่ละขั้นตอน

โหมดความล้มเหลวของ OTA ที่อันตรายที่สุดมีอะไรบ้าง?

โหมดความล้มเหลว OTA ที่ร้ายแรงที่สุดคืออุปกรณ์เสียหายจนไม่สามารถกู้คืนได้หากไม่มีการเข้าถึงทางกายภาพ ปัญหานี้เกิดขึ้นเมื่อบูตโหลดเดอร์เสียหายหรือเมื่อช่องเสียบเฟิร์มแวร์ทั้งสองช่องมีอิมเมจที่ไม่ถูกต้อง วิธีแก้ไขคือทำให้บูตโหลดเดอร์ไม่สามารถเปลี่ยนแปลงได้ (วางไว้ในพื้นที่แฟลชที่ป้องกันการเขียน) ใช้พาร์ติชั่นกู้คืนอิมเมจต้นแบบ (เฟิร์มแวร์ขนาดเล็กในพื้นที่แฟลชที่ป้องกันแยกต่างหาก ซึ่งบูตโหลดเดอร์ ROM จะใช้เป็นตัวสำรอง) และตรวจสอบระดับแบตเตอรี่ก่อนเริ่มกระบวนการอัปเดต สำหรับอุปกรณ์ STM32 ให้กำหนดค่า Option Bytes เพื่อป้องกันการเขียนพื้นที่แฟลชบูตโหลดเดอร์โดยใช้บิต WRP (Write Protection) ความล้มเหลวที่อันตรายอีกอย่างคือการอัปเดตสำเร็จแต่มีข้อบกพร่องเล็กน้อยที่ตรวจพบได้หลังจากนั้นหลายสัปดาห์ หลังจากที่อัปเดตอุปกรณ์ทั้งหมดแล้ว วิธีแก้ไขคือใช้การตรวจสอบสถานะอัตโนมัติ: เฟิร์มแวร์ที่อัปเดตแล้วต้องยืนยันตัวเองภายในระยะเวลาที่กำหนดได้ (30-300 วินาที) โดยการเรียกใช้ boot_write_img_confirmed() มิฉะนั้นบูตโหลดเดอร์จะกลับไปสู่สถานะเดิมโดยอัตโนมัติ ควรเพิ่มการทดสอบตัวเองเชิงฟังก์ชัน (การตรวจสอบความถูกต้องของการอ่านค่าเซ็นเซอร์ การวนรอบการสื่อสาร การตรวจสอบการทำงานของระบบเฝ้าระวัง) เข้าไปในตรรกะการยืนยัน ไม่ใช่แค่การใช้ตัวจับเวลาแบบง่ายๆ เท่านั้น

คุณจะเลือกอย่างไรระหว่างการอัปเดตแบบเต็มภาพและการอัปเดต OTA ของ Delta?

การอัปเดตอิมเมจแบบเต็มจะส่งไบนารีเฟิร์มแวร์ทั้งหมดที่ได้รับการตรวจสอบโดยแฮช SHA-256 และลายเซ็น ECDSA การอัปเดตแบบนี้ทำได้ง่ายกว่า ไม่ต้องใช้ตรรกะการสร้างใหม่ฝั่งไคลเอ็นต์ และสามารถอัปเดตจากเวอร์ชันใดก็ได้ไปยังเวอร์ชันใดก็ได้ อย่างไรก็ตาม การอัปเดตแบบนี้ใช้แบนด์วิดท์และเวลาในการถ่ายโอนสูงสุด ส่วนการอัปเดตแบบเดลต้าจะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งสร้างขึ้นโดยใช้อัลกอริทึม เช่น bsdiff, xdelta3 หรือ mender-binary-delta ของ Mender แพทช์เดลต้าโดยทั่วไปจะมีขนาด 10-30% ของขนาดอิมเมจแบบเต็มสำหรับการอัปเดตเล็กน้อย และ 40-60% สำหรับการปรับโครงสร้างครั้งใหญ่ ข้อเสียของการอัปเดตแบบเดลต้ามีมากมาย: การอัปเดตแบบเดลต้าต้องการให้เครื่องมี RAM หรือแฟลชชั่วคราวเพียงพอในการใช้แพทช์ (bsdiff ต้องการหน่วยความจำทำงานประมาณ 2 เท่าของขนาดแพทช์) ต้องสร้างแพทช์สำหรับแต่ละชุดเวอร์ชันต้นทางถึงเป้าหมาย (N เวอร์ชันสร้าง N-1 แพทช์สำหรับการอัปเดตตามลำดับ หรือ N*(N-1)/2 สำหรับการข้ามเวอร์ชันแบบสุ่ม) และอิมเมจปัจจุบันที่เสียหายจะป้องกันการใช้แพทช์ สำหรับอุปกรณ์ที่เชื่อมต่อผ่าน LPWAN ซึ่งมีข้อจำกัดด้านแบนด์วิดท์สูง การอัปเดตแบบเดลต้าจึงเป็นสิ่งจำเป็น ส่วนอุปกรณ์ที่เชื่อมต่อผ่าน Wi-Fi ซึ่งมีแบนด์วิดท์เหลือเฟือ การอัปเดตภาพเต็มรูปแบบนั้นง่ายกว่าและมีประสิทธิภาพมากกว่า

วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

ยกระดับการพัฒนาเฟิร์มแวร์ด้วย OTA พร้อมเรียนรู้หลักการทำงานและแนวทางการนำไปใช้

นักเขียนบทความ
by 
นักเขียนบทความ
วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

ยกระดับการพัฒนาเฟิร์มแวร์ด้วย OTA พร้อมเรียนรู้หลักการทำงานและแนวทางการนำไปใช้

การอัปเดตเฟิร์มแวร์แบบไร้สาย (OTA) ช่วยให้สามารถแก้ไขซอฟต์แวร์ของอุปกรณ์ฝังตัวจากระยะไกลได้โดยไม่ต้องเข้าถึงตัวอุปกรณ์ และกลายเป็นสิ่งจำเป็นสำหรับการรักษาความปลอดภัย แก้ไขข้อผิดพลาด และเพิ่มคุณสมบัติใหม่ให้กับอุปกรณ์ IoT ที่ใช้งานอยู่ตลอดอายุการใช้งาน ระบบ OTA ประกอบด้วยส่วนประกอบหลายอย่าง ได้แก่ กระบวนการสร้างและลงนามเฟิร์มแวร์ เซิร์ฟเวอร์กระจายหรือ CDN ตัวแทนการอัปเดตฝั่งอุปกรณ์ บูตโหลดเดอร์ที่สามารถจัดการช่องเฟิร์มแวร์หลายช่อง และกลไกการรายงานสถานะการอัปเดต สถาปัตยกรรมที่พบมากที่สุดคือการแบ่งพาร์ติชันแบบ A/B (dual-bank) โดยเฟิร์มแวร์ใหม่จะถูกดาวน์โหลดไปยังช่องที่ไม่ได้ใช้งานในขณะที่เฟิร์มแวร์ปัจจุบันยังคงทำงานอยู่ จากนั้นบูตโหลดเดอร์จะสลับไปยังช่องที่ใช้งานอยู่เมื่อรีบูตหลังจากตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจใหม่แล้ว วิธีนี้ช่วยให้มั่นใจได้ว่าอุปกรณ์จะมีระบบสำรองที่ใช้งานได้ดีเสมอหากการอัปเดตล้มเหลว การอัปเดตแบบเดลต้า (differential) ช่วยลดขนาดการดาวน์โหลดโดยการส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่มีแบนด์วิดท์จำกัดที่ใช้ LoRaWAN หรือ NB-IoT ซึ่งการถ่ายโอนอิมเมจแบบเต็มจะใช้เวลาหลายชั่วโมง

การอัปเดต OTA แบบแบ่งพาร์ติชั่น A/B ทำงานอย่างไร?

ในระบบแบ่งพาร์ติชั่นแบบ A/B หน่วยความจำแฟลชของอุปกรณ์จะถูกแบ่งออกเป็นพื้นที่บูตโหลดเดอร์ สล็อต 0 (หลัก/ใช้งาน) และสล็อต 1 (รอง/เตรียมการ) เมื่อมีการอัปเดต โปรแกรมอัปเดตจะดาวน์โหลดอิมเมจเฟิร์มแวร์ที่ลงนามแล้วใหม่ลงในสล็อต 1 ในขณะที่แอปพลิเคชันในสล็อต 0 ยังคงทำงานตามปกติ เมื่อการดาวน์โหลดเสร็จสมบูรณ์และตรวจสอบความถูกต้องของส่วนหัวของอิมเมจแล้ว อุปกรณ์จะตั้งค่าสถานะสล็อต 1 เป็นรอการดำเนินการและรีบูต บูตโหลดเดอร์ (โดยทั่วไปคือ MCUboot) จะอ่านสถานะรอการดำเนินการ ตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจในสล็อต 1 และสลับสล็อตทั้งสองหรือบูตจากสล็อตใหม่โดยตรง หลังจากบูตครั้งแรก แอปพลิเคชันจะต้องยืนยันการอัปเดตโดยการตั้งค่าสถานะ "ยืนยันแล้ว" มิฉะนั้น บูตโหลดเดอร์จะย้อนกลับไปใช้อิมเมจก่อนหน้าในการรีบูตครั้งถัดไป ซึ่งเป็นการป้องกันการย้อนกลับอัตโนมัติ

/* MCUboot swap states and OTA flow */

// Device flash layout
// ┌──────────────────┐ 0x00000
// │    MCUboot       │ (32 KB)
// ├──────────────────┤ 0x08000
// │  Slot 0 (Active) │ (384 KB)
// ├──────────────────┤ 0x68000
// │  Slot 1 (Staging)│ (384 KB)
// ├──────────────────┤ 0xC8000
// │  Scratch Area    │ (16 KB)
// └──────────────────┘

// OTA update agent pseudocode
void ota_update_task(void) {
    fw_image_t *image = ota_check_for_update();
    if (image == NULL) return;
    
    // Download to Slot 1
    ota_download_to_slot1(image->url, image->size);
    
    // Verify checksum before requesting swap
    if (verify_sha256(SLOT1_ADDR, image->size, image->hash)) {
        boot_request_upgrade();
        NVIC_SystemReset();
    }
}

// After boot, confirm update succeeded
void app_init(void) {
    if (boot_is_img_confirmed() == false) {
        if (self_test_passed()) {
            boot_write_img_confirmed();
        }
        // If not confirmed, MCUboot will revert on next reboot
    }
}

การอัปเดต Delta คืออะไร และคุณควรใช้งานเมื่อใด?

การอัปเดตแบบเดลต้า (ดิฟเฟอเรนเชียล) จะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งช่วยลดขนาดการดาวน์โหลดได้อย่างมาก เครื่องมืออย่าง jdiff, bsdiff หรือโมดูลการอัปเดตแบบเดลต้าของ Mender สามารถบีบอัดส่วนต่างของเฟิร์มแวร์ให้เหลือเพียง 10-30% ของขนาดอิมเมจเต็ม ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่เชื่อมต่อ LPWAN เนื่องจากอิมเมจเฟิร์มแวร์ขนาด 256 KB ที่อัตราการส่งข้อมูล LoRaWAN อาจใช้เวลาดาวน์โหลดมากกว่า 30 นาทีหากเป็นอิมเมจเต็ม แต่ใช้เวลาน้อยกว่า 5 นาทีหากเป็นการอัปเดตแบบเดลต้า ข้อเสียคือการอัปเดตแบบเดลต้าต้องการให้อุปกรณ์มี RAM หรือแฟลชชั่วคราวเพียงพอในการสร้างอิมเมจเต็มขึ้นมาใหม่ และต้องสร้างการอัปเดตแบบเดลต้าสำหรับแต่ละการเปลี่ยนจากเวอร์ชันต้นทางไปยังเวอร์ชันเป้าหมายโดยเฉพาะ

แพลตฟอร์มคลาวด์ใดบ้างที่รองรับการอัปเดต OTA สำหรับอุปกรณ์ IoT?

แพลตฟอร์มการอัปเดต OTA หลักๆ และจุดแข็งของแต่ละแพลตฟอร์ม:

  • AWS IoT Jobs + S3: การส่งมอบการอัปเดตที่ปรับขนาดได้ พร้อมการจัดการกลุ่มอุปกรณ์ การแจ้งเตือนงานแบบ MQTT และการผสานรวมกับไลบรารี FreeRTOS OTA
  • Azure Device Update สำหรับ IoT Hub: รองรับการอัปเดตแบบ A/B และการอัปเดตแบบเดลต้าด้วยกลุ่มอุปกรณ์และการทยอยเปิดใช้งาน
  • Mender.io: แพลตฟอร์ม OTA แบบโอเพนซอร์ส พร้อมรองรับ MCU, การอัปเดตแบบเดลต้า และตัวเลือก SaaS แบบโฮสต์ ได้รับความนิยมในกลุ่มผู้ใช้งานระบบฝังตัว
  • Memfault: ผสานรวมการอัปเดต OTA เข้ากับการตรวจสอบอุปกรณ์ การรายงานข้อผิดพลาด และเมตริกของกลุ่มอุปกรณ์ รองรับ MCUboot และบูตโหลดเดอร์แบบกำหนดเอง
  • Golioth: แพลตฟอร์มคลาวด์ที่ออกแบบมาโดยเฉพาะสำหรับอุปกรณ์ IoT ที่ใช้ MCU พร้อมระบบอัปเดตแบบไร้สาย (OTA) การบันทึกข้อมูล และการจัดการการตั้งค่าในตัว

วิธีป้องกันความล้มเหลวในการอัปเดต OTA คืออะไร?

ความน่าเชื่อถือของการอัปเดตแบบไร้สาย (OTA) ต้องอาศัยการออกแบบทางวิศวกรรมที่รอบคอบ ควรใช้การตรวจสอบความถูกต้องของข้อมูล (checksum) ในหลายระดับ ได้แก่ ความสมบูรณ์ของเลเยอร์การขนส่ง (TLS), แฮช SHA-256 ระดับอิมเมจ และการตรวจสอบลายเซ็น ใช้ตัวจับเวลาเฝ้าระวัง (watchdog timer) เพื่อตรวจจับการวนลูปการบูตและเรียกใช้การย้อนกลับอัตโนมัติ ทดสอบการอัปเดตกับฮาร์ดแวร์ทุกเวอร์ชันในอุปกรณ์ของคุณก่อนที่จะใช้งานในวงกว้าง ดำเนินการทดสอบแบบเป็นขั้นตอน (canary deployments) โดยเริ่มจากการอัปเดต 1%, 10% และ 100% ของอุปกรณ์ และตรวจสอบอัตราข้อผิดพลาดในแต่ละขั้นตอน เก็บรักษาบันทึกสถานะการอัปเดตอย่างถาวรเพื่อให้ระบบคลาวด์สามารถติดตามได้ว่าอุปกรณ์ใดอัปเดตสำเร็จ อุปกรณ์ใดล้มเหลว และเพราะเหตุใด สำหรับอุปกรณ์ที่ใช้แบตเตอรี่ ควรตรวจสอบระดับแบตเตอรี่ก่อนเริ่มการอัปเดต การอัปเดตที่ล้มเหลวระหว่างการเขียนเนื่องจากการสูญเสียพลังงานอาจทำให้อุปกรณ์เสียหายได้

ประเด็นสำคัญ: การอัปเดตเฟิร์มแวร์แบบ OTA จำเป็นต้องมีการแบ่งพาร์ติชั่นแฟลชแบบ A/B เพื่อการย้อนกลับที่ปลอดภัย การตรวจสอบลายเซ็นเข้ารหัสลับ (ECDSA P-256 หรือ Ed25519) เพื่อป้องกันการเรียกใช้โค้ดโดยไม่ได้รับอนุญาต ตัวนับเวอร์ชันแบบโมโนโทนิกเพื่อป้องกันการย้อนกลับ และการติดตั้งใช้งานในกลุ่มอุปกรณ์แบบเป็นขั้นตอน การอัปเดตแบบเดลต้าช่วยลดขนาดการดาวน์โหลดลง 70-90% สำหรับอุปกรณ์ LPWAN ที่มีแบนด์วิดท์จำกัด

เราจัดการกับการอัปเดต OTA สำหรับอุปกรณ์จำนวน 10,000 เครื่องได้อย่างไร?

ที่ EmbedCrest เราได้ออกแบบและติดตั้งโครงสร้างพื้นฐาน OTA สำหรับบริษัทมิเตอร์อัจฉริยะที่มีมิเตอร์น้ำเชื่อมต่อ LoRaWAN จำนวน 10,000 เครื่องทั่วพื้นที่เมืองใหญ่ มิเตอร์แต่ละเครื่องใช้ไมโครคอนโทรลเลอร์ STM32L4 ที่มีหน่วยความจำแฟลช 1 MB แบ่งเป็น MCUboot ขนาด 32 KB, Slot 0 (ใช้งานอยู่) ขนาด 448 KB, Slot 1 (เตรียมการ) ขนาด 448 KB และพื้นที่ชั่วคราวขนาด 16 KB เนื่องจากข้อจำกัดด้านแบนด์วิดท์ของ LoRaWAN (ประมาณ 50 ไบต์ต่อลิงก์อัปที่ SF10) การถ่ายโอนภาพเฟิร์มแวร์ขนาด 200 KB เต็มรูปแบบจะใช้แพ็กเก็ตมากกว่า 4,000 แพ็กเก็ตและใช้เวลานานกว่า 40 ชั่วโมง เราจึงนำการอัปเดตแบบเดลต้าโดยใช้ bsdiff มาใช้ ซึ่งบีบอัดการเปลี่ยนแปลงเฟิร์มแวร์ทั่วไปให้เหลือเพียง 15-30 KB ลดเวลาการถ่ายโอนเหลือ 3-6 ชั่วโมงต่ออุปกรณ์ กระบวนการอัปเดตใช้โหมดมัลติแคสต์คลาส C: มิเตอร์จะเปลี่ยนจากคลาส A (พลังงานต่ำสุด) ไปเป็นคลาส C (รับฟังอย่างต่อเนื่อง) ชั่วคราวในช่วงเวลาการบำรุงรักษาตามกำหนดการ รับข้อมูลส่วนต่างผ่านลิงก์ดาวน์ลิงก์มัลติแคสต์ และเปลี่ยนกลับไปเป็นคลาส A หลังจากได้รับการยืนยัน เราดำเนินการติดตั้งใน 5 ขั้นตอน: กลุ่มทดสอบ 1%, 10%, 25%, 50% และ 100% โดยตรวจสอบอัตราความสำเร็จ การตรวจจับลูปการบูต และความผิดปกติของการใช้พลังงานในแต่ละขั้นตอน

โหมดความล้มเหลวของ OTA ที่อันตรายที่สุดมีอะไรบ้าง?

โหมดความล้มเหลว OTA ที่ร้ายแรงที่สุดคืออุปกรณ์เสียหายจนไม่สามารถกู้คืนได้หากไม่มีการเข้าถึงทางกายภาพ ปัญหานี้เกิดขึ้นเมื่อบูตโหลดเดอร์เสียหายหรือเมื่อช่องเสียบเฟิร์มแวร์ทั้งสองช่องมีอิมเมจที่ไม่ถูกต้อง วิธีแก้ไขคือทำให้บูตโหลดเดอร์ไม่สามารถเปลี่ยนแปลงได้ (วางไว้ในพื้นที่แฟลชที่ป้องกันการเขียน) ใช้พาร์ติชั่นกู้คืนอิมเมจต้นแบบ (เฟิร์มแวร์ขนาดเล็กในพื้นที่แฟลชที่ป้องกันแยกต่างหาก ซึ่งบูตโหลดเดอร์ ROM จะใช้เป็นตัวสำรอง) และตรวจสอบระดับแบตเตอรี่ก่อนเริ่มกระบวนการอัปเดต สำหรับอุปกรณ์ STM32 ให้กำหนดค่า Option Bytes เพื่อป้องกันการเขียนพื้นที่แฟลชบูตโหลดเดอร์โดยใช้บิต WRP (Write Protection) ความล้มเหลวที่อันตรายอีกอย่างคือการอัปเดตสำเร็จแต่มีข้อบกพร่องเล็กน้อยที่ตรวจพบได้หลังจากนั้นหลายสัปดาห์ หลังจากที่อัปเดตอุปกรณ์ทั้งหมดแล้ว วิธีแก้ไขคือใช้การตรวจสอบสถานะอัตโนมัติ: เฟิร์มแวร์ที่อัปเดตแล้วต้องยืนยันตัวเองภายในระยะเวลาที่กำหนดได้ (30-300 วินาที) โดยการเรียกใช้ boot_write_img_confirmed() มิฉะนั้นบูตโหลดเดอร์จะกลับไปสู่สถานะเดิมโดยอัตโนมัติ ควรเพิ่มการทดสอบตัวเองเชิงฟังก์ชัน (การตรวจสอบความถูกต้องของการอ่านค่าเซ็นเซอร์ การวนรอบการสื่อสาร การตรวจสอบการทำงานของระบบเฝ้าระวัง) เข้าไปในตรรกะการยืนยัน ไม่ใช่แค่การใช้ตัวจับเวลาแบบง่ายๆ เท่านั้น

คุณจะเลือกอย่างไรระหว่างการอัปเดตแบบเต็มภาพและการอัปเดต OTA ของ Delta?

การอัปเดตอิมเมจแบบเต็มจะส่งไบนารีเฟิร์มแวร์ทั้งหมดที่ได้รับการตรวจสอบโดยแฮช SHA-256 และลายเซ็น ECDSA การอัปเดตแบบนี้ทำได้ง่ายกว่า ไม่ต้องใช้ตรรกะการสร้างใหม่ฝั่งไคลเอ็นต์ และสามารถอัปเดตจากเวอร์ชันใดก็ได้ไปยังเวอร์ชันใดก็ได้ อย่างไรก็ตาม การอัปเดตแบบนี้ใช้แบนด์วิดท์และเวลาในการถ่ายโอนสูงสุด ส่วนการอัปเดตแบบเดลต้าจะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งสร้างขึ้นโดยใช้อัลกอริทึม เช่น bsdiff, xdelta3 หรือ mender-binary-delta ของ Mender แพทช์เดลต้าโดยทั่วไปจะมีขนาด 10-30% ของขนาดอิมเมจแบบเต็มสำหรับการอัปเดตเล็กน้อย และ 40-60% สำหรับการปรับโครงสร้างครั้งใหญ่ ข้อเสียของการอัปเดตแบบเดลต้ามีมากมาย: การอัปเดตแบบเดลต้าต้องการให้เครื่องมี RAM หรือแฟลชชั่วคราวเพียงพอในการใช้แพทช์ (bsdiff ต้องการหน่วยความจำทำงานประมาณ 2 เท่าของขนาดแพทช์) ต้องสร้างแพทช์สำหรับแต่ละชุดเวอร์ชันต้นทางถึงเป้าหมาย (N เวอร์ชันสร้าง N-1 แพทช์สำหรับการอัปเดตตามลำดับ หรือ N*(N-1)/2 สำหรับการข้ามเวอร์ชันแบบสุ่ม) และอิมเมจปัจจุบันที่เสียหายจะป้องกันการใช้แพทช์ สำหรับอุปกรณ์ที่เชื่อมต่อผ่าน LPWAN ซึ่งมีข้อจำกัดด้านแบนด์วิดท์สูง การอัปเดตแบบเดลต้าจึงเป็นสิ่งจำเป็น ส่วนอุปกรณ์ที่เชื่อมต่อผ่าน Wi-Fi ซึ่งมีแบนด์วิดท์เหลือเฟือ การอัปเดตภาพเต็มรูปแบบนั้นง่ายกว่าและมีประสิทธิภาพมากกว่า

Lorem ipsum dolor sit amet, consectetur adipiscing elit. Suspendisse varius enim in eros elementum tristique. Duis cursus, mi quis viverra ornare, eros dolor interdum nulla, ut commodo diam libero vitae erat. Aenean faucibus nibh et justo cursus id rutrum lorem imperdiet. Nunc ut sem vitae risus tristique posuere.

วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

วิธีการอัปเดตเฟิร์มแวร์ผ่าน OTA: คู่มือสำคัญสำหรับบริษัทพัฒนาเฟิร์มแวร์

ยกระดับการพัฒนาเฟิร์มแวร์ด้วย OTA พร้อมเรียนรู้หลักการทำงานและแนวทางการนำไปใช้

Lorem ipsum dolor amet consectetur adipiscing elit tortor massa arcu non.

การอัปเดตเฟิร์มแวร์แบบไร้สาย (OTA) ช่วยให้สามารถแก้ไขซอฟต์แวร์ของอุปกรณ์ฝังตัวจากระยะไกลได้โดยไม่ต้องเข้าถึงตัวอุปกรณ์ และกลายเป็นสิ่งจำเป็นสำหรับการรักษาความปลอดภัย แก้ไขข้อผิดพลาด และเพิ่มคุณสมบัติใหม่ให้กับอุปกรณ์ IoT ที่ใช้งานอยู่ตลอดอายุการใช้งาน ระบบ OTA ประกอบด้วยส่วนประกอบหลายอย่าง ได้แก่ กระบวนการสร้างและลงนามเฟิร์มแวร์ เซิร์ฟเวอร์กระจายหรือ CDN ตัวแทนการอัปเดตฝั่งอุปกรณ์ บูตโหลดเดอร์ที่สามารถจัดการช่องเฟิร์มแวร์หลายช่อง และกลไกการรายงานสถานะการอัปเดต สถาปัตยกรรมที่พบมากที่สุดคือการแบ่งพาร์ติชันแบบ A/B (dual-bank) โดยเฟิร์มแวร์ใหม่จะถูกดาวน์โหลดไปยังช่องที่ไม่ได้ใช้งานในขณะที่เฟิร์มแวร์ปัจจุบันยังคงทำงานอยู่ จากนั้นบูตโหลดเดอร์จะสลับไปยังช่องที่ใช้งานอยู่เมื่อรีบูตหลังจากตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจใหม่แล้ว วิธีนี้ช่วยให้มั่นใจได้ว่าอุปกรณ์จะมีระบบสำรองที่ใช้งานได้ดีเสมอหากการอัปเดตล้มเหลว การอัปเดตแบบเดลต้า (differential) ช่วยลดขนาดการดาวน์โหลดโดยการส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่มีแบนด์วิดท์จำกัดที่ใช้ LoRaWAN หรือ NB-IoT ซึ่งการถ่ายโอนอิมเมจแบบเต็มจะใช้เวลาหลายชั่วโมง

การอัปเดต OTA แบบแบ่งพาร์ติชั่น A/B ทำงานอย่างไร?

ในระบบแบ่งพาร์ติชั่นแบบ A/B หน่วยความจำแฟลชของอุปกรณ์จะถูกแบ่งออกเป็นพื้นที่บูตโหลดเดอร์ สล็อต 0 (หลัก/ใช้งาน) และสล็อต 1 (รอง/เตรียมการ) เมื่อมีการอัปเดต โปรแกรมอัปเดตจะดาวน์โหลดอิมเมจเฟิร์มแวร์ที่ลงนามแล้วใหม่ลงในสล็อต 1 ในขณะที่แอปพลิเคชันในสล็อต 0 ยังคงทำงานตามปกติ เมื่อการดาวน์โหลดเสร็จสมบูรณ์และตรวจสอบความถูกต้องของส่วนหัวของอิมเมจแล้ว อุปกรณ์จะตั้งค่าสถานะสล็อต 1 เป็นรอการดำเนินการและรีบูต บูตโหลดเดอร์ (โดยทั่วไปคือ MCUboot) จะอ่านสถานะรอการดำเนินการ ตรวจสอบลายเซ็นการเข้ารหัสของอิมเมจในสล็อต 1 และสลับสล็อตทั้งสองหรือบูตจากสล็อตใหม่โดยตรง หลังจากบูตครั้งแรก แอปพลิเคชันจะต้องยืนยันการอัปเดตโดยการตั้งค่าสถานะ "ยืนยันแล้ว" มิฉะนั้น บูตโหลดเดอร์จะย้อนกลับไปใช้อิมเมจก่อนหน้าในการรีบูตครั้งถัดไป ซึ่งเป็นการป้องกันการย้อนกลับอัตโนมัติ

/* MCUboot swap states and OTA flow */

// Device flash layout
// ┌──────────────────┐ 0x00000
// │    MCUboot       │ (32 KB)
// ├──────────────────┤ 0x08000
// │  Slot 0 (Active) │ (384 KB)
// ├──────────────────┤ 0x68000
// │  Slot 1 (Staging)│ (384 KB)
// ├──────────────────┤ 0xC8000
// │  Scratch Area    │ (16 KB)
// └──────────────────┘

// OTA update agent pseudocode
void ota_update_task(void) {
    fw_image_t *image = ota_check_for_update();
    if (image == NULL) return;
    
    // Download to Slot 1
    ota_download_to_slot1(image->url, image->size);
    
    // Verify checksum before requesting swap
    if (verify_sha256(SLOT1_ADDR, image->size, image->hash)) {
        boot_request_upgrade();
        NVIC_SystemReset();
    }
}

// After boot, confirm update succeeded
void app_init(void) {
    if (boot_is_img_confirmed() == false) {
        if (self_test_passed()) {
            boot_write_img_confirmed();
        }
        // If not confirmed, MCUboot will revert on next reboot
    }
}

การอัปเดต Delta คืออะไร และคุณควรใช้งานเมื่อใด?

การอัปเดตแบบเดลต้า (ดิฟเฟอเรนเชียล) จะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันเฟิร์มแวร์ปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งช่วยลดขนาดการดาวน์โหลดได้อย่างมาก เครื่องมืออย่าง jdiff, bsdiff หรือโมดูลการอัปเดตแบบเดลต้าของ Mender สามารถบีบอัดส่วนต่างของเฟิร์มแวร์ให้เหลือเพียง 10-30% ของขนาดอิมเมจเต็ม ซึ่งมีความสำคัญอย่างยิ่งสำหรับอุปกรณ์ที่เชื่อมต่อ LPWAN เนื่องจากอิมเมจเฟิร์มแวร์ขนาด 256 KB ที่อัตราการส่งข้อมูล LoRaWAN อาจใช้เวลาดาวน์โหลดมากกว่า 30 นาทีหากเป็นอิมเมจเต็ม แต่ใช้เวลาน้อยกว่า 5 นาทีหากเป็นการอัปเดตแบบเดลต้า ข้อเสียคือการอัปเดตแบบเดลต้าต้องการให้อุปกรณ์มี RAM หรือแฟลชชั่วคราวเพียงพอในการสร้างอิมเมจเต็มขึ้นมาใหม่ และต้องสร้างการอัปเดตแบบเดลต้าสำหรับแต่ละการเปลี่ยนจากเวอร์ชันต้นทางไปยังเวอร์ชันเป้าหมายโดยเฉพาะ

แพลตฟอร์มคลาวด์ใดบ้างที่รองรับการอัปเดต OTA สำหรับอุปกรณ์ IoT?

แพลตฟอร์มการอัปเดต OTA หลักๆ และจุดแข็งของแต่ละแพลตฟอร์ม:

  • AWS IoT Jobs + S3: การส่งมอบการอัปเดตที่ปรับขนาดได้ พร้อมการจัดการกลุ่มอุปกรณ์ การแจ้งเตือนงานแบบ MQTT และการผสานรวมกับไลบรารี FreeRTOS OTA
  • Azure Device Update สำหรับ IoT Hub: รองรับการอัปเดตแบบ A/B และการอัปเดตแบบเดลต้าด้วยกลุ่มอุปกรณ์และการทยอยเปิดใช้งาน
  • Mender.io: แพลตฟอร์ม OTA แบบโอเพนซอร์ส พร้อมรองรับ MCU, การอัปเดตแบบเดลต้า และตัวเลือก SaaS แบบโฮสต์ ได้รับความนิยมในกลุ่มผู้ใช้งานระบบฝังตัว
  • Memfault: ผสานรวมการอัปเดต OTA เข้ากับการตรวจสอบอุปกรณ์ การรายงานข้อผิดพลาด และเมตริกของกลุ่มอุปกรณ์ รองรับ MCUboot และบูตโหลดเดอร์แบบกำหนดเอง
  • Golioth: แพลตฟอร์มคลาวด์ที่ออกแบบมาโดยเฉพาะสำหรับอุปกรณ์ IoT ที่ใช้ MCU พร้อมระบบอัปเดตแบบไร้สาย (OTA) การบันทึกข้อมูล และการจัดการการตั้งค่าในตัว

วิธีป้องกันความล้มเหลวในการอัปเดต OTA คืออะไร?

ความน่าเชื่อถือของการอัปเดตแบบไร้สาย (OTA) ต้องอาศัยการออกแบบทางวิศวกรรมที่รอบคอบ ควรใช้การตรวจสอบความถูกต้องของข้อมูล (checksum) ในหลายระดับ ได้แก่ ความสมบูรณ์ของเลเยอร์การขนส่ง (TLS), แฮช SHA-256 ระดับอิมเมจ และการตรวจสอบลายเซ็น ใช้ตัวจับเวลาเฝ้าระวัง (watchdog timer) เพื่อตรวจจับการวนลูปการบูตและเรียกใช้การย้อนกลับอัตโนมัติ ทดสอบการอัปเดตกับฮาร์ดแวร์ทุกเวอร์ชันในอุปกรณ์ของคุณก่อนที่จะใช้งานในวงกว้าง ดำเนินการทดสอบแบบเป็นขั้นตอน (canary deployments) โดยเริ่มจากการอัปเดต 1%, 10% และ 100% ของอุปกรณ์ และตรวจสอบอัตราข้อผิดพลาดในแต่ละขั้นตอน เก็บรักษาบันทึกสถานะการอัปเดตอย่างถาวรเพื่อให้ระบบคลาวด์สามารถติดตามได้ว่าอุปกรณ์ใดอัปเดตสำเร็จ อุปกรณ์ใดล้มเหลว และเพราะเหตุใด สำหรับอุปกรณ์ที่ใช้แบตเตอรี่ ควรตรวจสอบระดับแบตเตอรี่ก่อนเริ่มการอัปเดต การอัปเดตที่ล้มเหลวระหว่างการเขียนเนื่องจากการสูญเสียพลังงานอาจทำให้อุปกรณ์เสียหายได้

ประเด็นสำคัญ: การอัปเดตเฟิร์มแวร์แบบ OTA จำเป็นต้องมีการแบ่งพาร์ติชั่นแฟลชแบบ A/B เพื่อการย้อนกลับที่ปลอดภัย การตรวจสอบลายเซ็นเข้ารหัสลับ (ECDSA P-256 หรือ Ed25519) เพื่อป้องกันการเรียกใช้โค้ดโดยไม่ได้รับอนุญาต ตัวนับเวอร์ชันแบบโมโนโทนิกเพื่อป้องกันการย้อนกลับ และการติดตั้งใช้งานในกลุ่มอุปกรณ์แบบเป็นขั้นตอน การอัปเดตแบบเดลต้าช่วยลดขนาดการดาวน์โหลดลง 70-90% สำหรับอุปกรณ์ LPWAN ที่มีแบนด์วิดท์จำกัด

เราจัดการกับการอัปเดต OTA สำหรับอุปกรณ์จำนวน 10,000 เครื่องได้อย่างไร?

ที่ EmbedCrest เราได้ออกแบบและติดตั้งโครงสร้างพื้นฐาน OTA สำหรับบริษัทมิเตอร์อัจฉริยะที่มีมิเตอร์น้ำเชื่อมต่อ LoRaWAN จำนวน 10,000 เครื่องทั่วพื้นที่เมืองใหญ่ มิเตอร์แต่ละเครื่องใช้ไมโครคอนโทรลเลอร์ STM32L4 ที่มีหน่วยความจำแฟลช 1 MB แบ่งเป็น MCUboot ขนาด 32 KB, Slot 0 (ใช้งานอยู่) ขนาด 448 KB, Slot 1 (เตรียมการ) ขนาด 448 KB และพื้นที่ชั่วคราวขนาด 16 KB เนื่องจากข้อจำกัดด้านแบนด์วิดท์ของ LoRaWAN (ประมาณ 50 ไบต์ต่อลิงก์อัปที่ SF10) การถ่ายโอนภาพเฟิร์มแวร์ขนาด 200 KB เต็มรูปแบบจะใช้แพ็กเก็ตมากกว่า 4,000 แพ็กเก็ตและใช้เวลานานกว่า 40 ชั่วโมง เราจึงนำการอัปเดตแบบเดลต้าโดยใช้ bsdiff มาใช้ ซึ่งบีบอัดการเปลี่ยนแปลงเฟิร์มแวร์ทั่วไปให้เหลือเพียง 15-30 KB ลดเวลาการถ่ายโอนเหลือ 3-6 ชั่วโมงต่ออุปกรณ์ กระบวนการอัปเดตใช้โหมดมัลติแคสต์คลาส C: มิเตอร์จะเปลี่ยนจากคลาส A (พลังงานต่ำสุด) ไปเป็นคลาส C (รับฟังอย่างต่อเนื่อง) ชั่วคราวในช่วงเวลาการบำรุงรักษาตามกำหนดการ รับข้อมูลส่วนต่างผ่านลิงก์ดาวน์ลิงก์มัลติแคสต์ และเปลี่ยนกลับไปเป็นคลาส A หลังจากได้รับการยืนยัน เราดำเนินการติดตั้งใน 5 ขั้นตอน: กลุ่มทดสอบ 1%, 10%, 25%, 50% และ 100% โดยตรวจสอบอัตราความสำเร็จ การตรวจจับลูปการบูต และความผิดปกติของการใช้พลังงานในแต่ละขั้นตอน

โหมดความล้มเหลวของ OTA ที่อันตรายที่สุดมีอะไรบ้าง?

โหมดความล้มเหลว OTA ที่ร้ายแรงที่สุดคืออุปกรณ์เสียหายจนไม่สามารถกู้คืนได้หากไม่มีการเข้าถึงทางกายภาพ ปัญหานี้เกิดขึ้นเมื่อบูตโหลดเดอร์เสียหายหรือเมื่อช่องเสียบเฟิร์มแวร์ทั้งสองช่องมีอิมเมจที่ไม่ถูกต้อง วิธีแก้ไขคือทำให้บูตโหลดเดอร์ไม่สามารถเปลี่ยนแปลงได้ (วางไว้ในพื้นที่แฟลชที่ป้องกันการเขียน) ใช้พาร์ติชั่นกู้คืนอิมเมจต้นแบบ (เฟิร์มแวร์ขนาดเล็กในพื้นที่แฟลชที่ป้องกันแยกต่างหาก ซึ่งบูตโหลดเดอร์ ROM จะใช้เป็นตัวสำรอง) และตรวจสอบระดับแบตเตอรี่ก่อนเริ่มกระบวนการอัปเดต สำหรับอุปกรณ์ STM32 ให้กำหนดค่า Option Bytes เพื่อป้องกันการเขียนพื้นที่แฟลชบูตโหลดเดอร์โดยใช้บิต WRP (Write Protection) ความล้มเหลวที่อันตรายอีกอย่างคือการอัปเดตสำเร็จแต่มีข้อบกพร่องเล็กน้อยที่ตรวจพบได้หลังจากนั้นหลายสัปดาห์ หลังจากที่อัปเดตอุปกรณ์ทั้งหมดแล้ว วิธีแก้ไขคือใช้การตรวจสอบสถานะอัตโนมัติ: เฟิร์มแวร์ที่อัปเดตแล้วต้องยืนยันตัวเองภายในระยะเวลาที่กำหนดได้ (30-300 วินาที) โดยการเรียกใช้ boot_write_img_confirmed() มิฉะนั้นบูตโหลดเดอร์จะกลับไปสู่สถานะเดิมโดยอัตโนมัติ ควรเพิ่มการทดสอบตัวเองเชิงฟังก์ชัน (การตรวจสอบความถูกต้องของการอ่านค่าเซ็นเซอร์ การวนรอบการสื่อสาร การตรวจสอบการทำงานของระบบเฝ้าระวัง) เข้าไปในตรรกะการยืนยัน ไม่ใช่แค่การใช้ตัวจับเวลาแบบง่ายๆ เท่านั้น

คุณจะเลือกอย่างไรระหว่างการอัปเดตแบบเต็มภาพและการอัปเดต OTA ของ Delta?

การอัปเดตอิมเมจแบบเต็มจะส่งไบนารีเฟิร์มแวร์ทั้งหมดที่ได้รับการตรวจสอบโดยแฮช SHA-256 และลายเซ็น ECDSA การอัปเดตแบบนี้ทำได้ง่ายกว่า ไม่ต้องใช้ตรรกะการสร้างใหม่ฝั่งไคลเอ็นต์ และสามารถอัปเดตจากเวอร์ชันใดก็ได้ไปยังเวอร์ชันใดก็ได้ อย่างไรก็ตาม การอัปเดตแบบนี้ใช้แบนด์วิดท์และเวลาในการถ่ายโอนสูงสุด ส่วนการอัปเดตแบบเดลต้าจะส่งเฉพาะส่วนต่างของไบนารีระหว่างเวอร์ชันปัจจุบันและเวอร์ชันเป้าหมาย ซึ่งสร้างขึ้นโดยใช้อัลกอริทึม เช่น bsdiff, xdelta3 หรือ mender-binary-delta ของ Mender แพทช์เดลต้าโดยทั่วไปจะมีขนาด 10-30% ของขนาดอิมเมจแบบเต็มสำหรับการอัปเดตเล็กน้อย และ 40-60% สำหรับการปรับโครงสร้างครั้งใหญ่ ข้อเสียของการอัปเดตแบบเดลต้ามีมากมาย: การอัปเดตแบบเดลต้าต้องการให้เครื่องมี RAM หรือแฟลชชั่วคราวเพียงพอในการใช้แพทช์ (bsdiff ต้องการหน่วยความจำทำงานประมาณ 2 เท่าของขนาดแพทช์) ต้องสร้างแพทช์สำหรับแต่ละชุดเวอร์ชันต้นทางถึงเป้าหมาย (N เวอร์ชันสร้าง N-1 แพทช์สำหรับการอัปเดตตามลำดับ หรือ N*(N-1)/2 สำหรับการข้ามเวอร์ชันแบบสุ่ม) และอิมเมจปัจจุบันที่เสียหายจะป้องกันการใช้แพทช์ สำหรับอุปกรณ์ที่เชื่อมต่อผ่าน LPWAN ซึ่งมีข้อจำกัดด้านแบนด์วิดท์สูง การอัปเดตแบบเดลต้าจึงเป็นสิ่งจำเป็น ส่วนอุปกรณ์ที่เชื่อมต่อผ่าน Wi-Fi ซึ่งมีแบนด์วิดท์เหลือเฟือ การอัปเดตภาพเต็มรูปแบบนั้นง่ายกว่าและมีประสิทธิภาพมากกว่า