ก่อนอื่นคุณไม่ได้อยู่คนเดียวในการทำให้งงเกี่ยวกับปัญหาเหล่านี้
นี้ไม่ได้ จำกัด เพียงtmpfs
แต่ได้รับความกังวลอ้างกับ
NFSv4
หากแอปพลิเคชันอ่าน 'หลุม' ในไฟล์แบบกระจายระบบไฟล์จะแปลงบล็อกว่างเปล่าเป็นบล็อก "ของจริง" ที่เต็มไปด้วยเลขศูนย์และส่งกลับไปยังแอปพลิเคชัน
เมื่อmd5sum
พยายามสแกนไฟล์มันเลือกที่จะทำตามลำดับอย่างชัดเจน
ซึ่งจะทำให้มีความรู้สึกมากขึ้นอยู่กับสิ่งที่ md5sum พยายามทำ
เนื่องจากมีรู "พื้นฐาน" อยู่ในไฟล์การอ่านแบบต่อเนื่องนี้จะเกิดขึ้น (ในบางสถานการณ์) ทำให้สำเนาของการดำเนินการเขียนเช่นเดียวกับการกรอกไฟล์ นี้จากนั้นจะได้รับในปัญหาลึกรอบหรือไม่ว่าเป็นดำเนินการในระบบแฟ้มสนับสนุนfallocate()
FALLOC_FL_PUNCH_HOLE
โชคดีที่ไม่เพียง แต่tmpfs
รองรับสิ่งนี้ แต่ยังมีกลไกในการ "ขุด" หลุมกลับออกไป
การใช้ยูทิลิตี้ CLI ทำให้fallocate
เราสามารถตรวจจับและขุดหลุมเหล่านี้ได้สำเร็จ
ตามman 1 fallocate
:
-d, --dig-holes
Detect and dig holes. This makes the file sparse in-place, without
using extra disk space. The minimum size of the hole depends on
filesystem I/O block size (usually 4096 bytes). Also, when using
this option, --keep-size is implied. If no range is specified by
--offset and --length, then the entire file is analyzed for holes.
You can think of this option as doing a "cp --sparse" and then
renaming the destination file to the original, without the need for
extra disk space.
See --punch-hole for a list of supported filesystems.
fallocate
ทำงานในระดับไฟล์แม้ว่าและเมื่อคุณทำงานmd5sum
กับอุปกรณ์บล็อก (ขอให้อ่านตามลำดับ) คุณกำลังสะดุดช่องว่างที่แน่นอนระหว่างวิธีที่fallocate()
syscall ควรทำงาน เราสามารถเห็นสิ่งนี้ได้ในทางปฏิบัติ:
ในการดำเนินการโดยใช้ตัวอย่างของคุณเราเห็นดังต่อไปนี้:
$ fs=$(mktemp -d)
$ echo ${fs}
/tmp/tmp.ONTGAS8L06
$ dd if=/dev/zero of=${fs}/sparse100M conv=sparse seek=$((100*2*1024-1)) count=1 2>/dev/null
$ echo "Before:" "$(ls ${fs}/sparse100M -s)"
Before: 0 /tmp/tmp.ONTGAS8L06/sparse100M
$ sudo losetup /dev/loop0 ${fs}/sparse100M
$ sudo md5sum /dev/loop0
2f282b84e7e608d5852449ed940bfc51 /dev/loop0
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 102400 /tmp/tmp.ONTGAS8L06/sparse100M
$ fallocate -d ${fs}/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 0 /tmp/tmp.ONTGAS8L06/sparse100M
ตอนนี้ ... ที่ตอบคำถามพื้นฐานของคุณ คำขวัญทั่วไปของฉันคือ "ทำให้ประหลาด" ดังนั้นฉันจึงขุดเพิ่มเติม ...
$ fs=$(mktemp -d)
$ echo ${fs}
/tmp/tmp.ZcAxvW32GY
$ dd if=/dev/zero of=${fs}/sparse100M conv=sparse seek=$((100*2*1024-1)) count=1 2>/dev/null
$ echo "Before:" "$(ls ${fs}/sparse100M -s)"
Before: 0 /tmp/tmp.ZcAxvW32GY/sparse100M
$ sudo losetup /dev/loop0 ${fs}/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 1036 /tmp/tmp.ZcAxvW32GY/sparse100M
$ sudo md5sum ${fs}/sparse100M
2f282b84e7e608d5852449ed940bfc51 /tmp/tmp.ZcAxvW32GY/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 1036 /tmp/tmp.ZcAxvW32GY/sparse100M
$ fallocate -d ${fs}/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 520 /tmp/tmp.ZcAxvW32GY/sparse100M
$ sudo md5sum ${fs}/sparse100M
2f282b84e7e608d5852449ed940bfc51 /tmp/tmp.ZcAxvW32GY/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 520 /tmp/tmp.ZcAxvW32GY/sparse100M
$ fallocate -d ${fs}/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 516 /tmp/tmp.ZcAxvW32GY/sparse100M
$ fallocate -d ${fs}/sparse100M
$ sudo md5sum ${fs}/sparse100M
2f282b84e7e608d5852449ed940bfc51 /tmp/tmp.ZcAxvW32GY/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 512 /tmp/tmp.ZcAxvW32GY/sparse100M
$ fallocate -d ${fs}/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 0 /tmp/tmp.ZcAxvW32GY/sparse100M
$ sudo md5sum ${fs}/sparse100M
2f282b84e7e608d5852449ed940bfc51 /tmp/tmp.ZcAxvW32GY/sparse100M
$ echo "After:" "$(ls ${fs}/sparse100M -s)"
After: 0 /tmp/tmp.ZcAxvW32GY/sparse100M
คุณจะเห็นว่าเป็นเพียงการกระทำของการดำเนินการlosetup
เปลี่ยนแปลงขนาดของแฟ้มเบาบาง ดังนั้นสิ่งนี้จึงกลายเป็นการผสมผสานที่น่าสนใจของtmpfs
กลไกกลไก HOLE_PUNCH fallocate
และอุปกรณ์ตัดกัน