C# WPF アプリからコンソール アプリケーションを起動し、その stdin と stdout をリダイレクトするという興味深い (読む: イライラする) 問題があります。
それはほとんど稼働していますが、標準入力のリダイレクトを開始するとすぐに、標準出力から一部のデータを取得できなくなったようです。
例を挙げて説明します。STARTUPINFO 構造体で hStdInput を設定しない場合、子プロセスを開始すると、次のメッセージが表示されます。
MongoDB shell version: 2.2.0
connecting to: test
local:PRIMARY>
ただし、hStdInput を設定すると、次のようになります。
MongoDB shell version: 2.2.0
connecting to: test
stdin でプロセスに何かを送信すると、それに応じて応答するため、BackgroundWorker 処理 stdout がまだ機能していることはわかっています。
use TestDB
switched to db TestDB
だから、これは私がプロセスを作成する方法です:
_processInfo = new ProcessInfo();
bool ok = false;
SECURITY_ATTRIBUTES sattr = new SECURITY_ATTRIBUTES();
sattr.bInheritHandle = 1;
unsafe
{
sattr.lpSecurityDescriptor = null;
}
sattr.nLength = Marshal.SizeOf(sattr);
IntPtr hWrite;
ok = CreatePipe(out _hReadStdOut, out hWrite, ref sattr, 0);
ok = SetHandleInformation(_hReadStdOut, HANDLE_FLAGS.INHERIT, 0);
IntPtr hRead;
ok = CreatePipe(out hRead, out _hWriteStdIn, ref sattr, 0);
ok = SetHandleInformation(_hWriteStdIn, HANDLE_FLAGS.INHERIT, 0);
var startInfo = new StartupInfo
{
dwFlags = 0x0001 | 0x0100,
wShowWindow = 0,
hStdOutput = hWrite,
hStdError = hWrite,
hStdInput = hRead // If this is IntPtr.Zero, I get everything from stdout
};
SECURITY_ATTRIBUTES pSec = new SECURITY_ATTRIBUTES();
pSec.nLength = Marshal.SizeOf(pSec);
SECURITY_ATTRIBUTES tSec = new SECURITY_ATTRIBUTES();
tSec.nLength = Marshal.SizeOf(tSec);
unsafe
{
ok = CreateProcess(
null,
pathToExeAndArgs,
ref pSec,
ref tSec,
true,
0,
IntPtr.Zero,
null,
ref startInfo,
out _processInfo);
}
次のようにパイプを読み取る DoWork の標準出力を処理する BackgroundWorker があります。
success = ReadFile(
_hReadStdOut,
bufPtr,
1024,
&read,
IntPtr.Zero);
コンソール アプリケーションが改行を送信するまで stdout からデータを取得しなかったため、.Net Process クラスを使用していないため、その場合もプロンプトが返されませんでした。
これに関するヘルプは大歓迎です。
乾杯。