ป้อนติด namespace ก่อนที่จะตั้งขึ้นchrootจะช่วยให้คุณหลีกเลี่ยง cluttering namespace /procโฮสต์กับม้าเพิ่มเติมเช่นสำหรับ คุณสามารถใช้chrootใน namespace เมานต์เป็นแฮ็คที่ดีและเรียบง่าย
ฉันคิดว่ามันมีข้อดีที่จะเข้าใจpivot_rootแต่มันมีช่วงของการเรียนรู้เล็กน้อย เอกสารไม่ได้อธิบายทุกอย่าง ... แม้ว่าจะมีตัวอย่างการใช้งานในman 8 pivot_root(สำหรับคำสั่งเชลล์) man 2 pivot_root(สำหรับการเรียกของระบบ) อาจชัดเจนขึ้นถ้าทำเช่นเดียวกันและรวมโปรแกรมตัวอย่าง C ไว้ด้วย
วิธีใช้ pivot_root
ทันทีหลังจากเข้าสู่ Mount namespace คุณต้องmount --make-rslave /หรือเทียบเท่า มิฉะนั้นการเปลี่ยนแปลงติดของคุณทั้งหมดเผยแพร่สู่ม้าใน namespace pivot_rootเดิมรวมทั้ง คุณไม่ต้องการที่ :)
หากคุณใช้unshare --mountคำสั่งให้สังเกตว่ามีการบันทึกไว้เพื่อให้ใช้เป็นmount --make-rprivateค่าเริ่มต้น AFAICS นี่เป็นค่าเริ่มต้นที่ไม่ดีและคุณไม่ต้องการสิ่งนี้ในรหัสการผลิต เช่น ณ จุดนี้มันจะหยุดejectทำงานบน DVD หรือ USB ที่ติดตั้งในเนมสเปซโฮสต์ DVD หรือ USB จะยังคงติดตั้งอยู่ภายในแผนผังเมาท์ส่วนตัวและเคอร์เนลจะไม่อนุญาตให้คุณนำแผ่นดีวีดีออก
เมื่อคุณทำเช่นนั้นคุณสามารถติดตั้งเช่น/procไดเรกทอรีที่คุณจะใช้ chrootเช่นเดียวกับที่คุณต้องการสำหรับ
ซึ่งแตกต่างจากเมื่อคุณใช้chroot, pivot_rootต้องการให้ระบบแฟ้มรากใหม่ของคุณเป็นจุดติด mount --rbind new_root new_rootถ้ามันไม่ได้เป็นหนึ่งแล้วคุณสามารถตอบสนองนี้โดยเพียงแค่ใช้การผูกติด:
ใช้pivot_root- จากนั้นumountระบบไฟล์รูทแบบเก่าด้วยตัวเลือก-l/ MNT_DETACH( คุณไม่ต้องการumount -Rซึ่งอาจใช้เวลานานกว่า )
ในทางเทคนิคแล้วการใช้pivot_rootโดยทั่วไปจำเป็นต้องเกี่ยวข้องกับการใช้chrootเช่นกัน ไม่ใช่ "อย่างใดอย่างหนึ่งหรือ"
ตามที่man 2 pivot_rootกำหนดไว้เท่านั้นเป็นการแลกเปลี่ยนรูทของการเมาท์เนมสเปซ ไม่ได้กำหนดให้เปลี่ยนไดเรกทอรีทางกายภาพที่กระบวนการของกระบวนการกำลังชี้ไป หรือไดเรกทอรีทำงานปัจจุบัน ( /proc/self/cwd) มันเกิดขึ้นว่ามันไม่ทำเช่นนั้น แต่นี้เป็นสับที่จะจัดการกับหัวข้อเคอร์เนล manpage บอกว่าสามารถเปลี่ยนแปลงได้ในอนาคต
โดยปกติคุณต้องการลำดับนี้:
chdir(new_root); // cd new_root
pivot_root(".", put_old); // pivot_root . put_old
chroot("."); // chroot .
postition ของchrootในลำดับนี้เป็นอีกหนึ่งรายละเอียดที่ลึกซึ้ง แม้ว่าจุดประสงค์pivot_rootคือการจัดเรียงเมาท์เนมสเปซใหม่อีกครั้งรหัสเคอร์เนลดูเหมือนว่าจะค้นหาระบบไฟล์รูทเพื่อย้ายโดยดูที่รูตต่อกระบวนการซึ่งเป็นchrootชุด
ทำไมถึงใช้ pivot_root
โดยหลักการแล้วมันสมเหตุสมผลที่จะใช้pivot_rootเพื่อความปลอดภัยและการแยก ฉันชอบคิดเกี่ยวกับทฤษฎีความปลอดภัยตามความสามารถ คุณส่งรายการทรัพยากรเฉพาะที่จำเป็นและกระบวนการไม่สามารถเข้าถึงทรัพยากรอื่นได้ ในกรณีนี้เรากำลังพูดถึงระบบไฟล์ที่ส่งผ่านไปยังเมานต์เนมสเปซ แนวคิดนี้ใช้โดยทั่วไปกับคุณลักษณะ "namespaces" ของ Linux แม้ว่าฉันอาจจะไม่ได้แสดงความเป็นไปได้ดีนัก
chrootตั้งค่ากระบวนการรากเท่านั้น แต่กระบวนการยังคงอ้างถึงเนมสเปซการเมาท์แบบเต็ม หากกระบวนการยังคงมีสิทธิ์ดำเนินการchrootดังนั้นจะสามารถสำรองข้อมูลเนมสเปซระบบไฟล์ได้ ตามรายละเอียดในman 2 chroot"superuser สามารถหลบหนีจาก 'คุก chroot' โดย ... "
อีกวิธีหนึ่งที่กระตุ้นความคิดที่จะเลิกเป็นchroot nsenter --mount=/proc/self/ns/mntนี่อาจเป็นเหตุผลที่ดีกว่าสำหรับหลักการ nsenter/ setns()จำเป็นต้องโหลดรูทกระบวนการอีกครั้งจากรูทของเนมสเปซเมาต์ ... แม้ว่าข้อเท็จจริงนี้จะใช้งานได้เมื่อทั้งสองอ้างถึงฟิสิคัลไดเร็กทอรีที่ต่างกันอาจถูกพิจารณาว่าเป็นข้อบกพร่องเคอร์เนล (หมายเหตุทางเทคนิค: อาจมีหลายระบบไฟล์ติดตั้งที่ด้านบนของแต่ละอื่น ๆ ที่รูท; setns()ใช้ด้านบนติดตั้งล่าสุดหนึ่ง)
สิ่งนี้แสดงให้เห็นถึงข้อดีอย่างหนึ่งของการรวม mount namespace เข้ากับ "PID namespace" การอยู่ภายใน PID เนมสเปซจะป้องกันคุณจากการป้อนเมานต์เนมสเปซของกระบวนการที่ไม่ได้กำหนดไว้ นอกจากนี้ยังป้องกันไม่ให้คุณเข้าสู่รูทของกระบวนการที่ไม่ได้กำหนดไว้ ( /proc/$PID/root) และแน่นอนเนมสเปซ PID ยังป้องกันไม่ให้คุณฆ่ากระบวนการใด ๆ ที่อยู่นอก :-)
pivot_rootและchroot: ฉันลองดูที่แหล่งข้อมูลนักเทียบท่าและพบว่าหากการดำเนินการล้มเหลวpivot_rootมันกลับไปchrootเช่นกลไกเหล่านี้ถือว่ามีความคล้ายคลึงกันอย่างน้อยในการทำงานเพื่อวัตถุประสงค์ในการจัดเก็บ