For Programmers: Free Programming Magazines  


Home > Archive > PERL Beginners > January 2007 > Capture Exit Code Using Pipe & Tee









You are viewing an archived Text-only version of the thread. To view this thread in it's original format and/or if you want to reply to this thread please [click here]

 

Author Capture Exit Code Using Pipe & Tee
mthayer@qualcomm.com

2007-01-31, 6:59 pm

I have a piece of code provided below. The code calls a make command,
and redirects STDOUT/STDERR to tee, which then sends it to the screen,
and also to a log file. The problem is that I'm trying to capture the
exit code for make. However, what happens when I run the command a cmd
process starts up, and calls make and tee as peers, so make exits
first, then tee, which returns the exit code of tee to cmd, and cmd
returns the exit code to the script. What I need is the exit code from
make, and not tee.


$command = "make -f <parameters>";
$command .= " 2>&1 | tee -a build.log";
system $command;
$exit_value = $? >> 8;
print "\nExit Value: $exit_value\n\n";


The exit value is always 0, because it's returning the tee value, and
not make.


Any and all help is very appreciated.

Paul Lalli

2007-01-31, 9:59 pm

On Jan 31, 3:45 pm, mtha...@qualcomm.com wrote:
> I have a piece of code provided below. The code calls a make command,
> and redirects STDOUT/STDERR to tee, which then sends it to the screen,
> and also to a log file. The problem is that I'm trying to capture the
> exit code for make. However, what happens when I run the command a cmd
> process starts up, and calls make and tee as peers, so make exits
> first, then tee, which returns the exit code of tee to cmd, and cmd
> returns the exit code to the script. What I need is the exit code from
> make, and not tee.
>
> $command = "make -f <parameters>";
> $command .= " 2>&1 | tee -a build.log";
> system $command;
> $exit_value = $? >> 8;
> print "\nExit Value: $exit_value\n\n";
>
> The exit value is always 0, because it's returning the tee value, and
> not make.
>
> Any and all help is very appreciated.


I would suggest taking the system's tee out of the equation, and doing
that part within Perl. That way you can access the actual process.
Consider the following example. I have one program that simply
generates five lines to STDERR and five to STDOUT. Then I write a
program that uses IO::Tee. It opens a pipe to this process
(redirecting its STDERR to its STDOUT). Then for every line read from
the pipe, it prints that line to a IO::Tee object that's multiplexing
to this program's STDOUT and another file called output.txt. Finally,
it prints the return value of the first program.


$ cat runme.pl
#!/usr/bin/env perl
use strict;
use warnings;
my $i = 0;
print "$i\n" and warn "Warning $i\n" until $i++ == 5;
exit 2;

$ perl -MIO::Tee -we'
open my $ph, q{-|}, q{runme.pl 2>&1} or die "Cannot open runme: $!";
open my $ofh, q{>}, q{output.txt} or die "Cannot open output: $!\n";
my $tee = IO::Tee->new($ofh, \*STDOUT);
while (<$ph> ) {
print $tee $_;
}
close $ph;
my $val = $? >> 8;
print "Exit status: $val\n";
'
Warning 1
Warning 2
Warning 3
Warning 4
Warning 5
1
2
3
4
5
Exit status: 2

$ cat output.txt
Warning 1
Warning 2
Warning 3
Warning 4
Warning 5
1
2
3
4
5


Hope that helps,
Paul Lalli

Sponsored Links







Also available: Server administration forum archive | Web Design forum archive | Software forum archive | Hardware reviews archive

Copyright 2008 codecomments.com