วิศวกร AWS รายงานว่า PostgreSQL บน Linux 7.0 มีประสิทธิภาพลดลงครึ่งหนึ่ง — และอาจแก้ไขได้ไม่ง่าย
(phoronix.com/news)- วิศวกรของ Amazon/AWS พบว่าในเคอร์เนลพัฒนา Linux 7.0 เซิร์ฟเวอร์ฐานข้อมูล PostgreSQL เกิด การถดถอยด้านประสิทธิภาพอย่างรุนแรง โดย throughput ลดลงเหลือราวครึ่งหนึ่งเมื่อเทียบกับเคอร์เนลก่อนหน้า
- ผลการวัดบนเซิร์ฟเวอร์ Graviton4 พบว่า Linux 7.0 ให้ throughput เพียงประมาณ 0.51 เท่า ของเคอร์เนลก่อนหน้า และสาเหตุคือมีการใช้เวลาใน user-space spinlock มากขึ้นอย่างมาก
- สาเหตุของการถดถอยมาจากการเปลี่ยนแปลง ข้อจำกัดของโหมด kernel preemption ใน Linux 7.0 โดยมีการส่งแพตช์เพื่อคืนค่า PREEMPT_NONE ให้เป็นค่าเริ่มต้น แต่ยังไม่ชัดเจนว่าจะถูกรับเข้าหรือไม่
- Peter Zijlstra ผู้เขียนต้นฉบับระบุว่าแทนที่จะแก้ที่เคอร์เนล ควร ปรับ PostgreSQL ให้ใช้ส่วนขยาย RSEQ (Restartable Sequences) time slice
- Linux 7.0 รุ่นเสถียรมีกำหนดออกในอีกประมาณ 2 สัปดาห์ และจะถูกใช้เป็นเคอร์เนลพื้นฐานของ Ubuntu 26.04 LTS ด้วย ทำให้มีความกังวลว่า ประสิทธิภาพจะลดลงเป็นวงกว้างจนกว่า PostgreSQL จะปรับตัวรองรับ
การค้นพบปัญหาและขนาดของผลกระทบ
- Salvatore Dipietro วิศวกรของ Amazon/AWS รายงานการถดถอยของ throughput และ latency ใน PostgreSQL
- จากการวัดบน เซิร์ฟเวอร์ Graviton4 พบว่า Linux 7.0 ให้ throughput เพียง 0.51 เท่า เมื่อเทียบกับเคอร์เนลเดิม
- ตรวจสอบพบว่าสาเหตุคือมีการใช้เวลาใน user-space spinlock มากขึ้นอย่างมาก
สาเหตุของการถดถอย: การจำกัดโหมด preemption
- ผลจากการทำ bisect ระบุว่าต้นเหตุคือการเปลี่ยนแปลงที่ จำกัดโหมด kernel preemption ใน Linux 7.0
- การเปลี่ยนแปลงดังกล่าวทำขึ้นเพื่อคงไว้เฉพาะโหมด Full และ Lazy preemption สำหรับสถาปัตยกรรม CPU รุ่นใหม่ และถูกรวมเป็นส่วนหนึ่งของการอัปเดต scheduler ใน Linux 7.0
แพตช์ที่ถูกส่งและปฏิกิริยาของผู้ดูแลเคอร์เนล
- มีการส่งแพตช์ไปยัง Linux kernel mailing list เพื่อ คืนค่า PREEMPT_NONE ให้เป็นโหมด preemption เริ่มต้น โดยให้เหตุผลว่าเป็นการถดถอยร้ายแรง
- อย่างไรก็ตาม Peter Zijlstra ผู้เขียนโค้ดเดิมมีท่าทีไม่เห็นด้วยกับการรับแพตช์ดังกล่าว และระบุว่าทางแก้คือ ให้ PostgreSQL ใช้ส่วนขยาย RSEQ (Restartable Sequences) time slice
- ส่วนขยาย RSEQ time slice ก็เป็นฟีเจอร์ที่รวมอยู่ใน Linux 7.0 เช่นกัน
- Zijlstra อธิบายว่า "สิ่งนี้ช่วยจำกัดการเปิดให้เห็นการถูก preempt ของผู้ถือ lock ได้"
ขอบเขตผลกระทบและกำหนดการออกเวอร์ชัน
- หากจุดยืนนี้ยังคงเดิม ประสิทธิภาพของ PostgreSQL ในบางสถานการณ์บน Linux 7.0 รุ่นเสถียรอาจลดลงอย่างมากจนกว่าจะมีการอัปเดต PostgreSQL
- Linux 7.0 รุ่นเสถียรมีกำหนดออกใน อีกประมาณ 2 สัปดาห์
- Linux 7.0 จะเป็น เคอร์เนลพื้นฐานของ Ubuntu 26.04 LTS ซึ่งมีกำหนดออกช่วงปลายเดือนเมษายน ดังนั้น Ubuntu 26.04 LTS ก็อาจได้รับผลกระทบเดียวกันด้วย
2 ความคิดเห็น
เคยได้ยินมาว่าเหล่านักพัฒนาเคอร์เนลพูดกับนักพัฒนา PostgreSQL มาตลอดเกือบ 10-20 ปีว่า "ไม่แนะนำให้ใช้ spinlock ใน userland จึงอยากให้ช่วยทบทวนใหม่" ครับ..
https://x.com/kosaki55tea/status/2040458791536497035
ความเห็นจาก Hacker News
ควรค่าแก่การอ่าน โพสต์ติดตามบน LKML ของ Andres Freund นักพัฒนา Postgres
เป็นความเห็นที่ว่าเหล่าผู้ดูแล Linux ควรให้ แอปหลักอย่าง PostgreSQL เป็นกลุ่มที่ต้องรองรับก่อน
ทำให้นึกถึงกรณีในอดีตที่ Fedora บล็อกการอัปเดตเมื่อมีการติดตั้ง Wine
นั่นคือไม่ใช่ปัญหาที่ผู้ใช้ PostgreSQL ทุกคนจะเจอเมื่ออัปเดตไปใช้เคอร์เนลล่าสุด
มีความเห็นว่าการใช้ spinlock ใน userspace โดยไม่มีการรองรับจากเคอร์เนล เป็นการเชื้อเชิญให้เกิดปัญหาด้านประสิทธิภาพเอง
แต่ล็อกที่อิง futex ทำให้เกิด regression ด้านประสิทธิภาพได้จาก การเพิ่มขึ้นของ memory barrier
อีกทั้ง Postgres ยังต้องคำนึงถึงแพลตฟอร์มที่ยังไม่รองรับการทำ atomic operation ขนาด 8 ไบต์ จึงแทนที่ได้ยาก
spinlock ที่เป็นปัญหาถูกถอดออกไปเมื่อไม่นานนี้แล้ว และเมื่อ ใช้ huge pages คอขวดก็แทบหายไป
ยังมีการอ้างว่า “ไม่มีใครใช้เคอร์เนลล่าสุดในโปรดักชัน”
แต่ในความเป็นจริง Ubuntu 26.04 LTS ที่ อิง Linux 7.0 กำลังจะออกในไม่ช้า จึงจะมีผู้ใช้จำนวนมากใช้งานมันเร็ว ๆ นี้
ตอนนี้ปัญหาคือต้องใช้ kernel patch ไม่ใช่แค่ sysctl
ดูข้อมูลพื้นหลังของ PREEMPT_LAZY ได้ในบทความของ LWN
มีคอมเมนต์แซวว่า “เช็กหรือยังว่า Jia Tan เพิ่งส่ง kernel patch มาหรือเปล่า”
และมีคำตอบกลับมาว่า “ไม่เห็นต้องทำแบบนั้นเลย เพราะตอนนี้ก็มี ช่องโหว่มากพออยู่แล้ว”
มีความเห็นว่าสงสัยว่า asynchronous I/O และการปรับจูน parallel query ใน PostgreSQL 18 จะช่วยชดเชยการลดลงของประสิทธิภาพครั้งนี้ได้หรือไม่
ดูรายละเอียดที่เกี่ยวข้องได้ใน release note ของ PostgreSQL 18
ยังมีความเห็นตั้งคำถามว่าทำไมถึงต้องมี โหมด preemption แบบไดนามิก อย่าง PREEMPT_LAZY
เพราะประโยชน์ที่ผู้ใช้ทั่วไปจะได้รับนั้นไม่ชัดเจน
ทำให้เคอร์เนลได้รับข้อมูลที่ชัดเจนขึ้นและ ปรับปรุงการตัดสินใจด้าน scheduling ได้
มีคอมเมนต์หนึ่งบอกว่าเคยวัดได้ว่า ประสิทธิภาพลดลง 10% ระหว่าง FreeBSD 14 กับ 15.0 และพอเห็นกรณีนี้แล้วก็รู้สึกสบายใจขึ้น
ยังมีเสียงวิจารณ์ว่า Phoronix เขียนข่าวโดยตรวจสอบไม่เพียงพอ
ในอีเมลติดตามมีข้อสรุปว่า benchmark เองผิดพลาด และจริง ๆ แล้วไม่ได้เป็นปัญหาใหญ่
สำหรับ PostgreSQL อาจไม่ใช่ปัญหาใหญ่ แต่ก็อาจกระทบแอปอื่นที่ไม่สามารถใช้ huge pages ได้
ดังนั้นจึงมีความเห็นว่าไม่ควรปล่อยผ่านไปเฉย ๆ
มีการแชร์ ลิงก์เธรด LKML เก่า มาด้วย