SDV Media: จัดการจอแสดงผล

SDV Media จะแสดงจอแสดงผลที่มีให้ใช้งานแก่แอป OEM ด้วย Linux DRM API

การโต้ตอบระหว่างคอมโพเนนต์ DRM

รูปที่ 1 การโต้ตอบระหว่างคอมโพเนนต์ DRM

  • เฟรมบัฟเฟอร์เป็นแหล่งที่มาของข้อมูลพิกเซล ซึ่งได้รับการสนับสนุนจากบัฟเฟอร์หน่วยความจำที่จัดสรรภายนอก

  • ระนาบคือแหล่งที่มาของรูปภาพที่ CRTC ใช้ โดยจะเชื่อมโยงกับ เฟรมบัฟเฟอร์ และแสดงมุมมองที่ครอบตัดของเฟรมบัฟเฟอร์ได้

  • CRTC แสดงถึงไปป์ไลน์การแสดงผลโดยรวม โดยสามารถรวมระนาบหลายระนาบเพื่อสร้างเอาต์พุตวิดีโอขั้นสุดท้าย และส่งเอาต์พุตไปยังตัวเข้ารหัสหลายตัวได้

  • โปรแกรมเปลี่ยนไฟล์จะแปลงเอาต์พุตวิดีโอจาก CRTC เป็นรูปแบบที่เหมาะสำหรับ ขั้วต่อที่เฉพาะเจาะจง

  • ขั้วต่อแสดงถึงขั้วต่อจอแสดงผลที่พร้อมใช้งาน เช่น พอร์ต HDMI

ดูคำอธิบายแบบเจาะลึกเพิ่มเติมได้ที่

แพลตฟอร์ม API

SDV Media มีอินเทอร์เฟซ DRM ของ Linux แม้ว่าจะใช้โดยตรงได้ โดยใช้ ioctl syscall แต่เราขอแนะนำให้ใช้ ไลบรารีผู้ช่วยในพื้นที่ผู้ใช้สำหรับการพัฒนาแอปพลิเคชัน เช่น

  • drm-rs สำหรับ Rust (แนะนำ)
  • libdrm สำหรับ C/C++ drm-kms หน้า man จะแสดงภาพรวมโดยละเอียดของ API และการใช้งาน

ตั้งค่าการแสดงผลไปยังจอแสดงผลเดียว

  1. เปิดอุปกรณ์ DRM (/dev/dri/card*) และใช้ Linux DRM API เช่น ผ่าน libdrm ในตัวบอกไฟล์เพื่อเลือกจอแสดงผลและโหมด

    โดยปกติแล้ว ระบบโฮสต์จะแสดงอุปกรณ์ GPU เสมือนเพียงเครื่องเดียว ซึ่งจะปรากฏเป็น /dev/dri/card0

  2. จัดสรรบัฟเฟอร์ด้านหน้าและด้านหลังด้วย Linux DRM API

    ขอแนะนำให้ใช้ minigbm gbm_bo_create() และรับตัวบอกไฟล์ DMA-BUF ด้วย gbm_bo_get_fd()

  3. สร้าง Framebuffer ของ GL ที่มีบัฟเฟอร์ที่จัดสรรเป็นข้อมูลสำรอง

    1. สร้าง EGLImage นอกบัฟเฟอร์ DRM ด้วย eglCreateImageKHR โดยมี EGL_LINUX_DMA_BUF_EXT (จากส่วนขยาย EGL_EXT_image_dma_buf_import )

    2. สร้างเท็กซ์เจอร์ GL และใช้ glEGLImageTargetTexture2DOES (จากส่วนขยาย GL_OES_EGL_image) เพื่อตั้งค่าพื้นที่เก็บข้อมูลของเท็กซ์เจอร์เป็น EGLImage จากขั้นตอนก่อนหน้า

    3. สร้าง GL Framebuffer และใช้ glFramebufferTexture2D เพื่อตั้งค่า เท็กซ์เจอร์สำรองเป็นเท็กซ์เจอร์ที่สร้างขึ้นในขั้นตอนก่อนหน้า

  4. วิธีเรนเดอร์เฟรม

    1. เชื่อมโยง Framebuffer ของ GL ที่สร้างขึ้น

    2. วาดเฟรมด้วย GLES API ปกติ

    3. แสดงเฟรมบนหน้าจอ: ใช้ Linux DRM API (drmModeAtomicCommit()) เพื่อส่ง DRM_MODE_PAGE_FLIP_EVENT พร้อมตัวอธิบายไฟล์ DMA-BUF ที่ใช้โดยเฟรมบัฟเฟอร์ GL ที่เชื่อมโยง

สร้างเอาต์พุตวิดีโอจากหลายเลเยอร์

สำหรับการคอมโพสิตแบบหลายเลเยอร์ (หลายระนาบ) ที่เร่งด้วยฮาร์ดแวร์ เราจะใช้ ระบบโฮสต์ที่แสดงแต่ละเลเยอร์เป็นขั้วต่อ DRM แยกกัน (จอแสดงผลเสมือน) และแมปเลเยอร์เหล่านั้นไปยังตำแหน่ง / ไปป์ไลน์ฮาร์ดแวร์ที่ถูกต้อง

ดูรายละเอียดได้ที่ตั้งค่าการแสดงผลในหลายจอแสดงผล

ตั้งค่าการแสดงผลในหลายจอแสดงผล

  1. เปิดอุปกรณ์ /dev/dri/card* DRM เหมือนในโฟลว์แบบจอแสดงผลเดียว

  2. แสดงรายการขั้วต่อจอแสดงผลที่พร้อมใช้งาน

    จอแสดงผลแต่ละจอจะแสดงเป็นตัวเชื่อมต่อ DRM แยกกันของอุปกรณ์ DRM

  3. สำหรับขั้วต่อจอแสดงผลแต่ละตัว

    1. เลือก CRTC ที่เข้ากันได้กับตัวเชื่อมต่อ ขั้วต่อแต่ละตัวมีรายการ ของตัวเข้ารหัสที่ใช้ได้ และตัวเข้ารหัสแต่ละตัวจะระบุว่าใช้กับ CRTC ใดได้ โดยจะมี CRTC ที่เข้ากันได้อย่างน้อย 1 รายการเสมอ

      1. เลือกเครื่องบินที่เข้ากันได้กับ CRTC

      2. สร้างเฟรมบัฟเฟอร์ DRM ที่มีบัฟเฟอร์ GPU เป็นข้อมูลสำรอง กระบวนการนี้ จะเหมือนกับกระบวนการสำหรับรุ่นที่มีจอแสดงผลเดียว

      3. เชื่อมต่อระนาบ, CRTC และตัวเชื่อมต่อ แล้วตั้งค่าวิดีโอโหมดใน CRTC

        คุณสามารถตั้งค่าโหมดของจอแสดงผลหลายจอพร้อมกันได้ โดยใช้ Atomic API เพื่อตั้งค่าพร็อพเพอร์ตี้ DRM ต่อไปนี้สำหรับ แต่ละตัวเชื่อมต่อ, CRTC และชุดระนาบ

    รายการพร็อพเพอร์ตี้ที่จำเป็นทั้งหมดมีดังนี้

    เป้าหมาย พร็อพเพอร์ตี้ประเภทคำอธิบาย
    มนุษยสัมพันธ์ดีCRTC_IDCRTC IDรหัสของ CRTC ที่จะกำหนดให้กับตัวเชื่อมต่อ
    CRTCMODE_IDรหัส Blob รหัสของ Blob พร็อพเพอร์ตี้ที่สร้างขึ้นโดยใช้ drmModeCreatePropertyBlob ซึ่งมีโครงสร้าง drmModeModeInfo ของโหมดวิดีโอที่เลือก
    CRTCACTIVEบูลีนtrue เพื่อทําเครื่องหมายว่า CRTC ใช้งานอยู่
    เครื่องบินFB_IDรหัส Framebufferรหัสของเฟรมบัฟเฟอร์ DRM ที่จะแสดงบนหน้าจอ
    เครื่องบินSRC_Xพิกเซลพิกัด X ของสี่เหลี่ยมผืนผ้าของรูปภาพต้นฉบับของ Framebuffer
    เครื่องบินSRC_Yพิกเซลพิกัด Y ของสี่เหลี่ยมผืนผ้าของรูปภาพต้นฉบับของ Framebuffer
    เครื่องบินSRC_Wจุดคงที่ 16.16ความกว้างของสี่เหลี่ยมผืนผ้าของรูปภาพต้นฉบับของเฟรมบัฟเฟอร์ (พิกเซลที่เลื่อนไปทางซ้าย 16 บิต)
    เครื่องบินSRC_Hจุดคงที่ 16.16ความสูงของสี่เหลี่ยมผืนผ้าของรูปภาพต้นฉบับของเฟรมบัฟเฟอร์ (พิกเซลที่เลื่อนไปทางซ้าย 16 บิต)
    เครื่องบินCRTC_Xพิกเซลพิกัด X ของสี่เหลี่ยมผืนผ้าของรูปภาพปลายทาง CRTC
    เครื่องบินCRTC_Yพิกเซลพิกัด Y ของสี่เหลี่ยมผืนผ้าของรูปภาพปลายทาง CRTC
    เครื่องบินCRTC_Wพิกเซลความกว้างของสี่เหลี่ยมผืนผ้าของรูปภาพปลายทาง CRTC
    เครื่องบินCRTC_Hพิกเซลความสูงของสี่เหลี่ยมผืนผ้าของรูปภาพปลายทางของ CRTC
  4. เข้าสู่ลูปการแสดงผล

    1. รอเหตุการณ์การสลับหน้าใน CRTC ก่อนที่จะแสดงผลเฟรมถัดไป

    2. แสดงผลเฟรมและแสดงบนหน้าจอโดยกำหนดเวลาการสลับหน้า สำหรับ CRTC + เฟรมบัฟเฟอร์ที่ระบุ