2011-05-16 161 views
3

大家下午好,我們正在使用Windows和Linux的內存映射文件API來構建一個Windows/LINUX演示程序的原型。我們的扣除器通過對要刪除的所有數據庫記錄進行順序掃描開始。因此,在我們對要被重複刪除的數據庫記錄進行初始順序掃描期間,我們將標誌FILE_FLAG_SEQUENTIAL_SCAN傳遞給Windows API CreateFile。 一旦我們完成了我們的重複數據刪除過程的第一部分,我們嘗試使用Windows內存映射API來隨機訪問數據。此時,使用Windows C++ API,是否可以動態更改爲FILE_FLAG_RANDOM_ACCESS模式?是否可以從FILE_FLAG_SEQUENTIAL_SCAN動態更改爲FILE_FLAG_RANDOM_ACCESS?

In Linux, we are are able to do this with the following excerpt of code, 
    MapPtr = (char*)mmap((void *)BaseMapPtr ,mappedlength,PROT_READ, 
      MAP_PRIVATE, hFile,baseoff); 
        if (MapPtr == MAP_FAILED){ 
         perror("mmap"); 
         throw cException(ERR_MEMORYMAPPING,TempFileName); 
        } 
madvise(MapPtr,mappedlength,MADV_RANDOM); 

我們是通過在我們的重複數據刪除過程中的隨機訪問階段使用FILE_FLAG_SEQUENTIAL_SCAN付罰款在Windows中。謝謝。

回答

5

傳遞給CreateFile()的緩存提示標誌不會影響內存管理器滿足通過取消引用映射節中的地址而生成的頁面錯誤的方式。這樣的I/O使用相同的 - 它們使用與常規I/O相同的緩存頁面。

這就是說,當與FILE_FLAG_SEQUENTIAL_SCAN,高速緩存管理器可能進行預讀操作(甚至可將整個文件讀入內存,如果系統條件允許這一點)創建句柄到文件中。這意味着,如果順序訪問映射文件的頁面,則可能會遇到更少的硬頁面錯誤。

在我看來,通過簡單地重複使用在您的刪除處理過程中創建的句柄,您將獲得最佳服務。關閉和重新打開可能會導致文件的先前緩存頁面被丟棄,具體取決於緩存壓力。

+0

謝謝你的回答。我剛接受你的回答。我將更改我們的代碼以重用我們在重複數據刪除處理期間創建的句柄。我們注意到,當使用FILE_FLAG_SEQUENTIAL_SCAN創建文件句柄時,我們順序訪問映射文件的頁面時會遇到更少的硬頁面錯誤。這是否意味着我們在重複數據刪除處理期間不嘗試使用FILE_FLAG_RANDOM_ACCESS?謝謝。 – Frank 2011-05-17 05:52:09

+0

@Frank - 您的里程可能會有所不同。當指定FILE_FLAG_RANDOM_ACCESS時,對於句柄將禁用預讀。此外,緩存管理器在取消映射先前訪問過的文件頁面時不那麼積極 - 這裏的想法是在應用程序重新訪問頁面時最小化文件的映射/解映射事件。 – Bukes 2011-05-17 18:06:37

+0

謝謝你的回答。我想我們會嘗試使用CreateFile(...,FILE_FLAG_RANDOM_ACCESS)運行我們的重複數據刪除應用程序,以便在重複訪問重複頁面時儘量減少內存映射文件的映射/解映射事件。看到結果應該很有趣。謝謝。 – Frank 2011-05-18 01:43:58

3

如何FILE_FLAG_SEQUENTIAL_SCAN作品可以在這裏找到的描述:http://support.microsoft.com/kb/98756

因爲它只是與CreateFile函數使用,也沒有辦法,一旦文件被打開,以更新它。您可以隨時關閉文件並用另一個標誌重新打開文件。

+0

謝謝你的回答,我剛接受你的回答。你是否建議在我們的推理的第一個連續掃描階段之後,我們關閉文件。然後,在最終的隨機訪問階段,我們是否應該重新打開FILE_FLAG_RANDOM_ACCESS文件?這會影響我們使用Window Memory Mapping File API的能力嗎?謝謝。 – Frank 2011-05-16 17:03:37

+0

我們現在正在嘗試您的建議。所以我們:1.關閉(hFile)2. hFile = CreateFile((LPTSTR)TempFileName,.... Flags_ | FILE_FLAG_RANDOM_ACCESS); 3. Distance_.LowPart =(ULONG)FileSize_; Distance_.HighPart = 0; 4. dwPtr = :: SetFilePointer(hFile,Distance_.LowPart,&(Distance_.HighPart),FileBegin); 5. SetEndOfFile(hFile); 6. hMapping = :: CreateFileMapping(hFile,(SECURITY_ATTRIBUTES *)Security_,PAGE_READWRITE,0,0,0);謝謝。 – Frank 2011-05-16 17:18:42

+0

@Frank:您傳遞的標誌不會影響文件I/O的正確操作,它只會影響緩衝效率。內存映射完全可能會完全繞過緩衝,我不確定這一點。 – 2011-05-16 17:20:32

0

只是備份@Burkes回答:因爲你提到你是「使用Windows的內存映射文件API」,但應注意的是,Raymond Chen warns the cache hints have no affect on effect on memory mapped I/O

注:這些緩存提示只適用,如果你使用ReadFile(或道德等價物)。內存映射文件訪問不通過緩存管理器,因此這些緩存提示不起作用。

因此,已經被緩存的內容可能會有所幫助,但未來的內存映射訪問將無助於緩存被填充/刪除。