开发者

About stdout/stderr redirections

I wrote a code to get a runtime error intentionally:

int main()
{
 int a=5;
 printf("Hello World\n");
 printf("a=%s\n", a);
}

It gives:

$ ./error.o
Hello World
Segmentation Fault
$

Now, to record the runtime errors, I do:

$ ./error.o > so.txt
$ ./error.o &> soe.txt

But both the files are empty. Why?

EDIT:

I'm actual开发者_开发知识库ly writing a script for remote compilation and execution of a c program. From the answers I get that Segmentation Fault is not the program's error output. So, is there a way to capture that output? Also, the program is just a sample, so I can't add the statements. Can line-buffering be done any other way with redirections?


so.txt is empty because stdout didn't get flushed before the crash so the buffered content was lost. If you add: fflush(stdout); between the printf-commands, it will contain the expected text.

Your soe.txt is missing also the the message "Segmentation Fault" because it was printed by the shell, not by your program and thus wasn't part of your program's output that was to be redirected.

If you can't modify the code, you can turn on line buffering by fooling the program to think it's printing to a tty. Create the script error.sh:

#!/bin/sh
./error.o

Then do chmod a+x error.sh and call it like this on Linux:

script soe.txt -c ./error.sh

Or like this on OS X:

script soe.txt ./error.sh

The exact output is somewhat system-dependent but will probably contain both "Hello World" and "Segmentation Fault".

Also consider adding appropriate #include lines and returning a value from main.


Because a segmentation fault is serious. Buffers don't get flushed, your process just gets shut down violently.

The reason you see the text when you run without redirection is that standard output is line buffered (ISO C mandates that full buffering is used only if the device can be determined not to be an interactive one). In other words, it will flush whenever it sees a newline, and that happens before your invalid de-referencing.

But because the file output is not line-buffered, the information is still waiting to be sent out when your program's universe is yanked out from under it.

Although support for this is implementation-defined, you can set a specific file handle to be line buffered by using setvbuf with the _IOLBF mode, something like:

setvbuf (stdout, NULL, _IOLBF, BUFSIZ);

at the start of main() - it saves a substantial amount of typing over having to fflush every output line.


I think this should do it:

echo ./error.o | sh > error.txt
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜