Home > Archive > PERL Miscellaneous > October 2004 > system return value makes for strange logic
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 |
system return value makes for strange logic
|
|
|
| I was writing a short script to create a mysql database and kept getting
confusing results:
system("mysqladmin --user='$user' --password='$pass' create $db")
or die "$db not created due to error\n";
The function lead to die being called and printing the error message but the
database was being created successfully. I changed it to:
system("mysqladmin --user='$user' --password='$pass' create $db")
and die "$db not created due to error\n";
and even though it doesn't look right at first glance, it makes sense
because system apparently returns 0 with success and numbers > 0 for
failure. I read about it in 'Programming Perl' and saw the explanation
that the return value gives information about the nature of the failure.
Isn't this strange? Don't we normally look to $! for errors and consider 0
to mean failure? I can accept it, but 'do and die' sounds funny compared
to the usual 'do or die'.
wana
| |
| Chris Cole 2004-10-29, 3:57 pm |
| On Fri, 29 Oct 2004 11:25:35 -0400, wana wrote:
> I was writing a short script to create a mysql database and kept getting
> confusing results:
>
> system("mysqladmin --user='$user' --password='$pass' create $db")
> or die "$db not created due to error\n";
>
> The function lead to die being called and printing the error message but the
> database was being created successfully. I changed it to:
>
> system("mysqladmin --user='$user' --password='$pass' create $db")
> and die "$db not created due to error\n";
>
> and even though it doesn't look right at first glance, it makes sense
> because system apparently returns 0 with success and numbers > 0 for
> failure. I read about it in 'Programming Perl' and saw the explanation
> that the return value gives information about the nature of the failure.
> Isn't this strange? Don't we normally look to $! for errors and consider 0
> to mean failure? I can accept it, but 'do and die' sounds funny compared
> to the usual 'do or die'.
>
Try this for a more sensible format:
system("mysqladmin --user='$user' --password='$pass' create $db") == 0 or
die "$db not created due to error\n";
BTW why aren't you using perl DBI? That will give you more control over
errors and the like.
Chris.
| |
|
|
> Try this for a more sensible format:
>
> system("mysqladmin --user='$user' --password='$pass' create $db") == 0 or
> die "$db not created due to error\n";
>
> BTW why aren't you using perl DBI? That will give you more control over
> errors and the like.
> Chris.
I didn't realize you could create a database with DBI. I'll have to read up
on it more. I actually use DBI with CGI and MySQL a lot but I thought you
had to create the database first and specify it for DBI->connect. Thanks
for the suggestions. I like your == 0 or alternative.
wana
| |
| Eric Bohlman 2004-10-29, 3:57 pm |
| wana <ioneabu@yahoo.com> wrote in
news:10o4odkcq2dgm01@news.supernews.com:
> and even though it doesn't look right at first glance, it makes sense
> because system apparently returns 0 with success and numbers > 0 for
> failure. I read about it in 'Programming Perl' and saw the
> explanation that the return value gives information about the nature
> of the failure. Isn't this strange? Don't we normally look to $! for
> errors and consider 0 to mean failure? I can accept it, but 'do and
> die' sounds funny compared to the usual 'do or die'.
The reason is that system() returns the exit status of the program it runs.
What that status is is under the program's control, not perl's. The
convention (which again has nothing to do with Perl) is that a program
exits with 0 on success and any number of non-zero values upon failure.
Why? Because there's only one way a program can succeed, but quite a few
ways it can fail (the number of such ways varying from program to program)
and it's helpful if it can signal *why* it failed.
| |
| Arndt Jonasson 2004-10-29, 3:57 pm |
|
Eric Bohlman <ebohlman@omsdev.com> writes:
> wana <ioneabu@yahoo.com> wrote in
> news:10o4odkcq2dgm01@news.supernews.com:
>
>
> The reason is that system() returns the exit status of the program it runs.
> What that status is is under the program's control, not perl's. The
> convention (which again has nothing to do with Perl) is that a program
> exits with 0 on success and any number of non-zero values upon failure.
> Why? Because there's only one way a program can succeed, but quite a few
> ways it can fail (the number of such ways varying from program to program)
> and it's helpful if it can signal *why* it failed.
The history of that convention has mainly to do with Unix. I think VMS
is one system that treats return status from processes differently. At
least the C standard committee found it necessary to invent
preprocessor symbols for denoting successful and failing process exit,
since 0 for success was not universal.
Since I'm on the subject: it often happens in Perl code that people
take the return value from 'system', divide it by 256, and think they
have the exit status. They have that, if the process didn't dump core
(if we're on a Unix system). If it dumped core, the lowest bits are
nonzero. Thus, a program crash may be misinterpreted as successful
exit. The doc for 'system' does say this, but it may be easy to forget.
| |
| David Gale 2004-10-29, 3:57 pm |
| Quoth Arndt Jonasson <do-not-use@invalid.net>:
> Since I'm on the subject: it often happens in Perl code that people
> take the return value from 'system', divide it by 256, and think they
> have the exit status. They have that, if the process didn't dump core
> (if we're on a Unix system). If it dumped core, the lowest bits are
> nonzero. Thus, a program crash may be misinterpreted as successful
> exit. The doc for 'system' does say this, but it may be easy to
> forget.
Actually, they lose more than just whether or not it dumped core. If it was
interrupted by *any* signal, that goes in the lower bits.
Try:
perl -e 'print system("sleep 30")."\n";'
and hit Ctl-C while it's sleeping.
| |
| Abigail 2004-10-29, 8:56 pm |
| Eric Bohlman (ebohlman@omsdev.com) wrote on MMMMLXXVII September MCMXCIII
in < URL:news:Xns9591729577743ebohlmanomsdevc
om@130.133.1.4>:
%% wana <ioneabu@yahoo.com> wrote in
%% news:10o4odkcq2dgm01@news.supernews.com:
%%
%% > and even though it doesn't look right at first glance, it makes sense
%% > because system apparently returns 0 with success and numbers > 0 for
%% > failure. I read about it in 'Programming Perl' and saw the
%% > explanation that the return value gives information about the nature
%% > of the failure. Isn't this strange? Don't we normally look to $! for
%% > errors and consider 0 to mean failure? I can accept it, but 'do and
%% > die' sounds funny compared to the usual 'do or die'.
%%
%% The reason is that system() returns the exit status of the program it runs.
%% What that status is is under the program's control, not perl's. The
%% convention (which again has nothing to do with Perl) is that a program
%% exits with 0 on success and any number of non-zero values upon failure.
%% Why? Because there's only one way a program can succeed, but quite a few
%% ways it can fail (the number of such ways varying from program to program)
%% and it's helpful if it can signal *why* it failed.
Hindsight is 20/20 of course, but it there would have been some other
options. First, there's not really a reason the return value of system
should indicate the reason why - open doesn't use its return value to
indicate the reason for failure either. Instead, $! is set. And a system
that fails sets $? already, which gives the same information. I cannot
recall I ever used the return value of system other than for its boolean
value - if I want to know the reason, I always use $?. system could also
have returned a magical value, that in boolean context returned false on
a failure, and true on success, but in numerical context, it just acts
as $? now.
Abigail
--
perl -swleprint -- -_='Just another Perl Hacker'
| |
| Jürgen Exner 2004-10-30, 3:55 am |
| wana wrote:
> system("mysqladmin --user='$user' --password='$pass' create $db")
> or die "$db not created due to error\n";
>
> The function lead to die being called and printing the error message
> but the database was being created successfully. I changed it to:
>
> system("mysqladmin --user='$user' --password='$pass' create $db")
> and die "$db not created due to error\n";
>
> and even though it doesn't look right at first glance, it makes sense
> because system apparently returns 0 with success and numbers > 0 for
> failure.
Why don't you just check the documentation for the functions you are using?
It's explained right there in the third paragraph of "perldoc -f system".
jue
|
|
|
|
|