从32位应用程序打开64位regedit

Open 64 bit regedit from 32 bit application

本文关键字:64位 regedit 32位 应用程序      更新时间:2023-10-16

我正试图使用ShellExecute从我的32位应用程序中打开64位Regedit。

我在Process Explorer中注意到,如果我正常打开Regedit,它会显示图像为64位,但如果我使用ShellExecute从32位应用程序打开C:WindowsRegedit.exe,Process Explorer会显示图像是32位。

(它确实在Windows目录中打开regedit,而不是在SysWOW64中)

我发现,如果在调用ShellExecute之前使用Wow64DisableWow64FsRedirection函数,它会打开它的64位映像。但我的应用程序不会在32位XP上运行。

让我困惑的是,无论我以何种方式打开regedit,它们都位于C:Windows中,并且都是相同的可执行文件。同一个可执行文件怎么可能有两种不同的映像类型?如果没有Wow64DisableWow64FsRedirection,我如何打开64位的?

您需要检测您是否在使用Is64BitProcess的64位进程中,如果是,则访问指向"Real"System32文件夹的%windir%Sysnative,以便32位应用程序需要访问64位System32文件夹。

string system32Directory = Path.Combine(Environment.ExpandEnvironmentVariables("%windir%"), "system32");
if(Environment.Is64BitOperatingSystem && !Environment.Is64BitProcess)
{
    // For 32-bit processes on 64-bit systems, %windir%system32 folder
    // can only be accessed by specifying %windir%sysnative folder.
    system32Directory = Path.Combine(Environment.ExpandEnvironmentVariables("%windir%"), "sysnative");
}

这是我用来从32位应用程序启动64位regedit的代码:

    [DllImport("kernel32.dll", SetLastError = true)]
    [return: MarshalAs(UnmanagedType.Bool)]
    internal static extern bool Wow64DisableWow64FsRedirection(ref IntPtr ptr);
    [DllImport("kernel32.dll", SetLastError = true)]
    [return: MarshalAs(UnmanagedType.Bool)]
    internal static extern bool Wow64RevertWow64FsRedirection(IntPtr ptr);
    internal int ExecuteCommand64(string Command, string Parameters)
    {
        IntPtr ptr = new IntPtr();
        bool isWow64FsRedirectionDisabled = Wow64DisableWow64FsRedirection(ref ptr);
        if (isWow64FsRedirectionDisabled)
        {
            //Set up a ProcessStartInfo using your path to the executable (Command) and the command line arguments (Parameters).
            ProcessStartInfo ProcessInfo = new ProcessStartInfo(Command, Parameters);
            ProcessInfo.CreateNoWindow = true;
            ProcessInfo.UseShellExecute = false;
            ProcessInfo.RedirectStandardOutput = true;
            //Invoke the process.
            Process Process = Process.Start(ProcessInfo);
            Process.WaitForExit();
            //Finish.
            // this.Context.LogMessage(Process.StandardOutput.ReadToEnd());
            int ExitCode = Process.ExitCode;
            Process.Close();
            bool isWow64FsRedirectionOK = Wow64RevertWow64FsRedirection(ptr);
            if (!isWow64FsRedirectionOK)
            {
                throw new Exception("Le retour en 32 bits a échoué.");
            }
            return ExitCode;
        }
        else
        {
            throw new Exception("Impossible de passer en 64 bits");
        }
    }

我用下面的行来称呼它:

ExecuteCommand64(@"c:windowsregedit", string.Format(""{0}"", regFileName));

其中regFilename是我要添加到注册表中的注册表文件。