12.1. ทำไมต้องมีไลบรารีโปรโตคอล¶
สายเคเบิลคู่หนึ่งและอัตราบอดเพียงพอสำหรับการส่งไบต์จากกล้องไปยังพีซีโฮสต์ USB-CDC และ UART ต่างให้โปรแกรมกล้องมีสตรีมที่ write ใส่ไบต์เข้าจากด้านหนึ่งและ read ดึงออกจากอีกด้านหนึ่ง แล้ว ไลบรารีโปรโตคอล เพิ่มอะไรขึ้นมาบนพื้นฐานนั้น?
สามสิ่งที่คุณต้องเขียนเองทุกครั้ง หากคุณพยายามสร้างช่องทางการสื่อสารระหว่างกล้องกับโฮสต์โดยตรงบนไบต์ดิบ:
การแบ่งเฟรม สตรีมของไบต์ไม่มีโครงสร้างโดยธรรมชาติ กล้องเขียน temp=42 และโฮสต์อ่าน temp= แล้วมีอินเทอร์รัปต์เข้ามาทีหลัง จากนั้น 42 ก็มีข้อความถัดไปที่ขึ้นต้นด้วย humid=... วิ่งซ้อนเข้ามาแล้ว ไบต์ไม่มีขอบเขต ทุกการเชื่อมต่อโฮสต์ที่ไม่ใช่งานเล็กน้อยต่างต้องประดิษฐ์เครื่องหมายบางอย่างขึ้นมาเอง ไม่ว่าจะเป็น \n ระหว่างข้อความ เฮดเดอร์นำหน้าด้วยความยาว หรือ escape sequence สำหรับข้อมูลไบนารี เพื่อให้ผู้รับรู้ว่าข้อความหนึ่งสิ้นสุดและข้อความถัดไปเริ่มต้นที่ใด ไลบรารีโปรโตคอลมอบรูปแบบแพ็กเก็ตสม่ำเสมอพร้อม sync word และฟิลด์ความยาว โดยผู้รับไม่ต้องเดาเลย
ความน่าเชื่อถือ USB-CDC ไม่ทำให้ไบต์หายโดยไม่แจ้งในการทำงานปกติ แต่ UART ทำได้ (เมื่อโฮสต์หยุดให้บริการพอร์ตเร็วพอ) และสายสัญญาณที่ถอดแล้วเสียบใหม่อาจทำให้ฝั่งใดฝั่งหนึ่งมีแพ็กเก็ตที่ไม่สมบูรณ์ สิ่งที่ถูกต้องคือตรวจจับความเสียหาย ขอให้อีกฝ่ายส่งซ้ำ และส่งเฉพาะข้อความที่มาถึงสมบูรณ์ไปยังโค้ดแอปพลิเคชัน ไลบรารีโปรโตคอลทำเช่นนั้นสำหรับทุกแพ็กเก็ตด้วย CRC และการยืนยันรับรองต่อแพ็กเก็ต โดยเปิดใช้งานตามค่าเริ่มต้น แอปพลิเคชันไม่เห็นการส่งซ้ำ
การมัลติเพล็กซ์ มีพอร์ต USB-CDC เพียงพอร์ตเดียวระหว่างกล้องและโฮสต์ หากกล้องกำลังสตรีมภาพ และ โฮสต์กำลังส่งการกำหนดค่า และ IDE กำลังอ่าน stdout สำหรับผลลัพธ์ print การแลกเปลี่ยนทั้งสามต้องใช้สตรีมไบต์เดียวร่วมกัน ไลบรารีโปรโตคอลให้หมายเลข ช่องสัญญาณ แก่สตรีมอิสระแต่ละอัน ให้กล้องลงทะเบียนคลาส Python สำหรับแต่ละช่อง และป้องกันไม่ให้การอ่านของโฮสต์บนแต่ละช่องรบกวนช่องอื่น จากมุมมองของโค้ดแอปพลิเคชัน แต่ละช่องมีลักษณะเหมือนลิงก์ส่วนตัวของตัวเอง
12.1.1. ทำไมไม่เขียนเอง¶
คุณทำได้ ใช้เวลาสองสามสัปดาห์เพื่อให้ถูกต้องทั้งสามข้อบนสายสัญญาณอนุกรม และอีกสองสามสัปดาห์เพื่อให้การแบ่งเฟรมจัดการการกู้คืนจากการเสียบใหม่แบบ hot-plug ได้อย่างสมบูรณ์ ให้การส่งซ้ำทำงานโดยไม่เปลืองพลังงานกับรอบการสื่อสาร และให้มัลติเพล็กเซอร์รอดจากการอ่านบางส่วนโดยไม่ทำให้ไบต์ของช่องหนึ่งหลุดเข้าไปอีกช่องหนึ่ง
ไลบรารีโปรโตคอลได้ทำงานนั้นเสร็จแล้ว ได้รับการตรวจสอบบนกล้องที่รองรับทุกรุ่น และมีไลบรารีที่ตรงกันในฝั่งโฮสต์ที่ใช้รูปแบบสายสัญญาณเดียวกัน การใช้ไลบรารีนี้หมายความว่าโค้ดฝั่งกล้องเป็นคลาสเล็กๆ หนึ่งคลาสต่อช่อง และโค้ดฝั่งโฮสต์เป็นออบเจ็กต์ Camera ที่มีเมธอด channel_read และ channel_write พื้นที่ทางความคิดที่ประหยัดได้จะไปใช้กับสิ่งที่แอปพลิเคชันทำจริงๆ
บทนี้สอนโปรโตคอลตั้งแต่พื้นฐาน: รูปแบบสายสัญญาณ กฎการแบ่งเฟรม กลไกความน่าเชื่อถือ โมเดลช่องสัญญาณ และท้ายที่สุดคลาส Python ทั้งสองฝั่ง เมื่ออ่านจบผู้อ่านจะสร้าง GUI โฮสต์ที่คุยกับกล้องได้ สคริปต์ที่สตรีมข้อมูล sensor จากกล้องไปยังแล็ปท็อป และเครื่องมือปรับเทียบแบบโต้ตอบเช่นที่มาพร้อมใน openmv-projects/tools/