[Top][All Lists]

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: vms argv[0] and exit status fixes.

From: h.becker
Subject: Re: vms argv[0] and exit status fixes.
Date: Tue, 25 Mar 2014 16:48:39 +0100
User-agent: Mozilla/5.0 (X11; Linux i686; rv:17.0) Gecko/20130519 Icedove/17.0.5

On 03/25/2014 01:47 PM, John E. Malmberg wrote:
> On 3/24/2014 3:07 PM, h.becker wrote:
>> There are several problems with the checked-in old exit handling, which
>> aren't resolved by the recently suggested new code.
>> Old problems are:
>> - the %NONAME-?-NOMSG messages, which are generated by VMS when a
>> program returns a Unix style exit code; an exit code 2 shows as
>> %NONAME-E-NOMSG, Message number 00000002.
>> - VMS style warnings do not stop make.
>> New problems are:
>> - redirecting exit (and _exit, which seems wrong) to vms_exit, where the
>> passed exit code is adjusted, doesn't really know whether this is a make
>> exit code or one passed from an action routine, which can be of any style
>> - in case of an error there are error numbers printed by make, with the
>> adjusted exit codes, these numbers are no longer obvious.
> That is because the conversion is not complete, only the parent handling
> has been fixed, not the child status.

Can this code determine which style the exit code is? Or, should the
child exit code be converted as well?

> Documented Make exit codes are 0, 1, 2 and VMS style exit codes are 0
> for success, and VMS style failure codes start at 8 for Access violation.

SS$_NORMAL is 1 and an exit code 0 from whatever lib$spawn executed it
converted to 1, so, yes, 0 is a kind of VMS style success exit code.

As far as I know, documented Unix style exit codes are 0-255.

> The CRTL decc$exit() and decc$_exit() are already doing a translation of
> exit code 0 to be SS$_NORMAL.

That makes it difficult to distinguish between a Unix success and Unix
failure with 1, but ...

> So 0 is passed through to decc$exit, and codes 1 through 7 need to be
> encoded as POSIX exit codes.

The make exit codes need to be encoded as VMS style posix compatible
exit codes. Anything else should already be VMS style exit codes.
#define makes that simple.

> And after looking at how MAKE_TROUBLE works, as you had it, it does need
> to have an ERROR severity level.  A warning status should stop the make,
> but since the target actually got created, re-running make should
> continue.  Since MAKE_TROUBLE is returned when a target is not created,
> re-running the make should result in a failure again.

On warning,

$ ty nosuchfile.mf
        @ delete nosuchfile.;
        @ show time
$ make -f nosuchfile.mf
%DELETE-W-SEARCHFAIL, error searching for USR_ODS5:[USER.make]nosuchfile.;
-RMS-E-FNF, file not found
  25-MAR-2014 10:58:18

The old make didn't stop; with my changes it does:

$ mcr [.make]mcr -f nosuchfile.mf
%DELETE-W-SEARCHFAIL, error searching for USR_ODS5:[USER.make]nosuchfile.;
-RMS-E-FNF, file not found
nosuchfile.mf:2: recipe for target 'all' failed
make: *** [all] Error 0x10931238
$ sh symb $status
  $STATUS == "%X10931238"

> I am now able to run the complete test suite, and while not everything
> passes, I can now see the impact of using the POSIX encoding is, and
> where more adjustments are needed.
> For programs that never see VMS status codes, the _POSIX_EXIT macro
> definition fixes almost everything.  But we can not use it on GNU make
> because we need the VMS exit codes and want the VMS severity codes for
> backwards compatibility.

That's what I said, for GNU make it is a assumed that every action
routine returns VMS style exit codes. Home grown action routines which
differ, will not always work. The important action routines are the
compilers, the linker, etc.

>> It seems that having VMS specific codes for MAKE_SUCCESS, MAKE_TROUBLE
>> and MAKE_FAILURE is the way to go. Easy, as long as these codes
>> are always used. But there are hard coded numbers 0, 1 and 2 as well as
>> EXIT_FAILURE, passed to die() and/or exit().
> That may introduce other problems if Make or a child is using the hard
> coded number instead of the symbol.

For make and VMS I changed all occurences of 0, 1, 2, and EXIT_FAILURE
to the MAKE_mumble symbols. If the child runs make, then there is no
problem. Anything else is not under the control of make, so anything can
happen, even an $ EXIT command with a hard coded number. Why should make
change that to a posix compatible exit code?

> It is safer to have the exit() do the encoding, and that is more
> transparent to majority of the maintainers to make.
> The less VMS specific code they have to work around, the better.  And
> the less chance that they may break something VMS specific by accident.

Using #define results in less code.

>> So I suggest to always use the MAKE_mumble macros and to define them for
>> VMS as posix compatible exit codes. This avoids redirecting exit to
>> vms_exit; this assumes that the exit status of a child process is VMS
>> style, which makes checking for failure simpler; this allows to decode
>> and print the known make error numbers.
> If we were compiling /DEFINE=_POSIX_EXIT, then all this happens
> magically, except then we can not set the VMS severity bits.

Maybe I'm doing something stupid, but I do not like this magic:
$ ty ex.c
#include <stdlib.h>
main () {exit (0x10931238);}
$ cc ex
$ link ex
$ r ex
$ show symbol $status
  $STATUS == "%X10931238"
$ cc ex/main=pos
$ link ex
$ r ex
$ show symbol $status
  $STATUS == "%X0035A1C1"
$ write sys$output f$message(%X10931238)
%DELETE-W-SEARCHFAIL, error searching for !AS
$ write sys$output f$message(%X0035A1C1)
%C-S-NOMSG, Message number 0035A1C1

>> But it doesn't solve everything. The usual action routines will be VMS
>> utilities which set the VMS style exit codes. Any program which adheres
>> to the VMS style exit codes will work as an action routine as well. That
>> includes all programs which make use of the posix compatible exit codes
>> as well.
>> Action routines, which just return a Unix style number, would need
>> different checks. Although it seems simple to check for zero (when there
>> is no VMS facility code set), it turns out that the child processes, as
>> they are implemented today, never ever return zero. This way it is not
>> possible to find out whether it was successful or not.
> That is already being handled in the lib$spawn.  lib$spawn is returning
> the VMS status in a VMS specific variable, so the VMS status which
> includes POSIX encoded status.

No problem, except, as mentioned before, lib$spawn converts an exit code
0 to 1:
$ exit 0
%NONAME-W-NOMSG, Message number 00000000
$ sh symb $status
  $STATUS == "%X00000000"
$ spawn exit 0
%DCL-S-SPAWNED, process USER_59285 spawned
%DCL-S-ATTACHED, terminal now attached to process USER_59285
%NONAME-W-NOMSG, Message number 00000000
%DCL-S-RETURNED, control returned to process USER
$ sh symb $status
  $STATUS == "%X00000001"
> There is some extra handling needed in the VMS specific code around
> LIB$SPAWN to decode the POSIX status back to the original UNIX code.
> That will make the numbers reported by Make look like they should.  Once
> that is done, then the original UNIX constants for MAKE_<mumble> will
> match the output.

As far as I can see no code checks for a status to be MAKE_<mumble>.
It's "nice" to present Make error numbers.  And that's what I have in my
current version ...
$ ty ex.mf
all: ; exit %x1035A1C2
$ make -f ex.mf
exit %x1035A1C2
ex.mf:1: recipe for target 'all' failed
make.exe;2: *** [all] Error 0x1035a1c2
$ mcr [.make]mcr -f ex.mf
exit %x1035A1C2
ex.mf:1: recipe for target 'all' failed
make: *** [all] Error 56

> The only case that is problematic to handle is when a child utility
> ported from Unix using UNIX exit codes is not compiled with
> /DEFINE=_POSIX_EXIT/MAIN=POSIX_EXIT.  In that case, 0 and 1 are both
> treated as 1, and the rest of the numbers get passed through.

Where POSIX_EXIT doesn't really matter as long as lib$spawn is used to
run the action commands.

reply via email to

[Prev in Thread] Current Thread [Next in Thread]