2010-07-21 64 views
6

我試圖實現一個文件存儲機制,該機制在單個文件中保存了大量不定大小的記錄,保證記錄集將始終可恢復到一致狀態,即使系統在硬件故障水平。內存映射文件中的數據是否保證順序刷新?

到目前爲止,我提出的每個方案都是按順序寫入數據的關鍵。某些數據片段會附加到每條記錄的末尾,以確認寫入成功。但是,如果數據在刷新時不一定順序寫入磁盤,則可能在內容數據之前寫入確認數據。

周圍有此兩個明顯的方式,但兩者都不可取:

  1. 刷新內容,然後寫入確認並刷新它。增加額外的沖洗可能會降低性能。
  2. 在確認中包含校驗和(需要讀取內容以確認其有效)。

我在Windows上使用C#(32位和64位)和.NET 4.0的內存映射文件執行

+0

第二個想法(驗證數據,時間戳,序列號和校驗和)似乎是合法的。但是,一般來說,您應該查看高可用性羣集,並在網絡中使用不同的機器。所有記錄或日誌寫入都需要通過網絡複製到兩臺或更多臺機器上。您無法從單個機器提取任何保證期限。 – rwong 2014-10-13 21:15:31

回答

1

這是等級太低和操作系統具體爲C#。嘗試使用C語言的Windows API,並仔細閱讀API規範。

0

您是否嘗試過在底層文件流上使用FileOptions.WriteThrough?這可能有幫助,因爲它禁用緩衝。其他想法是將包含確認信息的單獨文件保存爲最後一次寫入的偏移量,如果它不符合文件大小(例如由於斷電),則可以簡單地截斷它,執行該大小

+1

在故障恢復方面,這些都是很好的想法。不幸的是,它們不適用於內存映射文件。 MM文件始終禁用WriteThrough,因爲它們使用操作系統的底層頁面管理器來處理緩衝。保留確認日誌也是一個好主意,但它還有其他問題。然後每個文件操作需要兩次刷新(一個用於MM文件,一個用於日誌)。更有問題的是,對於MM文件,您不知道刷新完成的時間。充其量,您可以指示操作系統開始刷新,但是在完成後您不會得到確認。這使得確定性日誌成爲不可行 – 2010-11-22 00:37:04

+0

@Kennet Belenky:關於刷新的內容很奇怪,與[Java]相比(http://docs.oracle.com/javase/1.4.2/docs/api/java/nio /MappedByteBuffer.html)。也許你可以使用一個正常的FileOutputStream日誌(日誌很短,所以不會有太多的速度差異)? IIUYC失去未經證實的記錄並不是那麼糟糕,所以你可以更少刷新日誌。 – maaartinus 2012-08-25 03:37:09

+0

@maaartinus Java的API肯定比較容易理解,但它也不完美。它很好,它提供了返回時刷新完成的保證。但是,如果它爲您提供了異步通知,那麼您就可以開展業務了。旋轉磁盤沖洗的10ms尋道時間是閒置很長時間。 – 2012-08-28 17:11:19

相關問題