Wow64DisableWow64FsRedirection 在 32 位 Windows XP 上

Posted

技术标签:

【中文标题】Wow64DisableWow64FsRedirection 在 32 位 Windows XP 上【英文标题】:Wow64DisableWow64FsRedirection on 32-bit Windows XP 【发布时间】:2014-10-14 08:03:49 【问题描述】:

我正在使用 Visual Studio C++ 编写一个程序,该程序需要在运行 Windows XP 32 位或任何更高版本的 Windows 操作系统的任何计算机上作为 32 位进程本机运行。该程序需要能够访问计算机上的C:\Windows\system32\ 文件夹,无论该程序是在 64 位还是 32 位系统上运行。为此,我使用Wow64DisableWow64FsRedirection 禁用Windows 通常对32 位进程执行的重定向,将它们发送到C:\Windows\syswow64。不幸的是,这破坏了兼容性——虽然我的程序可以在 Server 2003 和 XP x64 版本上运行,但只要在 32 位 XP RTM 系统上运行,程序就会失败,给我这个错误:

[Program Name] - Entry Point Not Found
  The procedure entry point Wow64DisableWow64FsRedirection could not be located
  in the dynamic link library KERNEL32.dll.

由于系统是32位的,调用显然是多余的,但是我想不出办法在运行时判断系统是否是64位,因此是否跳过调用,无需添加另一个本身会破坏兼容性的调用,例如 IsWow64Process(),这需要 XP Service Pack 2。

tl;dr:如何在不使用任何在消费者 64 位 Windows 出现后引入的调用的情况下确定系统是 64 位还是 32 位。 p>

【问题讨论】:

GetProcAddress一样,然后测试函数是否存在? 测试是否存在 syswow64 目录?它显然不会出现在 32 位 Windows 上。 @Marc-b 这很聪明,但我不能保证用户不会创建一个。这很愚蠢,但用户可能很愚蠢。 这里有一堆想法:***.com/questions/7011071/… @dr_andonuts:您确实意识到在您的代码中包含 if (magic_is_64bit()) Wow64DisableWow64FsRedirection(); 不会阻止 Windows 尝试在 32 位系统上解析 Wow64DisableWow64FsRedirection 导入,对吧? 【参考方案1】:

继续使用Wow64DisableWow64FsRedirection,但不要静态导入它。而是使用动态绑定 (GetProcAddress) 或延迟加载,这两种方法都可以让您在不崩溃的情况下处理缺失的函数(或者更糟糕的是,甚至无法启动,这是当前的情况)。

而且不用担心系统位数。如果该函数存在,请调用它。

typedef BOOL WINAPI fntype_Wow64DisableWow64FsRedirection(PVOID *OldValue);
auto pfnWow64DisableWow64FsRedirection = (fntype_Wow64DisableWow64FsRedirection*)GetProcAddress(GetModuleHandleA("kernel32.dll"), "Wow64DisableWow64FsRedirection");

if (pfnWow64DisableWow64FsRedirection) 
   // function found, call it via pointer
   PVOID arg;
   (*pfnWow64DisableWow64FsRedirection)(&arg);

else 
   // function was missing

现在链接器将找不到名为 Wow64DisableWow64FsRedirection 的未解析符号,因此它不会将该函数放入导入表中,并且 Windows 不会在进程启动期间查找它。

【讨论】:

不幸的是,静态链接我的程序会导致其他一系列问题,因为我的程序使用 VC++ 运行时库,由于其他原因需要静态链接。 VC++ 中有没有办法保持静态链接,但在那个实例上强制动态链接? @dr_andonuts:我没有说要更改导入 C++ 运行时的方式。就这一项功能。不要直呼其名。而是从GetProcAddress 获取一个指针,并通过指针调用它。

以上是关于Wow64DisableWow64FsRedirection 在 32 位 Windows XP 上的主要内容,如果未能解决你的问题,请参考以下文章

32位系统上的Wow64:还原[重复]

32位程序关闭路径重定向

Windows学习解决python无法访问win64系统drivers目录重定向文件问题

WoW64子系统

如何从WOW64进程注入x86 DLL到x64进程

在 64 位和 32 位 (WOW64) 应用程序之间使用 WM_COPYDATA 是不是安全?