我正在尝试创建一个在集中式设备上运行的小程序。这个程序将运行
"psexec server(s) netstat -na | findstr "LISTENING"
从远程节点收集netstat数据(应该将输出重定向到string),然后解析数据并与已知列表进行比较。我可以在cmd行运行上面的psexec
cmd而没有任何问题,但是当我尝试在c#程序中运行相同的命令作为进程时,没有返回要解析的数据。我可以看到netstat
正在运行(cmd窗口闪烁netstat结果),但进程。标准输出没有捕获流。如果我使用ping或几乎任何其他psexec
以外的参数,流被捕获,结果显示在我的文本框中。我还尝试将文件名设置为psexec.exe并指定参数,但我得到了相同的结果。最后但并非最不重要的一点是,如果我不带任何参数运行psexec,我将在文本框中获得返回的帮助反馈信息。这是真的,如果我运行psexec.exe
作为文件名,或者如果我运行cmd.exe
作为文件名,"/c psexec"指定为args
。
我只是想让psexec输出在本地执行时被捕获。稍后再考虑将psexec传输到远程机器的问题。如有任何帮助,我将不胜感激。
代码如下:
System.Diagnostics.Process pProcess = new System.Diagnostics.Process();
pProcess.StartInfo.FileName = "cmd.exe";
pProcess.StartInfo.Arguments = "/c psexec netstat";
pProcess.StartInfo.UseShellExecute = false;
pProcess.StartInfo.RedirectStandardOutput = true;
pProcess.Start();
string strOutput = pProcess.StandardOutput.ReadToEnd();
pProcess.WaitForExit();
if (pProcess.HasExited)
{
textBox1.Text = strOutput;
}
else
{
textBox1.Text = "TIMEOUT FAIL";
}
我建议还捕获标准错误输出,以防那里报告任何内容。
此外,如果您在64位操作系统上运行,则psexec的"位"和应用程序之间可能会断开连接。如果是这种情况,请更改项目的平台以匹配psexec的平台,而不是构建为Any CPU。
遇到了一些需要更改的地方,但是您关于捕获标准错误输出的建议非常正确,并且是一个良好的开端。结果是一些信息被发送到错误输出(即使真的不是错误,只是从psexec运行状态0),所以我知道在那一点psexec不只是吃所有的输出。一旦我开始尝试将远程主机作为参数传递,我就开始获得用户/传递错误数据。如果我想为过程运行提供凭据,还需要捕获标准输入。为远程执行器添加一些str文本和凭据,效果很好。谢谢你的帮助。下面是更新后的代码——
System.Diagnostics.Process pProcess = new System.Diagnostics.Process();
pProcess.StartInfo.Domain = "domain";
pProcess.StartInfo.UserName = "user with priv";
pProcess.StartInfo.Password = new System.Security.SecureString();
char [] pass = textBox3.Text.ToArray();
for (int x = 0; x < pass.Length; ++x)
{
pProcess.StartInfo.Password.AppendChar(pass[x]);
}
pProcess.StartInfo.FileName = @"psexec.exe";
pProcess.StartInfo.Arguments = @"\remoteHost netstat -ano";
pProcess.StartInfo.UseShellExecute = false;
pProcess.StartInfo.RedirectStandardInput = true;
pProcess.StartInfo.RedirectStandardOutput = true;
pProcess.StartInfo.RedirectStandardError = true;
pProcess.Start();
pProcess.WaitForExit(30000);
if (!pProcess.HasExited)
{
pProcess.Kill();
}
string strOutput = pProcess.StandardOutput.ReadToEnd();
string errOutput = pProcess.StandardError.ReadToEnd();
textBox1.Text = strOutput;
textBox2.Text = errOutput;