歡迎來到Linux教程網
Linux教程網
Linux教程網
Linux教程網
Linux教程網 >> Linux基礎 >> Linux教程 >> sync,fsync,fdatasync,fflush之間的區別

sync,fsync,fdatasync,fflush之間的區別

日期:2017/2/27 16:02:22   编辑:Linux教程
大多數的unix/linux對磁盤io的寫操作都是通過緩存來完成的,基本的原理如下:當將數據寫入文件時,內核通常先將該數據復制到其中一個緩沖區 中,如果該緩沖區尚未寫滿,則並不將其排入輸出隊列,而是等待其寫滿或者當內核需要重用該緩沖區以便存放其他磁盤塊數據時,再將該緩沖排入輸出隊列,然後 待其到達隊首時,才進行實際的I/O操作。 我們稱之為延遲寫,極大的減少了寫磁盤的次數。
但是在沒寫特殊的應用中我們需要實時的將應用層數據寫入到磁盤上 特別是一些高可靠性要求的系統中 數據需要及時的寫入磁盤 即便是瞬時系統故障 數據也可以安全恢復,於是就有了sync、fsync,fdatasync,fflush等函數。

主要區別:
sync:將所有修改過的快緩沖區排入寫隊列然後返回,並不等待實際寫磁盤操作結束;通常稱為update的系統守護進程會周期性地(一般每隔30秒)調用sync函數。這就保證了定期沖洗內核的塊緩沖區。該函數沒有參數,對系統中的所有緩沖區起作用。

fsync:只對有文件描述符指定的單一文件起作用,並且等待寫磁盤操作結束,然後返回(因此最安全);該函數以指定的文件描述符(對應以open等函數打開的文件)為參數,僅對該描述符指定的文件起作用。

fdatasync:類似於fsync,但只影響文件的數據部分。而fsync還會同步更新文件的屬性;實際上目前glibc中fdatasync函數的實現已經和fsync一摸一樣了。可以理解為與fsync相同

fflush:標准IO函數(如fread,fwrite等)會在內存中建立緩沖,該函數刷新內存緩沖,將內容寫入內核緩沖,要想將其真正寫入磁盤,還需要調用fsync。(即先調用fflush然後再調用fsync,否則不會起作用)。fflush以指定的文件流描述符為參數(對應以fopen等函數打開的文件流),僅僅是把上層緩沖區中的數據刷新到內核緩沖區就返回,因此相對於fsync而言不是很安全,還需要再調用一下fsync來把數據真正寫入硬盤。
為了實現以上功能,需要把文件流描述符(fp)轉換為文件描述符(fd),以方便fsync的調用,使用以下函數:
int fileno(FILE *fp); <- in stdio.

總結:
如果是對所有的緩沖區發出寫硬盤的命令,應該使用sync函數,但應注意該函數僅僅只是把該命令放入隊列就返回了,在編程時應注意這一點;
如果對要把一個已打開的文件所做的修改提交到硬盤,應調用fsync函數,該函數會在數據實際寫入硬盤後才返回,因此是最安全最可靠的方式;
如果是針對一個已打開的文件流操作,則應首先調用fflush把修改同步到內核緩沖區,然後再調用fsync把修改實際的同步到硬盤。
Copyright © Linux教程網 All Rights Reserved