Files & I/O

flushing, syncing, and durability

/ fsync -> EFF-sink /

When you 'save' a file, where does the data actually end up - and at what point is it safe from a power cut? There are several stops on the journey from your program to the spinning platter or flash chip, and 'I called write' does not mean 'it is safely on disk.' Understanding the layers is what stops you losing data when a machine crashes at the wrong moment.

There are typically three layers between your data and durability. First, if you used buffered stdio, the bytes may be sitting in the library's user-space buffer; fflush(stream) pushes them out of that buffer into the kernel. Second, once in the kernel, the bytes sit in the kernel's page cache - the operating system has accepted them but, for speed, has not necessarily written them to the physical device yet; write() has returned, yet the data is still only in RAM. Third, fsync(fd) tells the kernel to actually flush that file's data from the page cache down to the storage device and wait until the device confirms - only after fsync returns is the data durable against a crash or power loss. There is also fdatasync (flush the data but skip some metadata) and, for directory entries, you may need to fsync the directory too so that a newly created file's name survives.

Why it matters: this is the difference between 'it looked saved' and 'it is actually saved.' Databases, editors, and anything that must not lose your work call fsync at the right moments, accepting that fsync is slow (it waits for real hardware) precisely because durability has a cost. The common misconception is that a returned write() means the data is on disk - it does not; it means the kernel has it. Flushing the stdio buffer (fflush) and syncing to the device (fsync) are two different steps at two different layers, and you need both for a guarantee.

fputs(line, f); /* 1. bytes may be in the stdio buffer */ fflush(f); /* 2. push them from the buffer into the kernel */ fsync(fileno(f)); /* 3. force the kernel to write them to the device, durable now */

Three layers, three steps: stdio buffer -> kernel page cache -> physical device. Durability needs all three.

A returned write() does NOT mean the data is on the physical disk - it only means the kernel has accepted it into its cache. Durability against a crash requires fsync (or fdatasync); fflush alone only empties the stdio buffer into that same volatile cache.

Also called
fsync and durabilitydata durabilityfsync 與資料持久性