获得有效的可执行文件

时间:2010-08-24 23:37:43

标签: c# windows-7 64-bit filesystems redirect

.NET应用程序(托管)在Windows 7 64位上运行。它实际上是在64位环境中运行。

应用程序检查位于 c:\ windows \ syswow64 \ calc.exe 中的运行进程(例如,calc.exe)。

那么,为什么功能

Process.MainModule.Filename

返回 c:\ windows \ system32 \ calc.exe ?从SYSWOW64目录中未重定向时,是否可以获得有效的可执行主模块位置?


有哪些可行的解决方法?我写的最快的是以下片段:

bool iWindows = pFilename.StartsWith(@"c:\windows\", StringComparison.InvariantCultureIgnoreCase);
bool iWindowsSystem32 = pFilename.StartsWith(@"c:\windows\system32\", StringComparison.InvariantCultureIgnoreCase);

if ((iWindows == true) || (iWindowsSystem32 == true)) {
    string pActualFileName;

    if (iWindowsSystem32 == true)
        pActualFileName = pFilename.Replace(@"c:\windows\system32\", @"c:\windows\syswow64\");
    else
        pActualFileName = pFilename.Replace(@"c:\windows\", @"c:\windows\syswow64\");

我错过了什么吗?

2 个答案:

答案 0 :(得分:0)

尝试在使用Process.MainModule.Filename之前致电Wow64DisableWow64FsRedirection。建议在使用IsWow64Process之前使用Environment.Is64BitOperatingSystemWow64DisableWow64FsRedirection(如果使用.NET 4.0)在64位操作系统上运行程序。

更新:我确定您的代码中有一个小错误,或者问题可能出在您已安装的.NET版本上。我根据以下测试代码测试了您的问题

using System;
using System.Diagnostics;

namespace Win64ProcesPath {
    class Program {
        static void Main (string[] args) {
            Process myProcess = new Process ();

            try {
                myProcess.StartInfo.UseShellExecute = false;
                myProcess.StartInfo.FileName = "calc.exe";
                myProcess.StartInfo.CreateNoWindow = true;
                myProcess.Start ();
                System.Threading.Thread.Sleep (1000);
                Console.WriteLine ("{0}", myProcess.MainModule.FileName);

                Process p = Process.GetProcessById (myProcess.Id);
                Console.WriteLine ("{0}", p.MainModule.FileName);

                //Process p32 = Process.GetProcessById (8048);
                //Console.WriteLine ("{0}", p32.MainModule.FileName);
            }
            catch (Exception e) {
                Console.WriteLine (e.Message);
            }
        }
    }
}

在Vindows 7 64位(x64)上安装.NET 4.0和Visual Studio 2010。在Vindows 7 64位上有calc.exe的两个版本:C:\Windows\SysWOW64\calc.exe下的一个32位和C:\Windows\system32\calc.exe下的另一个64位。如何轻松验证文件具有不同的文件大小(776,192和918.528字节)。如果我将程序编译为64位程序,它将启动C:\Windows\system32\calc.exeProcess.GetProcessById(processId).MainModule.FileName也会显示正确的文件名。也可以使用Process.GetProcessById()来获取单独启动的32位版本calc.exe的正确路径(请参阅注释行)。因此,这个程序的64位版本在我的环境中没有任何问题。

如果您有32位应用程序,则可以在调用Wow64DisableWow64FsRedirection后访问完整的文件系统,但您能够访问64的内存-bit程序和Process.MainModule将使用代码System.ComponentModel.Win32ExceptionNativeErrorCode: 299抛出异常Message: "A 32 bit processes cannot access modules of a 64 bit process."为了能够获得64位应用程序的完整文件名,您应该使用API获得从64位操作系统组件(如WMI等)生成的结果。但它已经是另一个问题,因为你编写程序的方式是64位程序。

答案 1 :(得分:0)

尝试获取装配,然后获取装配位置,例如

System.Reflection.Assembly.GetExecutingAssembly().Location