powershell与Windows服务环境中的凭据一起使用时,启动 - 处理退出代码-1073741502

时间:2015-06-19 15:33:34

标签: powershell credentials start-process

我使用PowerShell Start-Process调用遇到了一个奇怪的行为。

这是电话:

$process = start-process `
    "C:\somepath\MyBinary.exe" `
    -PassThru `
    -Credential $defaultCredential `
    -Wait `
    -WorkingDirectory  "C:\somepath" `
    -LoadUserProfile
if ($process.ExitCode -ne 0)
{
#do something
}

此调用始终返回退出代码 - 1073741502 快速搜索后,当程序无法加载其所需的dll(aka。STATUS_DLL_INIT_FAILED)时,此退出代码似乎与一般错误有关。

当我在没有-Credential $credential的情况下运行程序时,程序运行正常。

为了隔离问题,我在带有目标凭据的提示中手动启动了some.exe,并且运行顺利。

所以问题似乎只来自start-process cmdlet有效启动进程的方式。

我找到了一些针对此问题的潜在解决方案,我尝试申请但没有运气:linklink

你知道这里发生了什么吗?

编辑1:
我直接或通过powershell脚本启动监视程序活动的proc mon。加载kernelbase.dll时似乎会出现问题。

本地procmon转储(工作):

9:06:35.3837439 AM  MyBinary.exe    2620    Load Image  C:\Windows\SysWOW64\kernelbase.dll  SUCCESS Image Base: 0x76270000, Image Size: 0x47000
9:06:35.4317417 AM  MyBinary.exe    2620    RegOpenKey  HKLM\System\CurrentControlSet\Control\Nls\Sorting\Versions  REPARSE Desired Access: Read
9:06:35.4317751 AM  MyBinary.exe    2620    RegOpenKey  HKLM\System\CurrentControlSet\Control\Nls\Sorting\Versions  SUCCESS Desired Access: Read
9:06:35.4318016 AM  MyBinary.exe    2620    RegSetInfoKey   HKLM\System\CurrentControlSet\Control\Nls\Sorting\Versions  SUCCESS KeySetInformationClass: KeySetHandleTagsInformation, Length: 0
9:06:35.4318152 AM  MyBinary.exe    2620    RegQueryValue   HKLM\System\CurrentControlSet\Control\Nls\Sorting\Versions\(Default)    SUCCESS Type: REG_SZ, Length: 36, Data: 00060101.00060101
...

Powershell procmon(失败,请参阅线程退出,并处理退出代码 - 1073741502):

9:35:07.9455191 AM  MyBinary.exe    2276    Load Image  C:\Windows\SysWOW64\kernelbase.dll  SUCCESS Image Base: 0x76270000, Image Size: 0x47000
9:35:07.9537146 AM  MyBinary.exe    2276    Thread Exit     SUCCESS Thread ID: 5112, User Time: 0.0000000, Kernel Time: 0.0000000
9:35:07.9537386 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\System32\apisetschema.dll    SUCCESS Name: \Windows\System32\apisetschema.dll
9:35:07.9537686 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\somepath\MyBinary\MyBinary.exe   SUCCESS Name: \somepath\MyBinary\MyBinary.exe
9:35:07.9537914 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\System32\wow64cpu.dll    SUCCESS Name: \Windows\System32\wow64cpu.dll
9:35:07.9538134 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\System32\wow64win.dll    SUCCESS Name: \Windows\System32\wow64win.dll
9:35:07.9538349 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\System32\wow64.dll   SUCCESS Name: \Windows\System32\wow64.dll
9:35:07.9538579 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\System32\ntdll.dll   SUCCESS Name: \Windows\System32\ntdll.dll
9:35:07.9538796 AM  MyBinary.exe    2276    QueryNameInformationFile    C:\Windows\SysWOW64\ntdll.dll   SUCCESS Name: \Windows\SysWOW64\ntdll.dll
9:35:07.9539425 AM  MyBinary.exe    2276    Process Exit        SUCCESS Exit Status: -1073741502, User Time: 0.0000000 seconds, Kernel Time: 0.0000000 seconds, Private Bytes: 339,968, Peak Private Bytes: 401,408, Working Set: 1,523,712, Peak Working Set: 1,826,816

编辑2:
我应该提到powershell脚本是从服务运行的(它是一个竹子服务代理)。我刚发现这个thread说:

  

Process.Start在内部调用CreateProcessWithLogonW(CPLW)   凭证已指定。无法调用CreateProcessWithLogonW   来自Windows服务环境(例如IIS WCF服务)。它   只能从交互式进程(应用程序)中调用   由通过CTRL-ALT-DELETE登录的用户启动。

我的猜测是,PowerShell启动过程调用正在使用CreateProcessWithLogonW ...

编辑3:
我的服务是使用自定义用户运行的(因为我无法模拟系统),因此请阅读link。我测试了确保"允许服务与桌面交互"已启用。由于它仅适用于非自定义帐户,因此我通过更改HKLM\System\CurrentControlSet\Services\%myservice%类型键(如herehere所述)在注册表上手动设置。

3 个答案:

答案 0 :(得分:6)

start-process是一个'别名'对于System.Diagnostics.Process.Start(),是的,它确实使用了CreateProcessWithLogonW()。如上所述,这种方法无法从服务流程中调用,只能通过“交互式”来调用。处理。警告只有"只有"是您发现的那个 - 当您没有更改凭据时,它至少可以启动该流程。 (这实际上甚至可能是一个错误 - 我与之谈过这个问题的微软支持工程师是#34;感到惊讶"它起作用了。)

从服务进程内启动另一个进程的唯一(支持)方法是使用本机Win32 API方法CreateProcessAsUser()。如何执行此操作的示例是{#3}}中的C#.NET可以在编辑#2中提到的问题中找到。

Windows进程必须作为用户会话的一部分启动。如果启动过程作为交互式会话的一部分运行 - 您使用CTRL + ALT + DELETE登录并打开桌面的类型 - 那么您可以使用CreateProcessWithLogonW(),它将自动使用您当前的用户会话。如果启动过程是服务,或者#34;批次"进程(如计划任务所示),然后启动过程必须创建一个新的用户会话(或识别现有的用户会话)以启动新进程(这是上述答案中的代码所做的。)

答案 1 :(得分:0)

到目前为止,我找到的唯一解决方案是禁用UAC(将EnableLUA设置为0 =本地安全策略中的管理员批准模式)。因此,它肯定是一个文件/文件夹/注册表访问问题,UAC在禁用时会忽略。

答案 2 :(得分:0)

在类似问题上有Microsoft KB 2701373可用的修补程序。帮我解决了这个问题。