For Programmers: Free Programming Magazines  


Home > Archive > Cobol > January 2008 > How to get the return code from a Unix command in Cobol









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 How to get the return code from a Unix command in Cobol
Robert

2008-01-11, 9:56 pm

The problem: I want to run a Unix command, program or script from Cobol and get its return
code. For example, I want to test whether /usr/tmp is a valid directory. On a shell
command line, I can say 'test -d /usr/tmp' (or ksh shortcut [ -d /usr/tmp ]) followed by
'echo $?'. The result will be 0 if valid, 1 if invalid. When I say the same in a Cobol
program ..

call 'system' using 'test -d /usr/tmp'
if return-code not = zero
display '/usr/tmp is not a valid directory'
set fatal-error to true
end-if

... the return-code is alswya zero.

The solution:

call 'system' using 'test -d /usr/tmp; exit $?'

System() forks a child process, execs it to the default shell (usually sh), feeds it your
command line and waits for it to terminate. It is functionally the same as saying:
sh -c 'test -d /usr/tmp'
The sh shell is supposed to exit by default with the last return code ($?), and system()
is supposed to do the same. There is a bug in one of the two causing that to not work, but
it does work when your command does an explicit exit.

This question came up here two years ago, without a conclusive answer. I opined the return
code should be passed back, Richard thought it was fundamentally impossible for a child
process to pass anything back to its parent. This solution shows I was right.

A further complication is that the system() surrogate supplied Micro Focus Server Express
4.1 running on HP-UX shifts the return code left 8 bits. Thus,
call 'system' using 'exit 123'
returns 31,488, which is 123*256. The 1 returned by the above directory test comes back as
256. At least it's not zero, which is all you care about.
Richard

2008-01-12, 3:55 am

On Jan 12, 2:53 pm, Robert <n...@e.mail> wrote:
> The problem: I want to run a Unix command, program or script from Cobol and get its return
> code. For example, I want to test whether /usr/tmp is a valid directory. On a shell
> command line, I can say 'test -d /usr/tmp' (or ksh shortcut [ -d /usr/tmp ]) followed by
> 'echo $?'. The result will be 0 if valid, 1 if invalid. When I say the same in a Cobol
> program ..
>
> call 'system' using 'test -d /usr/tmp'
> if return-code not = zero
> display '/usr/tmp is not a valid directory'
> set fatal-error to true
> end-if
>
> .. the return-code is alswya zero.
>
> The solution:
>
> call 'system' using 'test -d /usr/tmp; exit $?'
>
> System() forks a child process, execs it to the default shell (usually sh), feeds it your
> command line and waits for it to terminate. It is functionally the same as saying:
> sh -c 'test -d /usr/tmp'
> The sh shell is supposed to exit by default with the last return code ($?), and system()
> is supposed to do the same. There is a bug in one of the two causing that to not work, but
> it does work when your command does an explicit exit.
>
> This question came up here two years ago, without a conclusive answer. I opined the return
> code should be passed back, Richard thought it was fundamentally impossible for a child
> process to pass anything back to its parent. This solution shows I was right.


see * below

> A further complication is that the system() surrogate supplied Micro Focus Server Express
> 4.1 running on HP-UX shifts the return code left 8 bits. Thus,
> call 'system' using 'exit 123'
> returns 31,488, which is 123*256. The 1 returned by the above directory test comes back as
> 256. At least it's not zero, which is all you care about.


The "system() surrogate supplied Micro Focus" is not "system" but is
"SYSTEM" (upper case). CALL "system" is likely to use the C library
routine.

The return from "system" is implementor defined. In Linux this is
defined as being in the "format specified in wait(2)".

I cannot find anything in MF manuals that say what the return from
"SYSTEM" is.


* I looked "two years ago" and found this:

RW> Call SYSTEM to run a script containing two entries: make followed
by
RW> export rc=$?
RW> Then you can interrogate rc to get the compiler's return code.

RP> No, you cannot do that, it will not and does not work.

RP> The 'system' call creates a new shell below the current one. Any
RP> 'export' only changes what is in that new shell and this is
destroyed
RP> before the 'system' returns to the program.

What "will not work" was your 'export=$?' that you expected to survive
the exit and be put into the shell above the Cobol program.


> I opined the return code should be passed back,


It would not be passed back by that mechanism.

> Richard thought it was fundamentally impossible for a child
> process to pass anything back to its parent.


No, you are wrong, yet again. I made no comment at all whether a
return code could be passed back by some means to its parent, I simply
pointed out that the mechanism you described would not, and provably
did not, work.

> This solution shows I was right.


Wrong then, wrong again. Did you not read the rest of the thread where
several people _demonstrated_ that you were wrong.


Robert

2008-01-12, 6:56 pm

On Fri, 11 Jan 2008 22:53:22 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 12, 2:53 pm, Robert <n...@e.mail> wrote:
>
>see * below
>
>
>The "system() surrogate supplied Micro Focus" is not "system" but is
>"SYSTEM" (upper case). CALL "system" is likely to use the C library routine.


I used lower case.

>The return from "system" is implementor defined. In Linux this is
>defined as being in the "format specified in wait(2)".


Which is a pid_t: an integer containing the child's process id. What I get back is
WEXITSTATUS() in the left byte and zero in the right byte.

>I cannot find anything in MF manuals that say what the return from
>"SYSTEM" is.


I assume it's the same as the C function.

>* I looked "two years ago" and found this:
>
>RW> Call SYSTEM to run a script containing two entries: make followed
>by
>RW> export rc=$?
>RW> Then you can interrogate rc to get the compiler's return code.
>
>RP> No, you cannot do that, it will not and does not work.
>
>RP> The 'system' call creates a new shell below the current one. Any
>RP> 'export' only changes what is in that new shell and this is
>destroyed
>RP> before the 'system' returns to the program.
>
>What "will not work" was your 'export=$?' that you expected to survive
>the exit and be put into the shell above the Cobol program.


You're correct about that.

>
>It would not be passed back by that mechanism.


Yes, but it should be passed back by the wait() mechanism, which is used by system().

>
>No, you are wrong, yet again. I made no comment at all whether a
>return code could be passed back by some means to its parent, I simply
>pointed out that the mechanism you described would not, and provably
>did not, work.


True, but not helpful. The number of things that don't work is infinity minus 1. It can be
made to work by coding an explicit exit.

>
>Wrong then, wrong again. Did you not read the rest of the thread where
>several people _demonstrated_ that you were wrong.


That discussion was about running the make program to do a compilation. It would have been
helpful if someone had pointed out how to add .cbl to the suffix list, which would enable
writing a rule to compile all Cobol programs. It is done like this:

targets=prog1.so prog2.so prog3.so
..SUFFIXES:.cbl .so

..cbl.so: cob -z $< # this is a rule

$(targets) # this line compiles all stale targets
Richard

2008-01-12, 6:56 pm



Robert wrote:
> On Fri, 11 Jan 2008 22:53:22 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:
>
>
> I used lower case.
>
>
> Which is a pid_t: an integer containing the child's process id.


While the format is a pid_t, as I said, the content need not be a pid.

> What I get back is
> WEXITSTATUS() in the left byte and zero in the right byte.


If the return is bigendian, then will a S9(4) COMP-5 give it correctly
by reversing the bytes ?

>
> I assume it's the same as the C function.


I don't know why you would make such assumptions. "SYSTEM" does much
more than "system" because it adjusts the ADIS settings. What it
returns is entirely dependent on what MF want it to, and as far as I
can tell, they haven't said.

>
> You're correct about that.


So, you agree then that your: "Richard thought it was fundamentally
impossible for a child process to pass anything back to its parent."
was wrong and was gross misrepresentation, and that your: "This
solution shows I was right." was complete nonsense.


>
> Yes, but it should be passed back by the wait() mechanism, which is used by system().


That was not even discussed.

>
> True, but not helpful. The number of things that don't work is infinity minus 1. It can be
> made to work by coding an explicit exit.


What was entirely unhelpful at the time was your proposed mechanism
which had no hope of working, and your assurance that you had done it
many times:

RW>> I could swear on a stack of manuals I've done it many times.


>
> That discussion was about running the make program to do a compilation. It would have been
> helpful if someone had pointed out how to add .cbl to the suffix list, which would enable
> writing a rule to compile all Cobol programs. It is done like this:


You had ample opportunity to do that at the time, but, in fact, it was
unrequired. The requirement was to compile a single program on each
iteration and I had outlined a simple makefile which was sufficient.
The point at issue was entirely how to determine if the compile worked
or not.


> targets=prog1.so prog2.so prog3.so
> .SUFFIXES:.cbl .so
>
> .cbl.so: cob -z $< # this is a rule
>
> $(targets) # this line compiles all stale targets


More of your usual deflection.

Robert

2008-01-13, 3:55 am

On Sat, 12 Jan 2008 13:37:20 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:
>Robert wrote:
>
>While the format is a pid_t, as I said, the content need not be a pid.


I think there are backward compatibility issues with old (pre-POSIX) versions of system().
Returning the pid of a process that no longer exists has no utility. It appears that,
under certain conditions, you get the 'status' word, which contains the return code. Under
the covers, it is doing wait(&status), which is equivalent to waitpid(-1, &status, 0);

>
>If the return is bigendian, then will a S9(4) COMP-5 give it correctly
>by reversing the bytes ?


I was using return-code, rather than a user-defined variable, to eliminate that
complication. HP-UX is a bigendian (bassackwards) operating system. The underlying PA
processor can go either way; when it's running HP-UX, it's bigendian.

I no longer use COMP-n. Instead, I use BINARY, which lets the compiler deal with
endianness. I'm not interested in that petty squabble.

>
>I don't know why you would make such assumptions. "SYSTEM" does much
>more than "system" because it adjusts the ADIS settings. What it
>returns is entirely dependent on what MF want it to, and as far as I
>can tell, they haven't said.


I'll do an ldd to find out for sure whether I'm calling the C library "system" or the MF
surrogate "SYSTEM". Generally, MF likes to uppercase the names of programs it does not
recognize. All user defined programs are uppercased.

>
>So, you agree then that your: "Richard thought it was fundamentally
>impossible for a child process to pass anything back to its parent."
>was wrong and was gross misrepresentation, and that your: "This
>solution shows I was right." was complete nonsense.


Will you agree that I try to be helpful while you're a curmudgeon?

>
>That was not even discussed.


It should have been, because that's how a return code is passed back.

>
>What was entirely unhelpful at the time was your proposed mechanism
>which had no hope of working, and your assurance that you had done it
>many times:
>
>RW>> I could swear on a stack of manuals I've done it many times.


I HAD done it many times. Now I realize it must have been in functions within the same
script.

>
>You had ample opportunity to do that at the time, but, in fact, it was
>unrequired. The requirement was to compile a single program on each
>iteration and I had outlined a simple makefile which was sufficient.
>The point at issue was entirely how to determine if the compile worked
>or not.


In that case, they didn't need make, they could have just shelled to the compiler. In
either case, the trick to getting a return code was an explicit exit statement.

call 'system' using 'cob prog.cbl' *> always returns zero
call 'system' using 'cob prog.cbl; exit $?' *> returns non-zero for failure

That's the answer they were looking for.
Robert

2008-01-13, 3:55 am

On Sat, 12 Jan 2008 22:43:24 -0600, Robert <no@e.mail> wrote:


>call 'system' using 'cob prog.cbl' *> always returns zero


It is not necessary to null terminate the string passed to system. If you're anal
retentive, there are several (unnecessary) ways to do it:

call 'system' using z'cob ...'
call 'system' using 'cob ...' & x'00'
call 'system' using 'cob ...' & low-value
string 'cob ...' low-value delimited by size into unix-command
call 'system' using unix-command

It works exactly the same without the null terminator. The command shell (sh) probably
wastes a few microseconds skipping trailing spaces. If the program runs a million times,
those microseconds might add up to the extra typing time.
Richard

2008-01-13, 6:56 pm

On Jan 13, 6:33 pm, Robert <n...@e.mail> wrote:
> On Sat, 12 Jan 2008 22:43:24 -0600, Robert <n...@e.mail> wrote:
>
> It is not necessary to null terminate the string passed to system.


01 echo-me PIC X(8) VALUE "echo me."
01 next-field PIC X(12) VALUE "next field".

CALL "system" USING echo-me

produces:

me.next field

It may be that sometimes it doesn't need a terminator because, quite
by chance, there is a null in the packing bytes.


> If you're anal
> retentive, there are several (unnecessary) ways to do it:
>
> call 'system' using z'cob ...'
> call 'system' using 'cob ...' & x'00'
> call 'system' using 'cob ...' & low-value
> string 'cob ...' low-value delimited by size into unix-command
> call 'system' using unix-command
>
> It works exactly the same without the null terminator. The command shell (sh) probably
> wastes a few microseconds skipping trailing spaces. If the program runs a million times,
> those microseconds might add up to the extra typing time.


You are such a mine of misinformation.

Richard

2008-01-13, 6:56 pm

On Jan 13, 5:43 pm, Robert <n...@e.mail> wrote:
> On Sat, 12 Jan 2008 13:37:20 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
[color=darkred]
>
> I'll do an ldd to find out for sure whether I'm calling the C library "system" or the MF
> surrogate "SYSTEM". Generally, MF likes to uppercase the names of programs it does not
> recognize. All user defined programs are uppercased.


No, you are wrong again. Microfocus does _NOT_ uppercase user defined
programs, at least it does not in my compiles.

It may be that Windows file systems are case insensitive so calling
"xyz" and "XYZ" access the same file, but MF uses the name as written
in the source.

Once again you are a mine of misinformation.

I should add that Fujitsu _does_ (or might) modify CALL "program" when
a literal is used and Program-id names and this depends on the setting
of directives such as the ALPHAL=.


>
> Will you agree that I try to be helpful while you're a curmudgeon?


You may _try_ to be helpful, but providing incorrect information is
counter productive and often you dash into trying to show how clever
you are (such as your range of adding nulls) rather than helping with
the _actual_question_.


>
>
>
>
> It should have been, because that's how a return code is passed back.


You had ample opportunity at the time to provide information on that
subject.

Richard

2008-01-13, 6:56 pm

On Jan 13, 5:43 pm, Robert <n...@e.mail> wrote:

>
> Will you agree that I try to be helpful while you're a curmudgeon?


So, instead of acknowledging that you had maligned me by gross
misrepresentation you resort to name calling. Instead of noticing that
your original claims were unworkable, you call them 'helpful'.

No wonder others think that you are arrogant.



Pete Dashwood

2008-01-13, 6:56 pm



"Richard" <riplin@azonic.co.nz> wrote in message
news:f6e84aa2-f932-4f78-98fd-4feaf853e737@k39g2000hsf.googlegroups.com...
> On Jan 13, 5:43 pm, Robert <n...@e.mail> wrote:
>
>
> So, instead of acknowledging that you had maligned me by gross
> misrepresentation you resort to name calling. Instead of noticing that
> your original claims were unworkable, you call them 'helpful'.
>
> No wonder others think that you are arrogant.
>
>
>

Without taking sides, I'd just remind both of you that your contributions
here are extremely valuable.

Speaking only for myself, I have found posts from both of you to be
extremely helpful and useful.

It is quite obvious that you both are way above average in knowledge and
experience, and a valuable resource to this group.

If you really must behave like Tweedledum and Tweedledee that's entirely a
matter for the two of you, but the ad hominem on both sides is not
strengthening any cases...:-)

(Had to smile at "curmudgeon"... a beautiful old word :-) Nevertheless, an
insult beautifully framed is still an insult, and probably doesn't help
anybody...)

Pete.
--
"I used to write COBOL...now I can do anything."


Richard

2008-01-13, 6:56 pm

On Jan 14, 10:16 am, "Pete Dashwood"
<dashw...@removethis.enternet.co.nz> wrote:


> If you really must behave like Tweedledum and Tweedledee that's entirely a
> matter for the two of you, but the ad hominem on both sides is not
> strengthening any cases...:-)


Since when did pointing out multiple factual errors count as an ad
hominem ?

Now, not only do I get called a 'curmudgeon' for defending myself
against being malaigned, but also a 'Tweedledee'.

William M. Klein

2008-01-14, 6:56 pm


"Richard" <riplin@azonic.co.nz> wrote in message
news:3100d3c2-c525-4a71-9838-a778c7825825@y5g2000hsf.googlegroups.com...
> On Jan 13, 5:43 pm, Robert <n...@e.mail> wrote:
>
>
> No, you are wrong again. Microfocus does _NOT_ uppercase user defined
> programs, at least it does not in my compiles.
>

Micro Focus (not Microfocus) hs directives that determines this. (Actually,
they have more than one) See for example the description of the CASE directive:

"CASE leaves the case of external symbols as is. This is useful if you are
calling a program written in C, where names are case dependent.

NOCASE folds external symbols to upper case."

and also

"With NOFOLD-CALL-NAME, by normal COBOL convention the program-name is folded to
upper case unless enclosed in quotes. This also applies to the root program of a
nested program. All the subprogram-names are folded to upper case even when in
quotes. (Enclosing program-names in quotes is a Micro Focus extension.)"

there may be some others as well.


--
Bill Klein
wmklein <at> ix.netcom.com


Robert

2008-01-14, 6:56 pm

On Sun, 13 Jan 2008 10:53:38 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 13, 5:43 pm, Robert <n...@e.mail> wrote:
>
>
>No, you are wrong again. Microfocus does _NOT_ uppercase user defined
>programs, at least it does not in my compiles.
>
>It may be that Windows file systems are case insensitive so calling
>"xyz" and "XYZ" access the same file, but MF uses the name as written
>in the source.
>
>Once again you are a mine of misinformation.


I checked and found that for calls IN, entry points, Micro Focus does it both ways: as
written and in upper case. The upper case is more noticable because it is the first few
entries in the symbol table.

For calls OUT, externs, it leaves the names as written. Thus, a call to 'system' is not
translated to 'SYSTEM'.

That's true using default options. I didn't look for options to make it act differently.

>I should add that Fujitsu _does_ (or might) modify CALL "program" when
>a literal is used and Program-id names and this depends on the setting
>of directives such as the ALPHAL=.
>
>
>
>You may _try_ to be helpful, but providing incorrect information is
>counter productive and often you dash into trying to show how clever
>you are (such as your range of adding nulls) rather than helping with
>the _actual_question_.


I try to avoid saying something is fact unless I've tested it.

>
>You had ample opportunity at the time to provide information on that
>subject.


At the time, no one knew the answer. I posted it when I figued it out, two years later.
Richard

2008-01-14, 6:56 pm

On Jan 15, 8:11 am, Robert <n...@e.mail> wrote:
> On Sun, 13 Jan 2008 10:53:38 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
>
>
>
>
>
>
> I checked and found that for calls IN, entry points, Micro Focus does it both ways: as
> written and in upper case. The upper case is more noticable because it is the first few
> entries in the symbol table.
>
> For calls OUT, externs, it leaves the names as written. Thus, a call to 'system' is not
> translated to 'SYSTEM'.
>
> That's true using default options. I didn't look for options to make it act differently.
>
>
>
>
>
> I try to avoid saying something is fact unless I've tested it.


As I said, it may well be that under certain conditions the call
"system" will work without an explicit null because the packing bytes
may provide this. So a single test may show it to work in some
circumstances, or to not work as in my test.

The problem that I see is that you extrapolate from a small sample
(possibly just one) into being a 'universal truth'.

You claimed "All user defined programs are uppercased.". You did not
test "All user defined programs", nor all possible combinations of
compiler options.

You claimed 3 times: "It is not necessary to null terminate the
string" and "(unnecessary)" and "It works exactly the same without the
null terminator."

And you added an ad hominem "anal retentive" to anyone who didn't
accept your falacious claims.

One simple test showed you were quite wrong. So what testing _did_ you
do ?


>
>
>
>
>
>
> At the time, no one knew the answer. I posted it when I figued it out, two years later.


Several adequate mechanisms were provided at the time (plus your
unworkable one).

Pete Dashwood

2008-01-14, 6:56 pm



"Richard" <riplin@azonic.co.nz> wrote in message
news:ab0a259a-215f-4fce-bf8f-14864b900493@i29g2000prf.googlegroups.com...
> On Jan 14, 10:16 am, "Pete Dashwood"
> <dashw...@removethis.enternet.co.nz> wrote:
>
>
>
> Since when did pointing out multiple factual errors count as an ad
> hominem ?
>
> Now, not only do I get called a 'curmudgeon' for defending myself
> against being malaigned, but also a 'Tweedledee'.
>


No, I had you down as Tweedledum... :-)

Seriously, pointing out factual errors is never an ad hominem and very
necessary.

I still think the two of you are very good to have around :-)

Pete.
--
"I used to write COBOL...now I can do anything."


Robert

2008-01-14, 9:56 pm

On Mon, 14 Jan 2008 11:58:09 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 15, 8:11 am, Robert <n...@e.mail> wrote:
>
>As I said, it may well be that under certain conditions the call
>"system" will work without an explicit null because the packing bytes
>may provide this. So a single test may show it to work in some
>circumstances, or to not work as in my test.
>
>The problem that I see is that you extrapolate from a small sample
>(possibly just one) into being a 'universal truth'.
>
>You claimed "All user defined programs are uppercased.". You did not
>test "All user defined programs", nor all possible combinations of
>compiler options.
>
>You claimed 3 times: "It is not necessary to null terminate the
>string" and "(unnecessary)" and "It works exactly the same without the
>null terminator."
>
>And you added an ad hominem "anal retentive" to anyone who didn't
>accept your falacious claims.
>
>One simple test showed you were quite wrong. So what testing _did_ you
>do ?


I was referring to calling with a literal e.g. call 'system' using 'cob ....' I thought
that was obvious in the examples. Micro Focus doesn't say so in its manuals, but I've
learned from experience that literal strings in call are automatically null terminated.

I've tested it dozens of times.

>
>Several adequate mechanisms were provided at the time (plus your
>unworkable one).


The only suggestion was ugly: overwriting a file. I say ugly because it was asymmetric.
The parent Cobol program wrote 'failure' and the child make overwrote it with 'success'.
A symmetric solution would look like this:

program: program.cbl; \
cob program \
&& echo 'success' > myfile \
|| echo 'failure' > myfile

http://groups.google.com/group/comp...
eb20c49e

Richard

2008-01-14, 9:56 pm

On Jan 15, 2:26 pm, Robert <n...@e.mail> wrote:
> On Mon, 14 Jan 2008 11:58:09 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
>
> I was referring to calling with a literal e.g. call 'system' using 'cob ....' I thought
> that was obvious in the examples.


Not only was it not "obvious", but you explicitly referred to a call
'system' using variable:

RW> It is not necessary to null terminate the string passed to
system.
RW> If you're anal retentive, there are several (unnecessary)
RW> ways to do it:

RW> [...]
RW> string 'cob ...' low-value delimited by size into unix-command
RW> call 'system' using unix-command

RW> It works exactly the same without the null terminator.

In what way is unix-command a literal ?

It should also be obvious that your "call 'system' using 'cob ....'"
is not particularly useful in a literal as it may be required to
compile different program on each execution.

Not only were you wrong about not needing a null terminator you were
also wrong that you were "referring to calling with a literal".

This is your usual deflection, you make up excuses for your
misinformation without bothering to check.

> Micro Focus doesn't say so in its manuals, but I've
> learned from experience that literal strings in call are
> automatically null terminated.


One of the problems with relying on undocumented 'features' is that it
may disappear in some new version, or it may only actually be a
'feature' with a particular set of compiler options.

For example it may work with OPT"0" (.int byte coded) because the
interpreter may have to drag the parameter somewhere else, but could
fail with OPT"1" (.gnt generated) or OPT"2" (optimised) because it
inlines the code.

It was poor advice, wrongly stated, and was simple misinformation.


> I've tested it dozens of times.


>
> The only suggestion was ugly: overwriting a file. I say ugly because it was asymmetric.
> The parent Cobol program wrote 'failure' and the child make overwrote it with 'success'.



'Ugly' and working is still better than unworkable and wrong.



Richard

2008-01-14, 9:56 pm

On Jan 15, 2:26 pm, Robert <n...@e.mail> wrote:
> On Mon, 14 Jan 2008 11:58:09 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
>
>
> The only suggestion was ugly: overwriting a file.


Daniel (LX-I) wrote:
> There was one process that we couldn't do from within
> the program, so the program writes a sequence of commands
> to a file, "add"s it to the run (which means it starts
> executing when this program stops), and finishes.
> The last statement in the file re-executes the checker to
> check that final process.


Simon Tobias wrote:
> Cob -- which isn't COBOL, by the way -- will return a zero
> return-code is the compilation is successful, so I would
> *assume* that the return-code will trickle back down from
> a CALL "SYSTEM" to the calling COBOL app.


So that was three, which counts as 'several'.

The point about overwriting the file before the CALL "SYSTEM" is that
if the CALL fails, or the SYSTEM fails, or the command file fails,
then the program will not pick up the previous 'result file' which may
still contain 'success'.

These failure safeguards should be readily understood by someone who
is no longer a newbie.

I'd rather have 'looks ugly' than your 'does ugly' anyday.
Robert

2008-01-15, 3:55 am

On Mon, 14 Jan 2008 19:49:54 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 15, 2:26 pm, Robert <n...@e.mail> wrote:
>
>Daniel (LX-I) wrote:

Terminating is hardly a solution to 'call the compiler and get its return code.'
[color=darkred]
>Simon Tobias wrote:

That's precisely what did not work.
[color=darkred]
>So that was three, which counts as 'several'.
>
>The point about overwriting the file before the CALL "SYSTEM" is that
>if the CALL fails, or the SYSTEM fails, or the command file fails,
>then the program will not pick up the previous 'result file' which may
>still contain 'success'.
>
>These failure safeguards should be readily understood by someone who
>is no longer a newbie.
>
>I'd rather have 'looks ugly' than your 'does ugly' anyday.


My solution detects all those exceptions.

Robert

2008-01-15, 3:55 am

On Mon, 14 Jan 2008 18:03:07 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 15, 2:26 pm, Robert <n...@e.mail> wrote:
>
>Not only was it not "obvious", but you explicitly referred to a call
>'system' using variable:
>
>RW> It is not necessary to null terminate the string passed to
>system.
>RW> If you're anal retentive, there are several (unnecessary)
>RW> ways to do it:
>
>RW> [...]
>RW> string 'cob ...' low-value delimited by size into unix-command
>RW> call 'system' using unix-command
>
>RW> It works exactly the same without the null terminator.
>
>In what way is unix-command a literal ?


Because it is not a literal, I terminated it with a low-value. The literal was 'cob ...'
I gave an example of how to explicitly null terminate a literal.

>It should also be obvious that your "call 'system' using 'cob ....'"
>is not particularly useful in a literal as it may be required to
>compile different program on each execution.


In that case, use a make file, or assemble the command WITH a terminator, or initialize
the string area to low-values.

>Not only were you wrong about not needing a null terminator you were
>also wrong that you were "referring to calling with a literal".


>This is your usual deflection, you make up excuses for your
>misinformation without bothering to check.


This is your usual pettiness, which amounts to an ad hominem.

>
>One of the problems with relying on undocumented 'features' is that it
>may disappear in some new version, or it may only actually be a
>'feature' with a particular set of compiler options.
>
>For example it may work with OPT"0" (.int byte coded) because the
>interpreter may have to drag the parameter somewhere else, but could
>fail with OPT"1" (.gnt generated) or OPT"2" (optimised) because it
>inlines the code.


The default is "2". Adding or deleting a null terminator has no affect on the program's
speed.

>It was poor advice, wrongly stated, and was simple misinformation.


I thought it was useful information.

>
>
>
>'Ugly' and working is still better than unworkable and wrong.


Getting the return code, which was the original question and title of this thread, is
better than a kludgy solution.
Richard

2008-01-15, 3:55 am

On Jan 15, 6:55 pm, Robert <n...@e.mail> wrote:
> On Mon, 14 Jan 2008 18:03:07 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:


>
>
>
>
>
>
>
>
> Because it is not a literal, I terminated it with a low-value. The literal was 'cob ...'
> I gave an example of how to explicitly null terminate a literal.


You claimed it was "not necessary to null terminate the string" and
"(unnecessary)", _and_ called anyone who would want to add the null
"anal retentive".

(which BTW _is_ ad hominem).

>
> This is your usual pettiness, which amounts to an ad hominem.



As expected, instead of admitting you were wrong you try to hide it
("I was referring to calling with a literal"), attempt to blame
everyone else ("it should have been obvious") and then claim that
correcting your misinformation is "petty" and "ad hominem".


>
>
>
> The default is "2". Adding or deleting a null terminator has no affect on the program's
> speed.


No, but different OPT, or other options, may change the way the code
works in respect of any undocumented 'features'.

Anyone who believes your claim that "nulls are unnecessary" may not
get the results they expect.


>
> I thought it was useful information.


And you probably still it is so, I have noticed in the past how
resistant you are to correction of your mistakes.


[color=darkred]
>
>
>
> Getting the return code, which was the original question and title of this thread, is
> better than a kludgy solution.


Richard

2008-01-15, 3:55 am

On Jan 15, 6:55 pm, Robert <n...@e.mail> wrote:
> On Mon, 14 Jan 2008 19:49:54 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
>
>
>
>
> Terminating is hardly a solution to 'call the compiler and get its return code.'


>
> That's precisely what did not work.


I think that your whole rant has been wasted.

I just tested CALL "SYSTEM" and CALL "system" with and without a
RETURNING Result. In all cases I got the correct expected result in
Result or RETURN-CODE. It was zero if the command worked and non-zero
(granted byte order mangled) if it failed. There is no need (in my
tests) for any "exit &?".

I tested using CALL "SYSTEM|system" USING "sh do.sh" &
x"00" [RETURNING Result]

do.sh was:

#!/bin/sh
ls /xyz

as /xyz was missing it returned 2 (as 512).

I don't know what you did wrong in your tests but you seem to have
misdiagnosed the problem and provided a 'solution' to a non-problem.


>
>
>
>
> My solution detects all those exceptions.


How so ?



Robert

2008-01-15, 9:56 pm

On Mon, 14 Jan 2008 23:40:29 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 15, 6:55 pm, Robert <n...@e.mail> wrote:
>
>
>I think that your whole rant has been wasted.
>
>I just tested CALL "SYSTEM" and CALL "system" with and without a
>RETURNING Result. In all cases I got the correct expected result in
>Result or RETURN-CODE. It was zero if the command worked and non-zero
>(granted byte order mangled) if it failed. There is no need (in my
>tests) for any "exit &?".
>
>I tested using CALL "SYSTEM|system" USING "sh do.sh" &
>x"00" [RETURNING Result]
>
>do.sh was:
>
>#!/bin/sh
>ls /xyz
>
>as /xyz was missing it returned 2 (as 512).
>
>I don't know what you did wrong in your tests but you seem to have
>misdiagnosed the problem and provided a 'solution' to a non-problem.


I tried similar and also got the return code back. But some commands return zero until I
add an explicit exit. It acts as though a null command -- ;: or ;; -- is being added.

>
>How so ?


All those failures, except the first, return a non-zero return code.

In the unlikely event call 'system' fails, Cobol will abort both unless the call contains
an ON EXCEPTION clause.
Richard

2008-01-15, 9:56 pm

On Jan 16, 2:11 pm, Robert <n...@e.mail> wrote:
> On Mon, 14 Jan 2008 23:40:29 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:


>


Well, actually it can be. It may depend on the OS and how the command
file works.

>

Perhaps it did work for him. You always seem to think that your
samples are globally applicable universal truths.

[color=darkred]
>
>
>
>
>
>
>
> I tried similar and also got the return code back. But some commands return zero until I
> add an explicit exit. It acts as though a null command -- ;: or ;; -- is being added.


Perhaps because you failed to add the null terminator and some sort of
null command _was_ added.

Maybe your actual test had an 'echo &?' so you could see the value,
after which the return was bound to be zero.

Perhaps adding the 'exit &?' changed length of the string and what
characters followed it.

I tried your CALL "system" USING "test -d ..." and it worked exactly
as expected.


>
>
>
>
>
>
> All those failures, except the first, return a non-zero return code.
>
> In the unlikely event call 'system' fails, Cobol will abort both unless the call contains
> an ON EXCEPTION clause.


I was actually asking how it did this after you had taken my 'ugly'
code and made it 'pretty' with your so-called 'symmetric solution':

RW> The only suggestion was ugly: overwriting a file. I
RW> say ugly because it was asymmetric.
RW> The parent Cobol program wrote 'failure' and the
RW> child make overwrote it with 'success'.
RW> A symmetric solution would look like this:

RW> program: program.cbl; \
RW> cob program \
RW> && echo 'success' > myfile \
RW> || echo 'failure' > myfile

This doesn't have the same functionality.
Robert

2008-01-16, 3:56 am

On Tue, 15 Jan 2008 17:59:21 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 16, 2:11 pm, Robert <n...@e.mail> wrote:
[color=darkred]
>
>Perhaps because you failed to add the null terminator and some sort of
>null command _was_ added.


That's possible. I would expect random bytes to be an invalid parameter.
When I call 'system' using 'echo abc', there are no extra bytes at the end.

>Maybe your actual test had an 'echo &?' so you could see the value,
>after which the return was bound to be zero.


I'm not that stupid.

>Perhaps adding the 'exit &?' changed length of the string and what
>characters followed it.


Anything following exit is irrelevant.

>I tried your CALL "system" USING "test -d ..." and it worked exactly
>as expected.


Thanks for trying it. I'm puzzled as to why it didn't work for me.

>
>I was actually asking how it did this after you had taken my 'ugly'
>code and made it 'pretty' with your so-called 'symmetric solution':
>
>RW> The only suggestion was ugly: overwriting a file. I
>RW> say ugly because it was asymmetric.
>RW> The parent Cobol program wrote 'failure' and the
>RW> child make overwrote it with 'success'.
>RW> A symmetric solution would look like this:
>
>RW> program: program.cbl; \
>RW> cob program \
>RW> && echo 'success' >$ myfile \
>RW> || echo 'failure' > $myfile
>
>This doesn't have the same functionality.


I left out the Cobol program:

select myfile assign to external '$myfile' file status file-status.

call 'system' using 'export myfile=`mktemp`' & x'0'
call 'system' using 'make' & x'0'
open input myfile

if file-status not less than '10'
move 'make error' to compilation-result
else
read myfile into compilation-result
at end move 'result empty' to compilation-result
end-read
end-if
close myfile
delete file myfile
if compilation-result not = 'success'
display 'compilation result is ' compilation-result
exit program returning 4
end-if

Richard

2008-01-16, 3:56 am

On Jan 16, 5:12 pm, Robert <n...@e.mail> wrote:
> On Tue, 15 Jan 2008 17:59:21 -0800 (PST), Richard <rip...@azonic.co.nz> wrote:
[color=darkred]
>
> I'm not that stupid.


(hmmm)

>
> I left out the Cobol program:
>
> select myfile assign to external '$myfile' file status file-status.
>
> call 'system' using 'export myfile=`mktemp`' & x'0'
> call 'system' using 'make' & x'0'
> open input myfile


When you started this thread you grossly misrepresented what I said
when I indicated, 2 years ago, where you had coded an export that
simply could not work the way you wanted (it was nothing to do with
whether you could get a return code).

It seems that you still haven't been paying attention. You still think
that an export in a child shell (as started by call 'system') will
survive the end of that shell.

RW>> Call SYSTEM to run a script containing two entries: make followed
by
RW>> export rc=$?
RW>> Then you can interrogate rc to get the compiler's return code.

RP>No, you cannot do that, it will not and does not work.

RP>The 'system' call creates a new shell below the current one. Any
RP>'export' only changes what is in that new shell and this is
destroyed
RP>before the 'system' returns to the program.


> if file-status not less than '10'
> move 'make error' to compilation-result
> else
> read myfile into compilation-result
> at end move 'result empty' to compilation-result
> end-read
> end-if
> close myfile
> delete file myfile
> if compilation-result not = 'success'
> display 'compilation result is ' compilation-result
> exit program returning 4
> end-if


It is obvious that you haven't tested this, and probably not even
tried to compile it.

Robert

2008-01-16, 3:56 am

On Tue, 15 Jan 2008 22:11:48 -0800 (PST), Richard <riplin@azonic.co.nz> wrote:

>On Jan 16, 5:12 pm, Robert <n...@e.mail> wrote:
>
>
>(hmmm)
>
>
>When you started this thread you grossly misrepresented what I said
>when I indicated, 2 years ago, where you had coded an export that
>simply could not work the way you wanted (it was nothing to do with
>whether you could get a return code).
>
>It seems that you still haven't been paying attention. You still think
>that an export in a child shell (as started by call 'system') will
>survive the end of that shell.


Whoops, you're right. Ok, hard code the file name.

>RW>> Call SYSTEM to run a script containing two entries: make followed
>by
>RW>> export rc=$?
>RW>> Then you can interrogate rc to get the compiler's return code.
>
>RP>No, you cannot do that, it will not and does not work.
>
>RP>The 'system' call creates a new shell below the current one. Any
>RP>'export' only changes what is in that new shell and this is
>destroyed
>RP>before the 'system' returns to the program.
>
>
>
>It is obvious that you haven't tested this, and probably not even
>tried to compile it.


What's wrong with it?
William M. Klein

2008-01-16, 6:56 pm

I don't really think it will end much debate, but when talking about
"null-termination of literals" in a CALL statement, it is clear (to me at least)
that there is a difference between literal-1 and literal-2 in the following:

Call "literal-1" using "literal-2"

I (personally) know of NO environment where literal-1 needs to be
null-terminated. I do know of some cases in some environments where NOT using a
null-terminated literal-2 causes problems.

P.S. For those looking for null-terminated literals, you might want to check if
your compiler supports the extension of
z-literals
e.g.

Call "literal-1" using z"literal-2"

****

Also going back to the subject of the thread, I believe that SOME compilers do
support
Returning Return-Code
while others explicitly state that the (extension) return-code special register
should NOT be used in the RETURNING phrase.

--
Bill Klein
wmklein <at> ix.netcom.com


Sponsored Links







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

Copyright 2008 codecomments.com