[英]Handle leaking in WinAPI CreateFile?
CreateFile分配2(!!)句柄,而CloseHandle在嘗試獲取對cd-rom設備的低級訪問時僅關閉一個句柄。 操作系統Windows XP SP3,經測試的7台計算機中的5台工作原理相同。
當試圖訪問硬盤驅動器盤符時,CreateFiles工作正常並只分配一個句柄。
以下是示例代碼:
HANDLE m_driveHandle = CreateFileW(“\\\\\\\\。\\\\ E”,GENERIC_READ | GENERIC_WRITE,FILE_SHARE_READ | FILE_SHARE_WRITE,NULL,OPEN_EXISTING,FILE_ATTRIBUTE_NORMAL,NULL);可能的原因是什么,或者只是一個微軟的bug?
UPD。 驅動器名稱未被剪切和粘貼..正確的字符串是L“\\\\。\\ E:”。 Bug仍然存在。
UPD2。 問題解決了! 請參閱下面的答案(歐米茄)。
您的示例代碼中似乎存在一些錯誤。 如果它實際上是從你的程序中復制和粘貼的話,那么就必須有其他東西在進行。
首先,您使用MBCS字符串調用Unicode函數:第一個參數應該以L
為前綴或用_T()
包圍。
其次,也許更重要的是, "\\\\\\\\.\\\\E"
不是有效名稱。 你錯過了一個尾隨冒號:要打開一個卷,它必須是\\\\.\\X:
的形式,或者在你的情況下是"\\\\\\\\.\\\\E:"
。
修復了這兩個錯誤(第一個阻止編譯,第二個需要獲得除INVALID_HANDLE_VALUE
以外的任何東西),一切似乎都按預期工作。 我使用GetProcessHandleCount來計算打開句柄的數量,它之前和之后都是相同的:
HANDLE m_driveHandle = NULL;
HANDLE m_process = GetCurrentProcess();
DWORD handleCount;
GetProcessHandleCount(m_process, &handleCount);
cout << "Currently held handles: " << handleCount << endl;
for (int i = 0; i < 10; ++i) {
m_driveHandle = CreateFileW(L"\\\\.\\E:",
GENERIC_READ | GENERIC_WRITE,
FILE_SHARE_READ | FILE_SHARE_WRITE,
NULL,
OPEN_EXISTING,
FILE_ATTRIBUTE_NORMAL,
NULL
);
if (INVALID_HANDLE_VALUE == m_driveHandle) {
cout << "Invalid handle" << endl;
} else {
CloseHandle(m_driveHandle);
}
GetProcessHandleCount(m_process, &handleCount);
cout << "Currently held handles: " << handleCount << endl;
}
注釋掉CloseHandle調用會導致handleCount按預期增加。
問題出在Kaspersky Antivirus軟件中。 在所有測試的機器上安裝了KAV 6.0。 刪除軟件后,需要清除注冊表中CD驅動程序的UpperFilters和LowerFilters:
HKEY_LOCAL_MACHINE \\ SYSTEM \\ CURRENTCONTROLSET \\控制\\類{4D36E965-E325-11CE-BFC1-08002BE10318}
只有在這些步驟處理后才能停止泄漏..最新版本的軟件,卡巴斯基互聯網安全,也可以在不泄漏的情況下運行。
建議:
將日志開始於調用CreateFileW,這確認它執行了多少次;
你試過SysInternals的“處理”工具嗎? 它可以顯示程序打開的每個句柄,而不僅僅是計數。 因此,您將知道哪個句柄保持打開狀態。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.