我一直在努力解决 Chris Iverson was having in this other Stackoverflow question 的问题。

我想以编程方式启动 SFC( 系统文件检查器 工具)。

它适用于 Windows XP:

private void RunSfc()
{
    ProcessStartInfo startInfo = new ProcessStartInfo("cmd", "/K sfc.exe /scannow");
    System.Diagnostics.Process.Start(startInfo);
}

在 Windows XP 下运行的其他变体:
//Launch SFC directly
ProcessStartInfo startInfo = new ProcessStartInfo("sfc.exe", "/scannow");
System.Diagnostics.Process.Start(startInfo);

//Use full path to SFC
String sfcPath = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.System), "sfc.exe");
ProcessStartInfo startInfo = new ProcessStartInfo(sfcPath, "/scannow");

相同的代码在 Windows 7 上失败(以管理员身份运行启动程序)。控制台窗口出现,但 SFC 给出错误:
Windows Resource Protection could not start the repair service.

但是,如果我从 单独的 提升的命令提示符手动运行 sfc /scannow,它会起作用:

因此,Windows Vista/7/8 显然发生了一些奇怪的事情。我不知道是什么,确切地说。但这可能与 UAC、UIPI、 session 0 隔离或 console windows were run by CSRSS 的事实有关

但是,我仍然不明白这个问题。

如果我想做他所做的事情,那么解决克里斯的问题会很好。

请记住 :我的代码已经以管理员身份运行。我右键单击 以管理员身份启动 :

这并不意味着问题不是与 UAC 相关的其他一些微妙问题,但这不是因为我以标准用户身份运行。

WinForms 应用程序中的代码
private void button1_Click(object sender, EventArgs e)
{
    RunSfc();
}

32 位失败

原来有一个 32 位版本的 cmd.exe 和一个 32 位版本的 sfc.exe :
  • C:\Windows\SysWOW64\cmd.exe
  • C:\Windows\SysWOW64\sfc.exe

  • 如果您运行提升的 32 位 cmd ,则 sfc 的 32 位和 64 位版本都不起作用。

    所以难题变成了如何从 32 位进程启动 64 位 cmd.exe。这可能意味着难题变成了如何 从 32 位进程中找到 cmd.exe 的 64 位版本,给定:
  • 你可能不在 64 位机器上
  • 您可能已经在运行 64 位进程
  • Windows 喜欢根据进程的位数来伪造 System32 文件夹的名称
  • 最佳答案

    我的实验表明该问题与 WOW64 模拟器有关。我在非提升的 WinForms 应用程序中有此代码:

    ...
    using System.Diagnostics;
    ...
    
    ProcessStartInfo startInfo = new ProcessStartInfo("cmd", "/K sfc.exe /scannow");
      startInfo.UseShellExecute = true;
      startInfo.Verb = "runas";
    Process.Start(startInfo);
    

    在 32 位 WOW64 进程中,此操作失败并在控制台窗口中显示以下消息:



    从 64 位进程来看,上面的代码成功了。

    事实上,我认为 .net 或 WinForms 在这里根本不相关。如果我从 SysWOW64 文件夹运行 32 位 cmd.exe,然后调用 sfc,我会遇到失败。但是我在 64 位 cmd.exe 上成功了。

    甚至根本不需要将 cmd.exe 带入其中。从一个 64 位进程,在没有提升的情况下运行,以下成功:
    ...
    using System.Diagnostics;
    ...
    
    ProcessStartInfo startInfo = new ProcessStartInfo("sfc.exe", "/scannow");
    startInfo.UseShellExecute = true;
    startInfo.Verb = "runas";
    Process.Start(startInfo);
    

    所以我想你的问题的解决方案将涉及将你的主程序切换到 64 位(可能有点激烈),或者将 64 位进程拼接到链中,以便可以运行 64 位 sfc

    关于c# - 如何在 Windows Vista/7/8 上以编程方式启动 SFC?,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/20871514/

    10-12 12:49
    查看更多