2013-05-21 87 views
3

我正在嘗試使用kernel32.dll的CreateFile方法來創建一個安全的文件句柄,它總是返回一個無效的句柄。Kernel32.dll中的CreateFile返回一個無效的句柄

對我在做什麼錯在這裏「C任何幫助:?

CreateFile(
    lpFileName: "C:", 
    dwDesiredAccess: FileAccess.ReadWrite, 
    dwShareMode: FileShare.ReadWrite, 
    lpSecurityAttributes: IntPtr.Zero, 
    dwCreationDisposition: FileMode.OpenOrCreate, 
    dwFlagsAndAttributes: FileAttributes.Normal, 
    hTemplateFile: IntPtr.Zero); 

[DllImport("kernel32.dll", SetLastError = true, CharSet = CharSet.Auto)] 
public static extern SafeFileHandle CreateFile(
    string lpFileName, 
    [MarshalAs(UnmanagedType.U4)] FileAccess dwDesiredAccess, 
    [MarshalAs(UnmanagedType.U4)] FileShare dwShareMode, 
    IntPtr lpSecurityAttributes, 
    [MarshalAs(UnmanagedType.U4)] FileMode dwCreationDisposition, 
    [MarshalAs(UnmanagedType.U4)] FileAttributes dwFlagsAndAttributes, 
    IntPtr hTemplateFile); 
+2

什麼錯誤代碼,你從'GetLastError函數()'得到什麼? – Steve

回答

3

有一對夫婦的參數並不完全正確

  1. 要打開的卷,你必須前綴驅動信與\\.\
  2. 只能打開音量與讀取權限。

試試這個代碼:

SafeFileHandle handle = CreateFile(
    lpFileName: @"\\.\C:", 
    dwDesiredAccess: FileAccess.Read, 
    dwShareMode: FileShare.ReadWrite, 
    lpSecurityAttributes: IntPtr.Zero, 
    dwCreationDisposition: FileMode.OpenOrCreate, 
    dwFlagsAndAttributes: FileAttributes.Normal, 
    hTemplateFile: IntPtr.Zero); 

注意,打開卷句柄與讀取權限,你必須以管理員身份運行,否則你將得到拒絕訪問(錯誤代碼5)。正如Nik Bougalis和CreateFile文檔指出的那樣,如果您指定dwDesiredAccess爲0,則不需要管理員權限。

如果此參數爲零,則即使GENERIC_READ訪問被拒絕,應用程序也可以在不訪問該文件或設備的情況下查詢某些元數據,如文件,目錄或設備屬性。

+0

即使您沒有以管理員身份運行,也可以嘗試使用'0'開啓'dwDesiredAccess'的音量。根據MSDN上的''CreateFile'頁面(http://msdn.microsoft.com/en-us/library/windows/desktop/aa363858(v = vs.85).aspx):「'dwDesiredAccess'參數可以爲零,允許應用程序在不訪問設備的情況下查詢設備屬性,這對讀取統計數據很有用,而不需要更高級別的數據讀/寫權限。正如所解釋的那樣,返回的句柄**嚴重**受限制,但這樣可以避免需要管理員訪問常規查詢。 –

+1

@NikBougalis謝謝你指出。我已經更新了我的答案以反映這一點。 – Steve

1

我這是怎麼解決這個問題

private const int GENERIC_READ = unchecked((int)0x80000000); 
    private const int FILE_SHARE_READ = 1; 
    private const int FILE_SHARE_WRITE = 2; 
    private const int OPEN_EXISTING = 3; 
    private const int IOCTL_DISK_GET_DRIVE_LAYOUT_EX = unchecked((int)0x00070050); 
    private const int ERROR_INSUFFICIENT_BUFFER = 122; 
    NativeMethods.CreateFile("\\\\.\\PHYSICALDRIVE" + PhysicalDrive, GENERIC_READ, FILE_SHARE_READ | FILE_SHARE_WRITE, IntPtr.Zero, OPEN_EXISTING, 0, IntPtr.Zero)) 
相關問題