O_APPEND mengubah write dari dua tindakan yang dapat dipisahkan menjadi satu operasi terpadu: Linux menempatkan open file description pada akhir file saat ini lalu melakukan write sebagai satu langkah atomik.
Sifat ini penting ketika beberapa writer menulis ke regular file yang sama. Urutan lseek(fd, 0, SEEK_END) lalu write(fd, ...) tidak memiliki semantik append yang sama karena writer lain dapat mengubah file di antara kedua system call tersebut.
Status append berada pada open file description
O_APPEND adalah file status flag. File status flag disimpan pada open file description, bukan pada integer file descriptor itu sendiri.
Descriptor yang dibuat dengan dup() merujuk ke open file description yang sama dengan sumbernya. Descriptor yang diwariskan melalui fork() juga tetap merujuk ke objek bersama tersebut. Mengubah O_APPEND melalui fcntl() pada salah satu descriptor karena itu memengaruhi I/O melalui descriptor lain yang berbagi open file description yang sama.
Dua pemanggilan open() yang terpisah biasanya membuat open file description berbeda walaupun keduanya menunjuk pathname yang sama. Masing-masing tetap dapat memakai O_APPEND, dan filesystem dapat menserialisasi operasi append mereka pada batas file.
Atomicity append tidak bergantung pada writer yang berbagi objek file offset. Sifat tersebut bergantung pada setiap append write yang ditempatkan di akhir file sebagai bagian dari operasi write itu sendiri.
Seek lalu write menyisakan titik interleaving
Urutan append manual dapat terlihat setara pada satu proses. Dengan writer yang berjalan bersamaan, celah di antara lseek() dan write() dapat diamati. Dua proses dapat sama-sama melakukan seek ke akhir file yang sama, kemudian melakukan write setelah masing-masing memilih posisi tersebut. Perilaku ini bukan jaminan append yang diberikan O_APPEND.
Ketika file dibuka dengan O_APPEND, kernel menempatkan offset pada akhir file tepat sebelum setiap write(), dengan penentuan posisi dan transfer data membentuk langkah append atomik.
lseek() sebelumnya tidak menggantikan perilaku ini. Selama O_APPEND tetap aktif, write() berikutnya ditempatkan pada akhir file tanpa memedulikan offset yang dipilih oleh seek.
Append atomik tidak membuat record menjadi satu transaksi
Unit atomiknya adalah penentuan posisi akhir dan penempatan data untuk satu operasi write. Record aplikasi yang dibagi ke beberapa write() tetap terdiri dari beberapa operasi, sehingga writer lain dapat berjalan di antara pemanggilan tersebut.
Setiap pemanggilan tetap di-append tanpa race seek/write, tetapi beberapa bagian record tidak dijamin tetap bersebelahan sebagai satu transaksi logis. Aplikasi yang membutuhkan satu record berada dalam satu operasi append dapat menyusun record sebelum melakukan write, dengan tetap mengikuti semantik dan batas normal filesystem serta antarmuka I/O. writev() juga dapat mengekspresikan beberapa buffer sebagai satu vectored write ketika sesuai dengan layout data.
Write yang berhasil dapat lebih pendek dari jumlah byte yang diminta. Penempatan append tidak menghapus kebutuhan menangani partial write.
Pergerakan file offset tetap terlihat
Setelah append write, offset open file description mencerminkan posisi hasil operasi. Descriptor yang berbagi open file description tersebut melihat state offset yang sama.
Hal ini dapat menghasilkan interaksi yang tidak sederhana ketika kode mencampur append write dengan read atau seek eksplisit pada descriptor yang dibuka untuk membaca dan menulis. Flag append mengatur penempatan write; flag tersebut tidak memaksa read dilakukan dari akhir file.
Setelah seek, read dapat menggunakan offset yang dipilih, sementara write() biasa berikutnya tetap menuju akhir file saat ini karena O_APPEND mengambil alih penempatan write.
Append per operasi dapat menghindari status append persisten
Linux menyediakan RWF_APPEND untuk pwritev2(). Flag ini meminta perilaku append untuk operasi write tersebut tanpa mengharuskan O_APPEND tetap aktif pada open file description.
Perbedaan ini berguna ketika satu descriptor menangani positioned write sekaligus append sesekali. O_APPEND persisten mengubah semantik write biasa melalui semua descriptor yang berbagi open file description, sedangkan RWF_APPEND membatasi permintaan append pada satu operasi vectored write.
Linux versi baru juga menyediakan RWF_NOAPPEND untuk pwritev2(), sehingga suatu operasi dapat melewati O_APPEND dan menghormati offset eksplisitnya. Antarmuka ini membuat cakupan kebijakan append lebih eksplisit: kebijakan dapat berupa state pada open file description atau properti satu operasi write.
Network filesystem dapat memiliki batas berbeda
Dokumentasi Linux open(2) mencatat batas penting pada NFS. NFS tidak menyediakan primitive append native yang sama seperti penanganan file lokal Linux, sehingga client harus mensimulasikan perilaku append. Beberapa appender yang berjalan bersamaan karena itu tidak memperoleh jaminan yang identik dengan regular file lokal.
Batas tersebut mencegah jaminan system call lokal diperlakukan sebagai jaminan universal untuk distributed filesystem. Semantik filesystem remote bergantung pada protokol dan implementasinya, bukan hanya flag yang diberikan ke open().
Filesystem dan lapisan storage lain juga dapat memiliki batas masing-masing. Format yang sensitif terhadap append perlu memperlakukan semantik filesystem sebagai bagian dari model concurrency.
Penempatan append terpisah dari durability
O_APPEND mengatur penempatan. Flag ini tidak menyatakan bahwa write yang selesai sudah mencapai persistent storage.
Proses dapat berhasil melakukan append tetapi data yang baru ditulis belum tentu durable jika data dan metadata terkait belum mencapai media persisten sesuai aturan filesystem dan storage stack. Flag seperti O_DSYNC atau O_SYNC, serta pemanggilan sinkronisasi seperti fsync(), menangani jaminan yang berbeda.
Pemisahan ini penting untuk log dan journal. Penempatan concurrent yang benar mencegah writer berlomba pada posisi akhir logis yang sama, sedangkan kebijakan durability menentukan kapan record yang selesai dapat bertahan terhadap kegagalan sistem.
O_APPEND menyelesaikan masalah concurrency yang sempit: setiap append write memilih akhir file saat itu dan menulis di sana sebagai satu operasi. Flag ini tidak menggabungkan beberapa write menjadi transaksi, tidak menjamin persistence, dan tidak menghapus batas semantik filesystem remote.