The Linux Programming Interface

(nextflipdebug5) #1

242 Chapter 13


After this open() call, every write() to the file automatically flushes the file data and
metadata to the disk (i.e., writes are performed according to synchronized I/O file
integrity completion).

Older BSD systems used the O_FSYNC flag to provide O_SYNC functionality. In
glibc, O_FSYNC is defined as a synonym for O_SYNC.

Performance impact of O_SYNC
Using the O_SYNC flag (or making frequent calls to fsync(), fdatasync(), or sync()) can
strongly affect performance. Table 13-3 shows the time required to write 1 million
bytes to a newly created file (on an ext2 file system) for a range of buffer sizes with
and without O_SYNC. The results were obtained (using the filebuff/write_bytes.c
program provided in the source code distribution for this book) using a vanilla
2.6.30 kernel and an ext2 file system with a block size of 4096 bytes. Each row
shows the average of 20 runs for the given buffer size.
As can be seen from the table, O_SYNC increases elapsed times enormously—in
the 1-byte buffer case, by a factor of more than 1000. Note also the large differences
between the elapsed and CPU times for writes with O_SYNC. This is a consequence of
the program being blocked while each buffer is actually transferred to disk.
The results shown in Table 13-3 omit a further factor that affects performance
when using O_SYNC. Modern disk drives have large internal caches, and by default,
O_SYNC merely causes data to be transferred to the cache. If we disable caching on
the disk (using the command hdparm –W0), then the performance impact of O_SYNC
becomes even more extreme. In the 1-byte case, the elapsed time rises from 1030
seconds to around 16,000 seconds. In the 4096-byte case, the elapsed time rises
from 0.34 seconds to 4 seconds.
In summary, if we need to force flushing of kernel buffers, we should consider
whether we can design our application to use large write() buffer sizes or make judi-
cious use of occasional calls to fsync() or fdatasync(), instead of using the O_SYNC flag
when opening the file.

Table 13-3: Impact of the O_SYNC flag on the speed of writing 1 million bytes

BUF_SIZE

Time required (seconds)
Without O_SYNC With O_SYNC
Elapsed Total CPU Elapsed Total CPU
1 0.73 0.73 1030 98.8
16 0.05 0.05 65.0 0.40
256 0.02 0.02 4.07 0.03
4096 0.01 0.01 0.34 0.03
Free download pdf