【问题标题】:C# PInvoke I can't open the volume with CreateFileC# PInvoke 我无法使用 CreateFile 打开卷
【发布时间】:2020-05-07 00:28:04
【问题描述】:

我必须使用 PInvoke 中的 CreateFile 打开卷:

[DllImport("kernel32.dll", SetLastError = true)]
static extern SafeFileHandle CreateFile(string lpFileName, uint dwDesiredAccess, FileShare dwShareMode, IntPtr securityAttrs, FileMode dwCreationDisposition, FileOptions dwFlagsAndAttributes, IntPtr hTemplateFile);

但是当我使用它时:

var fileName = @"C:\Users\myuser\Desktop\file.txt"
var root = Path.GetPathRoot(fileName);
var volumePath = @"\\.\" + root.Substring(0, root.Length - 1);

var volume = CreateFile(volumePath, GENERIC_READ, FileShare.Read, IntPtr.Zero, FileMode.Open, FileOptions.None, IntPtr.Zero);
if (volume.IsInvalid)
    throw new Win32Exception(Marshal.GetLastWin32Error());

打印出来:

访问被拒绝

但是,如果我以提升的权限打开它,它会打印:

该进程无法访问该文件,因为它正被另一个进程使用

我一直在尝试一切,甚至从很多地方获取代码,但我无法让它工作。

【问题讨论】:

  • 要么该代码块被调用两次并且在第二次调用时失败(我怀疑),要么其他东西已经在没有设置共享标志的情况下访问文件。就是这么简单。等到你得到错误和断点。打开 Process Explorer 并查看谁拥有该文件的打开句柄。
  • 不错!谢谢帕桑特先生!

标签: c# pinvoke kernel32


【解决方案1】:

使用取自 here 的 PInvoke 代码:

var volume = CreateFile(volumePath, EFileAccess.GenericRead, EFileShare.Read|EFileShare.Write, IntPtr.Zero, ECreationDisposition.OpenExisting, 0, IntPtr.Zero);

我已经设法让它工作了。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2019-06-14
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多