Windows控制台:
- 工具A可以将二进制数据写入文件,但是没有选择告诉它使用stdout的选项。
- 工具B可以从stdin读取二进制数据并处理其中的信息。
如何在不使用中间文件的情况下从A通过B获得输出?
换句话说:Windows等效于/dev/stdout
什么?
--jeroen
Windows控制台:
如何在不使用中间文件的情况下从A通过B获得输出?
换句话说:Windows等效于/dev/stdout
什么?
--jeroen
Answers:
Windows确实有一个/ dev / stdout的类似物,CON:
考虑到Microsoft正在进行的“旧版兼容性”计划,我认为它仍然可以工作。
啊..找到了。 Microsoft支持提供了保留名称的列表。您不能使用这些名称来命名文件,它们在用作输入或输出时具有特殊含义。
您可能可以将CON用作输出设备以发送到stdout。
名单:
Name Function
---- --------
CON Keyboard and display
PRN System list device, usually a parallel port
AUX Auxiliary device, usually a serial port
CLOCK$ System real-time clock
NUL Bit-bucket device
A:-Z: Drive letters
COM1 First serial communications port
LPT1 First parallel printer port
LPT2 Second parallel printer port
LPT3 Third parallel printer port
COM2 Second serial communications port
COM3 Third serial communications port
COM4 Fourth serial communications port
Unity.exe -batchmode -quit -projectPath "%cd%" -logFile CON -buildWindows64Player ".\GameBuild\Generic.exe"
。没有日志文件,命令运行正常,但没有生成输出。
program > file.txt
),也不能在管道中使用(将数据传递到)中的另一个程序的stdin中program | another_program
。写入CON的输出始终显示。正确的答案是“ Windows没有等效的/ dev / stdout”
Windows没有直接等效于/dev/stdout
。
这是我编写C#程序的尝试,该程序创建一个命名管道,可以将其作为文件名提供给程序A。需要.NET v4。
(C#是因为编译器随.NET运行时一起提供的,并且最近哪些计算机没有.NET?)
PipeServer.cs
using System;
using System.IO;
using System.IO.Pipes;
class PipeServer {
static int Main(string[] args) {
string usage = "Usage: PipeServer <name> <in | out>";
if (args.Length != 2) {
Console.WriteLine(usage);
return 1;
}
string name = args[0];
if (String.Compare(args[1], "in") == 0) {
Pipe(name, PipeDirection.In);
}
else if (String.Compare(args[1], "out") == 0) {
Pipe(name, PipeDirection.Out);
}
else {
Console.WriteLine(usage);
return 1;
}
return 0;
}
static void Pipe(string name, PipeDirection dir) {
NamedPipeServerStream pipe = new NamedPipeServerStream(name, dir, 1);
pipe.WaitForConnection();
try {
switch (dir) {
case PipeDirection.In:
pipe.CopyTo(Console.OpenStandardOutput());
break;
case PipeDirection.Out:
Console.OpenStandardInput().CopyTo(pipe);
break;
default:
Console.WriteLine("unsupported direction {0}", dir);
return;
}
} catch (IOException e) {
Console.WriteLine("error: {0}", e.Message);
}
}
}
编译:
csc PipeServer.cs /r:System.Core.dll
csc
可以在 %SystemRoot%\Microsoft.NET\Framework64\<version>\csc.exe
例如,在32位Windows XP上使用.NET Client Profile v4.0.30319:
"C:\WINDOWS\Microsoft.NET\Framework\v4.0.30319\csc.exe" PipeServer.cs /r:System.Core.dll
跑:
PipeServer foo in | programtwo
在第一个窗口中,然后:
programone \\.\pipe\foo
在第二个窗口中。
programone
什么pipe
,它可以完成\\.\pipe\foo
programone
完成数据输出后,它将仅关闭其使用的输出文件。(从客户端来看,管道的工作方式与普通文件相同。)这样做的话pipe.exe
-更准确地说pipe.CopyTo(...)
-将到达EOF并直接退出。
out
)方向上使用该工具(将stdin复制到管道中)时,在第一个1 kB之后它死于“ Broken pipe”错误。in
但是,将管道复制到stdout()时不会发生,因此不会影响您的程序。(正如他们所说,欢迎打补丁。)
基于grawity的答案,我创建了扩展版本,该版本允许无需使用多个终端窗口即可直接启动进程。
一般用法:
PipeServer [in|out] [process name] [argument 1] [argument 2] [...]
然后,将字符串“ {pipe}”替换为重定向路径。
真实示例:
PipeServer.exe in "C:\Keil\UV4\Uv4.exe" -b "C:\Project\Project.uvproj" -j0 -o "{pipe}"
例如,可以将该命令行直接插入Eclipse,以将某个外部构建器的构建日志重定向到StdOut。
这可能是最好的...
Unity.exe -batchmode -projectPath C:\***\Application -logFile -buildWebPlayer web -quit
。不带参数(文件名)的-logFile
-必须将输出打印到控制台,但不是。添加CON(即--logFile CON
)之后-: ))