.NET File.Exists在Windows\System32\Drivers文件夹中不起作用?

Dav*_*vy8 7 .net 64-bit drivers windows-vista

这个过程被提升了,我确保VS调试器中的路径是正确的(我使用的是Environment.GetFolderPath(Environment.SpecialFolder.System)而不是硬编码)但File.Exists仍然返回false.

我需要这个的原因是确保安装某些第三方驱动程序的解决方法,因为他们的注册表设置在卸载时不会被删除.

我知道写入是通过虚拟化重定向的,但这对于检查文件的存在也是如此吗?

Pau*_*der 10

是的,虚拟化发生在非常低​​的水平.File.Exists方法基本上调用Win32 CreateFile方法并检查错误.CreateFile由WOW子系统重定向.

您可以在呼叫前暂时禁用虚拟化.

[DllImport( "kernel32", CharSet=CharSet.Unicode, SetLastError=true )]
public static extern bool Wow64DisableWow64FsRedirection( ref IntPtr oldValue );

[DllImport( "kernel32", CharSet=CharSet.Unicode, SetLastError=true )]
public static extern bool Wow64RevertWow64FsRedirection( IntPtr oldValue );
Run Code Online (Sandbox Code Playgroud)

当然要完成,你必须检查文件存在与虚拟化以及关闭.这同样适用于检查注册表项.

public static bool FileExists( string path )
{
    if( File.Exists( path ) ) return true;
    IntPtr oldValue = IntPtr.Zero;
    try
    {
        if( Environment.GetEnvironmentVariable( "PROCESSOR_ARCHITEW6432" ) == null )
            return false;

        Wow64DisableWow64FsRedirection( ref oldValue );
        if( File.Exists( path ) ) return true;

        return false;
    }
    finally
    {
        if( oldValue != IntPtr.Zero )
            Wow64RevertWow64FsRedirection( ref oldValue );            
    }   
}
Run Code Online (Sandbox Code Playgroud)

更新:您可能还需要在禁用WOW重定向之前检查操作系统版本,因为早期版本的XP(我相信的Pre SP2)不会公开这些方法.

更新2:添加了64位操作系统检查.所有64位版本的操作系统都实现了这些方法,如果在64位操作系统上运行,则只需要禁用状态.