ข้อได้เปรียบของกลไกการเข้าถึงสถานะโดยตรงของ OpenGL คืออะไร


11

ฉันได้อ่านเกี่ยวกับ OpenGL 4.5 Direct State Access (DSA) ที่opengl.orgและไม่แน่ใจว่าฉันทำให้ถูกต้องหรือไม่

ดูเหมือนจะบอกเป็นนัยว่าวิธีเก่ามีประสิทธิภาพน้อยกว่า:

glBind(something)
glSetA(..)
glSetB(..)
glSetC(..)

กว่าวิธีใหม่:

glSetA(something, ..)
glSetB(something, ..)
glSetC(something, ..)

จากลักษณะของมันตอนนี้แต่ละคนglSetมีการรวมglBind(something)ภายในของมันและถ้า OpenGL somethingที่ยังคงความเป็นรัฐที่เครื่องไม่สามารถใช้ประโยชน์จากการเปลี่ยนแปลงที่นำไปใช้กับสตรีมเดียว

โปรดอธิบายเหตุผลเบื้องหลังและข้อดีของ DSA ใหม่

คำตอบ:


21

จากรูปลักษณ์ของมันตอนนี้แต่ละ glSet ต้องรวม glBind (บางอย่าง) ไว้ข้างใน

ไม่แน่นอน มันเป็นวิธีอื่น ๆ ตามที่อธิบายไว้หลายย่อหน้าด้านล่าง

แม้ว่าจะเป็นจริงโปรดจำไว้ว่าคำสั่ง GL จากแอปไคลเอ็นต์ไปยังเซิร์ฟเวอร์ GL (ไดรเวอร์ aka) มีค่าใช้จ่ายในการจัดส่งจำนวนมากเมื่อเทียบกับการเรียกใช้ฟังก์ชันปกติ แม้ว่าเราจะสมมติว่าฟังก์ชั่น DSA เป็นเพียงแค่ล้อมรอบฟังก์ชั่นที่มีอยู่พวกมันกำลังห่อหุ้มที่อยู่ภายในเซิร์ฟเวอร์ GL และด้วยเหตุนี้จึงสามารถมีค่าใช้จ่ายน้อยลง (เล็กน้อย)

ถ้า OpenGL ยังคงเป็นเครื่องสถานะไม่สามารถใช้ประโยชน์จากการเปลี่ยนแปลงแบบสตรีมที่ใช้กับสิ่งใดสิ่งหนึ่งได้

GPU ไม่ใช่เครื่องจักรของรัฐ อินเทอร์เฟซของเครื่องจักรสถานะ GL เป็นการจำลองที่ล้อมรอบไดรเวอร์ DSA เหมือนไม่ใช่วิธีอื่น

การลบเลเยอร์หนึ่ง - เลเยอร์ที่ต้องการการโทรจำนวนมากเกินไปไปยังเซิร์ฟเวอร์ GL - เป็นชัยชนะที่ชัดเจนแม้ว่าจะเป็นเลเยอร์เล็ก ๆ

วิธีการใช้เครื่องรัฐก็ไม่สมเหตุสมผลเมื่อต้องจัดการกับหลายเธรด GL ยังคงแย่มากในกรณีที่ใช้งานนี้ แต่ไดรเวอร์มักใช้เธรดเบื้องหลังและเครื่องสถานะต้องใช้การซิงโครไนซ์เธรดจำนวนมากหรืออัลกอริธึมขนาน / การสร้างเพื่อให้สิ่งต่าง ๆ ทำงานได้อย่างน่าเชื่อถือ

ส่วนขยาย DSA ยังคงดำเนินการต่อในแง่ของการเปลี่ยนแปลงสถานะเนื่องจากเป็นส่วนต่อขยายไปยังเอกสารตามสถานะที่มีอยู่และไม่ใช่ API ใหม่ทั้งหมดดังนั้นจึงต้องพร้อมที่จะเชื่อมต่อกับข้อกำหนด GL ที่มีอยู่ ภาษาและคำศัพท์ของเอกสาร แม้ว่าภาษาที่มีอยู่นั้นค่อนข้างเหมาะสมกับงานของมันในฐานะ API ฮาร์ดแวร์กราฟิกที่ทันสมัย

โปรดอธิบายเหตุผลเบื้องหลังและข้อดีของ DSA ใหม่

เหตุผลที่ใหญ่ที่สุดคือวิธีเก่าคือความเจ็บปวด มันทำให้ยากมากในการเขียนไลบรารีเข้าด้วยกันซึ่งแต่ละครั้งอาจแก้ไขหรือพึ่งพาสถานะ GL มันทำให้มันยากที่จะห่อ GL API อย่างมีประสิทธิภาพในรูปแบบเชิงวัตถุหรือการทำงานเนื่องจากรากการจัดการสถานะขั้นตอนลึกซึ่งทำให้การห่อ API ในภาษาที่ไม่ใช่ C ต่างๆยากและทำให้มันยากที่จะให้ห่ออุปกรณ์กราฟิกที่มีประสิทธิภาพ OpenGL ที่เป็นนามธรรมจาก Direct3D

ที่สองคือค่าใช้จ่าย API ของเครื่องสถานะขั้นตอนตามที่อธิบายไว้ก่อนหน้านี้

ประการที่สามฟังก์ชั่น DSA เปลี่ยนซีแมนติกส์ตามความเหมาะสมจาก API เก่าที่อนุญาตให้ปรับปรุงประสิทธิภาพ สิ่งที่ไม่สามารถเปลี่ยนแปลงได้ก่อนหน้านี้ถูกทำให้ไม่เปลี่ยนรูปแบบเช่นซึ่งจะลบรหัสการเก็บหนังสือจำนวนมากออกจากเซิร์ฟเวอร์ GL แอปพลิเคชันสามารถโทรไปยังฮาร์ดแวร์หรือตรวจสอบได้เร็วขึ้น (หรือในแถบอเมริกาแบบขนาน) เมื่อเซิร์ฟเวอร์ GL ไม่ต้องจัดการกับวัตถุที่ไม่แน่นอน

-

เหตุผลเพิ่มเติมและคำอธิบายจะได้รับในข้อกำหนดส่วนขยาย EXT_direct_state_accessสเปคขยาย

-

การเปลี่ยนแปลงฮาร์ดแวร์ที่เกี่ยวข้องกับการออกแบบ API นั้นค่อนข้างมาก

โปรดจำไว้ว่า OpenGL มีอายุย้อนไปถึงปี 1991 ฮาร์ดแวร์เป้าหมายไม่ใช่กราฟิกการ์ดระดับผู้บริโภค (ที่ไม่มีอยู่) แต่เวิร์คสเตชั่ CAD ขนาดใหญ่และสิ่งที่คล้ายกัน ฮาร์ดแวร์ในยุคนั้นมีซองจดหมายประสิทธิภาพที่แตกต่างจากวันนี้มาก มัลติเธรดนั้นหายากขึ้นรถบัสหน่วยความจำและซีพียูมีช่องว่างความเร็วน้อยกว่าและ GPU ทำอะไรได้มากกว่าการเรนเดอร์สามเหลี่ยมแบบฟังก์ชันคงที่เล็กน้อย

มีการเพิ่มคุณสมบัติฟังก์ชั่นคงที่มากขึ้น มีการเพิ่มโมเดลแสงโหมดพื้นผิวและอื่น ๆ ทั้งหมดซึ่งแต่ละชิ้นต้องการสถานะของตนเอง วิธีการของรัฐที่ใช้งานง่ายนั้นทำงานเมื่อคุณมีสถานะไม่มากนัก เมื่อเพิ่มสถานะมากขึ้นเรื่อย ๆ API ก็เริ่มระเบิดที่ตะเข็บ API นั้นดูน่าอึดอัดมากขึ้น แต่ก็ไม่ได้ห่างจากโหมดฮาร์ดแวร์มากนักเนื่องจากมันใช้สวิตช์สถานะเป็นจำนวนมาก

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

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

ฮาร์ดแวร์ที่ทันสมัยทำงานได้ดียิ่งขึ้นจากรุ่น OpenGL คลาสสิก DSA เป็นการเปลี่ยนแปลงเพียงเล็กน้อยที่ต้องการมากกว่า 10 ปีก่อน (สัญญาเดิมเป็นส่วนหนึ่งของ OpenGL 3.0) คล้ายกับสิ่งที่ D3D10 ทำ หลายของฮาร์ดแวร์ที่มีการเปลี่ยนแปลงข้างต้นจำเป็นต้องไปไกลกว่าเพียง DSA เพื่อให้ OpenGL ที่เกี่ยวข้องซึ่งเป็นเหตุผลที่ยังคงส่วนขยายใหญ่มากขึ้นอย่างเห็นได้ชัดว่าการเปลี่ยนรูปแบบ OpenGL ที่มีอยู่ จากนั้นก็มี GLnext API ใหม่ทั้งหมดรวมทั้ง D3D12, Mantle, Metal และอื่น ๆ ไม่ใช่หนึ่งเดียวที่จะทำให้เครื่องสถานะที่ล้าสมัย


ขอบคุณสำหรับคำตอบ. ดังนั้นดูเหมือนว่าก่อนที่จะถึงจุดที่สถานะเครื่องจักร (ไม่ใช่ DSA) เป็นผู้ชนะ แต่ในบางจุดมีการเปลี่ยนแปลงและตอนนี้ DSA เป็นข้อได้เปรียบ คุณช่วยส่องแสงสิ่งที่เปลี่ยนไปได้ไหม
Kromster

@ KromStern: ทำดีที่สุดแล้ว หากคุณต้องการรายละเอียดเพิ่มเติมใครบางคนมีความรู้มากกว่าที่ฉันจะต้องให้มัน
Sean Middleditch

@ KromStern ฉันได้เห็น (จากการวิจัยที่ จำกัด ของฉันในประวัติศาสตร์) openGL เลื่อนไปทางด้านข้างของ CPU น้อยลงและน้อยลง รายการที่แสดง (สำหรับสิ่งที่คุ้มค่า), glDrawArrays (ดึงในสายเดียว), VBOs (อัปโหลดไปยัง GPU หนึ่งครั้ง), VAO (ผูกบัฟเฟอร์กับแอตทริบิวต์หนึ่งครั้ง), วัตถุบัฟเฟอร์ชุด (ชุดเครื่องแบบในครั้งเดียว) มีมากกว่าที่ฉันหายไปฉันแน่ใจ
ratchet freak

@ ratchetfreak: ขำ ๆ พอเราย้ายไปทางอื่นแล้ว APIs / ส่วนขยายที่ทันสมัยมุ่งเน้นที่การเพิ่มการเรียกการดึงของเราต่อเฟรมส่วนใหญ่โดยการลบสถานะทั้งหมดที่จะต้องมีการตั้งค่า / ส่งต่อการเรียกการดึงและการเรียกการดึงนั้นน้อยกว่า ชุดของสถานะคงที่และทรัพยากร bindless Oooh ไร้สาระฉันลืมที่จะพูดถึงส่วนนั้นในคำตอบของฉัน
Sean Middleditch

@SeanMiddleditch ฉันควรจะตั้งค่าการโทรต่อเฟรม
วงล้อประหลาด

1

ภาพรวมแสดงเหตุผลโดย:

จุดประสงค์ของส่วนขยายนี้คือการทำให้ไลบรารีมีประสิทธิภาพมากขึ้นเพื่อหลีกเลี่ยงการรบกวนตัวเลือกและสถานะการล็อค ส่วนขยายยังช่วยให้การใช้คำสั่งมีประสิทธิภาพมากขึ้นโดยไม่จำเป็นต้องใช้คำสั่งการปรับปรุงตัวเลือก

ฉันคิดว่า "มีประสิทธิภาพมากขึ้น" ที่นี่หมายถึงค่าใช้จ่ายในการทำบัญชีน้อยลงสำหรับผู้เขียนห้องสมุดและทำให้มีประสิทธิภาพสูงขึ้น ด้วย API ปัจจุบันเพื่อให้เป็น "ตัวตนที่ดี" คุณจะต้องค้นหาสถานะเก็บไว้เปลี่ยนสถานะเพื่อทำสิ่งที่คุณต้องการจากนั้นเรียกคืนสถานะเดิม

ชอบ

oldState = glGet()
glBind()
glDoThings...
glSet(oldState)  // restore, in case anyone needs it just as they left it

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


"ต้องค้นหา / ซ่อน / เปลี่ยนแปลง / กู้คืน" - ดีอย่างไรกับ DSA
Kromster

.. รหัสปลอมที่จะแสดงเพิ่ม ด้วย DSA ไม่จำเป็นต้องทำสิ่งใด สันนิษฐานว่าฮาร์ดแวร์ในปัจจุบันไม่จำเป็นต้องมีสถานะ "ผูกพัน" จริงๆสามารถเข้าถึงได้ทั้งหมดตามต้องการ
david van brink

ห่วงโซ่get/bind/do/setไม่ค่อยได้ใช้เพราะ 'รับ' ช้ามาก โดยปกติแล้วแอพจะต้องรักษาแบบจำลองของตัวแปรอยู่bind/doเสมอ ฉันเห็นจุดแม้ว่า
Kromster

2
@krom จากสถานะไดร์เวอร์สามารถทำงานได้อย่างรวดเร็วบางสถานะ gettable ไม่มีธุรกิจอยู่บน GPU ดังนั้นจึงสามารถรับจาก RAM ที่รวดเร็ว
วงล้อประหลาด
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.