2012-02-20 67 views
2

據我瞭解,使用stdio.hFILE比直接read()/write()的優勢之一是緩衝,中斷處理等,所以,據我所知,所有的fwrite()小號得到緩衝,直到我做一個fclose()。到現在爲止還挺好。現在,當我做一個fclose()時,我會阻塞,直到數據刷新到磁盤或fclose()將數據交給操作系統後立即返回,並讓它閒置時刷新到磁盤?使用stdio.h異步緩衝io?

+0

在Linux上,即使'write'也不能保證數據在物理上位於磁盤上。您需要使用[fsync](http://linux.die.net/man/2/fsync)。 – 2012-02-21 09:38:56

+0

@Banthar或使用O_DIRECT選項。 – 2012-02-21 10:53:18

回答

3

有很多級別的緩衝,這取決於操作系統和許多其他的東西。

通常有一個在FILE *活在你的應用程序,要麼刷新到該文件的內部緩衝區(或任何設備的文件*連接)

  • 當內部FILE *緩衝區已滿
  • 當你寫一個換行符(在一條線上緩衝FILE *的情況下)
  • 當您關閉FILE *
  • 當你調用fflush()
  • 的FILE *也可以緩衝

在一個普通的磁盤文件的情況下,大多數操作系統具有緩衝的內核,所以沖洗 FILE *緩衝區涉及或多或少只是從你的應用程序的緩衝存儲器複製到操作系統內核,內核會照顧它在異步時將其寫入實際文件,這將導致fclose()立即返回。

在數據被複制到操作系統/內核緩衝區之前,操作系統首先必須做一些清潔工作,例如,它可能需要將數據刷新到物理文件以騰出更多數據,在文件中分配空間以確保存在空間等等,使其不會立即返回。

簡而言之,它取決於,而你無法控制它。通常,您可以使用的「最佳」方法是使用平臺相關的API,它們至少允許您將OS緩衝區刷新到物理文件,例如posix fsync()/ fdatasync()API。

0

你的理解是(至少部分)錯誤的。

I/O被緩衝,但緩衝區大小有限制。當緩衝區溢出時,它們將被刷新。另外,許多流是行緩衝;當您編寫換行符時,緩衝區將被刷新。如果情況並非如此,輸出到終端對於程序終止時所有輸出顯示都是不切實際的。

我認爲這些調用不一定會被阻塞,否則有一些函數會嘗試確保底層介質與寫入同步。這通常會造成「太低級」的問題,需要處理高速緩存和緩存這兩種軟件的複雜性,而且還需要在硬件中處理這些問題。硬盤驅動器。