Page 1 of 2

COBOL calling C pointer problem?

PostPosted: Fri Jul 09, 2010 2:38 pm
by blueywilson
Hello,

Hopefully one of you guys could help with a problem that has seen us banging our heads
against the wall now for a number of days.

We are calling a C function (in a DLL) from COBOL returning a pointer as follows:

CALL 'cfunction1' RETURNING C-POINTER.

Stepping through using the z/OS Debug tool v8.1 we can see the pointer being set within
the C function and when control returns to the COBOL program the COBOL pointer contains
the same value.

We then call a second C function as follows:

CALL 'cfunction2' USING BY VALUE C-POINTER
BY REFERENCE C-GROUP
RETURNING C-STATUS.

The parameters are defind in COBOL as:

01 C-POINTER USAGE IS POINTER.
01 C-GROUP PIC X(28)
01 C-STATUS PIC XX.

C-GROUP is filled with low-values prior to the call to cfunction2.

Again through debug, upon entry to cfunction2 the value of C-POINTER has changed
and we can't see any reason why this would be the case? Any ideas? What are we
missing?

We're running on z/OS v1.9, Enterprise COBOL v4. Any help would be much
appreciated.

Re: COBOL calling C pointer problem?

PostPosted: Sat Jul 10, 2010 2:34 am
by dick scherrer
Hello and welcome to the forum,

Is there an abend? If yes, which abend?

What is the "good" value and what is the changed value?

What might happen if you replace the second c function with a simple cobol stub (just for an experiment, not to really replace the second c module)? Does the value get changed or does this work as expected?

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 2:13 pm
by blueywilson
Thanks for your help Dick.

Yes there is an abend in cfunction1, not on entry to the function but after a number of
lines of code have been processed which I presume is when the pointer is referenced.
The abend is as follows:

"CEE3204S The system detected a protection exception (System Completion Code=0C4 ).
From compile unit //'HPW.ATLASC.BATCH.C(ATLXFH)' at entry point _atlxfh_ClosePZON
at statement 863 at compile unit offset +000000FC at entry offset +000000FC at address
0A75F20C.

Abend 0C4000 hex occurred processing command 'CALL '."

The values of the pointer are, before call being '0BAD2028' and after the call '0A1EDD98'.

I have created a simple COBOL stub as you suggested passing the same parameters
as cfunction2 and this works as expected ie the value of the pointer remains intact during
the call and on exit.

We have also tried using another C function that also uses the pointer, this one being
very simple passing two intergers. The call for this third function from the COBOL is as
follows:

CALL 'cfunction3' USING BY VALUE C-POINTER
BY VALUE C-INT1
BY VALUE C-INT2.

where C-INT1 and C-INT2 are both defined as PIC X.

When we perform this call the value of the pointer DOES NOT change and remains
consistent within the cfunction3 as passed from the COBOL? Very confusing?

Any help is gratefully received.

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 3:13 pm
by blueywilson
A bit more information. I've just tried a fourth C function, the COBOL call to this function
being:

CALL 'cfunction4' USING BY VALUE C-POINTER
BY REFERENCE C-GROUP2.

where C-GROUP2 is defined as PIC x(531).

The pointer again in this instance DOES NOT change after the call is made to the C function
which begs the question what is different about the call to 'cfuncntion2' that is causing the
value of the pointer to change?

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 5:40 pm
by blueywilson
It gets even stranger!

I tried the failing call (cfunction2) again but this time removing the third parameter such that
the COBOL call looked like this:

CALL 'cfunction2' USING BY VALUE C-POINTER
BY REFERENCE C-GROUP.

and surprisingly the pointer did not change value as it does when all three parameters
are included in the call. The cfunction2 is specified as follows in the C source:

_F2(U32 ENTRYPOINT cfunction2, ATLGDB*,gdb, char*,path)

??????

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 6:16 pm
by Robert Sample
Have you studied -- closely -- chapter 4 of the manual Language Environment Writing ILC Applications which covers COBOL to C programming interfaces? This manual is in the Language Environment bookshelf.

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 6:47 pm
by blueywilson
Thanks Robert, but yes we have studied closely the documentation and would have posted an question
without first trawling through any literature that may be relevant. That said nothing I've read throws
any light on the problem to my untrained eyes?

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 6:49 pm
by blueywilson
Sorry...meant 'would not have posted'.

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 7:19 pm
by Robert Sample
1. The manual makes a major distinction between programs using #pragma and programs NOT using #pragma. You have not indicated which is the case for you, so any advice we can provide is, at best, quite limited. It is your choice whether or not to provide complete information -- if you do not do so, you cannot expect accurate answers.

2. Section 4.3.1.1 of the manual is quoted below. You have not indicated your code is following the approach in the manual.
Passing by Value (Indirect): Data cannot be passed from C to COBOL; however, data can be passed by value (indirect) from COBOL to C. In this case, the variable is passed as a BY CONTENT argument and received by C as a pointer to the given type. For example, if a C function called FROMCOB is to receive a parameter passed by value (indirect) of type int, the function prototype declaration would look like this:

void FROMCOB(int *)

The C function must dereference the pointer to access the actual value. If the value of the pointer is modified by the C function, as opposed to modifying the value that the pointer points to, the results on return to COBOL are unpredictable. Thus, passing values by value (indirect) from COBOL to C should be used with caution, and only in cases where the exact behavior of the C function is known.


3. Do you understand the meaning of "BY VALUE"? This means the data is copied before the call -- so a pointer variable will, by its very definition, not contain the same value in the subroutine as the calling program. If you dereference the pointer, can you access the data value? If so why worry about the change in address?

Re: COBOL calling C pointer problem?

PostPosted: Mon Jul 12, 2010 8:49 pm
by blueywilson
Thanks Robert,

We are not using the #pragma approach.

Since many things are and could be involved with this problem it is difficult to ascertain what is
and what is not pertinent. If I haven't included a piece of information, then I apologise and will
gladly supply such if requested.

We also believe we are following the approach as laid out in the documentation. Also we believe
that we are passing by Value (Direct) not by Value (Indirect) and as such we do not need to
deference the the pointer before we can access the actual value. Our testing has shown that the
pointer does have the same value in the calling program as in the sub-program which you
say by definition can't be the case?

Perhaps I don't understand the meaning of BY VALUE which perhaps is why I've posted on
this forum to be guided by someone with a more indepth knowledge of the subject.

The question is why on this specific call does the pointer not contain the same actual value
whereas in other calls it does so?