启动应用程序,在c ++中捕获stdout和stderr [英] launch app, capture stdout and stderr in c++

查看:195
本文介绍了启动应用程序,在c ++中捕获stdout和stderr的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

如何启动应用程序并通过stdout和stderr捕获输出?

How do I launch an app and capture the output via stdout and maybe stderr?

我正在编写一个自动构建系统,我需要捕获输出以进行分析。我想更新svn repo并抓住修订版本号,所以我可以移动autobuild / revNumber /如果成功的文件。我也想建立使用make和上传编译文本到我的服务器为大家看到在失败的构建的警告和错误。

I am writing an automated build system and I need to capture the output to analyze. I'd like to update the svn repo and grab the revision number so I can move the files in autobuild/revNumber/ if successful. I also would like to build using make and upload the compile text to my server for everyone to see the warnings and errors on a failed build.

我找不到 system()函数,但是我在MSDN上找到了 CreateProcess()我能够发射我需要的,但我不知道如何捕获stderr和stdout。我注意到该进程单独启动,除非我设置一个断点,并保持我的应用程序退出,然后它将保持我的应用程序控制台窗口中的所有文本。我也想等待所有进程完成,然后扫描它产生的数据做任何额外的操作,我需要。

I can't find the system() function, but I found the CreateProcess() function on MSDN. I am able to launch what I need but I have no idea how to capture the stderr and stdout. I notice the process launches separately unless I set a breakpoint and keep my app exiting which it then will keep all the text in my app console window. I would also want to wait until all processes are finished and then scan the data it produced to do any additional operations I need. How do I do any of this?

推荐答案

在真实的shell中(意思是,不是海贝壳 - 或其衍生物),则:

In real shells (meaning, not sea shells - I mean, not in C Shell or its derivatives), then:

program arg1 arg2 >/tmp/log.file 2>&1

这将使用给定的参数运行程序,并将stdout重定向到/tmp/log.file;标记( hieroglyph )' 2>& 1 '将stderr(文件描述符2)发送到stdout描述符1)正在进行。注意,操作的顺序很重要;如果你反转它们,那么标准错误将转到标准输出的地方,然后标准输出(而不是标准错误)将被重定向到该文件。

This runs program with the given arguments, and redirects the stdout to /tmp/log.file; the notation (hieroglyph) '2>&1' at the end sends stderr (file descriptor 2) to the same place that stdout (file descriptor 1) is going. Note that the sequence of operations is important; if you reverse them, then standard error will go to where standard output was going, and then standard output (but not standard error) will be redirected to the file.

所显示的文件名的选择是多种多样的原因 - 您应该允许用户选择目录,并且可能应该在文件名中包括进程ID或时间戳。

The choice of file name shown is abysmal for numerous reasons - you should allow the user to choose the directory, and probably should include the process ID or time stamp in the file name.

LOG=${TMPDIR:-/tmp}/log.$$.$(date +%Y%m%d-%H%M%S)
program arg1 arg2 >$LOG 2>&1

在C ++中,可以使用 system()函数(继承自C)来运行进程。如果你需要知道C ++程序中的文件名(可能),然后在程序中生成名称( strftime()是你的朋友),并创建命令字符串该文件名。
(严格地说,您还需要 getenv()才能获得$ TMPDIR,并且POSIX函数 getpid()获取进程ID,然后可以模拟两行shell脚本(虽然PID使用的是C ++程序,而不是启动的shell)。

In C++, you can use the system() function (inherited from C) to run processes. If you need to know the file name in the C++ program (plausible), then generate the name in the program (strftime() is your friend) and create the command string with that file name. (Strictly, you also need getenv() to get $TMPDIR, and the POSIX function getpid() to get the process ID, and then you can simulate the two-line shell script (though the PID used would be of the C++ program, not the launched shell).

你可以使用POSIX popen()函数;你必须包括' 2>& 1 ''在您创建的命令字符串中的标记,以将命令的标准错误发送到与标准输出相同的位置,但不需要临时文件:

You could instead use the POSIX popen() function; you'd have to include the '2>&1' notation in the command string that you create to send the standard error of the command to the same place as standard output goes, but you would not need a temporary file:

FILE *pp = popen("program arg1 arg2 2>&1", "r");

然后你可以读取文件流。我不知道是否有一个干净的方式将C文件流映射到C ++ istream;可能是。

You can then read off the file stream. I'm not sure whether there's a clean way to map a C file stream into a C++ istream; there probably is.

这篇关于启动应用程序,在c ++中捕获stdout和stderr的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆