Discussion:
COBOL question: Array of String Descriptors
(too old to reply)
V***@SendSpamHere.ORG
2017-12-22 21:40:42 UTC
Permalink
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.

There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.

Salacious Saturnalia to all!!!
--
VAXman- A Bored Certified VMS Kernel Mode Hacker VAXman(at)TMESIS(dot)ORG

I speak to machines with the voice of humanity.
Arne Vajhøj
2017-12-22 23:07:05 UTC
Permalink
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
I know nothing about COBOL, but would it by an option to let them pass
a variable number of arguments of type descriptor to string?

Example:

$ type c2cmain.cob
IDENTIFICATION DIVISION.
PROGRAM-ID. C2CMAIN.

ENVIRONMENT DIVISION.

DATA DIVISION.
WORKING-STORAGE SECTION.
01 N PIC 9(1) BINARY.
01 S1 PIC X(10).
01 S2 PIC X(10).
01 S3 PIC X(10).

PROCEDURE DIVISION.
MAIN-PARAGRAPH.
MOVE 3 TO N.
MOVE "A" TO S1
MOVE "BB" TO S2
MOVE "CCC" TO S3
CALL "FUNC" USING BY REFERENCE N, BY DESCRIPTOR S1, BY DESCRIPTOR
S2, BY DES
CRIPTOR S3.
STOP RUN.
$ cob c2cmain
$ type c2cfunc.c
#include <stdio.h>
#include <stdarg.h>

#include <descrip.h>

void func(int *n, ...)
{
va_list argptr;
struct dsc$descriptor_s *sd;
int i;
va_start(argptr, n);
for(i = 0; i < *n; i++)
{
sd = va_arg(argptr, struct dsc$descriptor_s *);
printf("|%*s|\n", sd->dsc$w_length, sd->dsc$a_pointer);
}
va_end(argptr);
}
$ cc c2cfunc
$ link c2cmain+c2cfunc
$ run c2cmain
|A |
|BB |
|CCC |

It should be easy to create an array of descriptors from this on the
C side.

Arne
Stephen Hoffman
2017-12-26 22:56:12 UTC
Permalink
Post by Arne Vajhøj
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them --
it's NOT COBOL code but it IS called by them from their COBOL.
....
I know nothing about COBOL, but would it by an option to let them pass
a variable number of arguments of type descriptor to string?
...
It should be easy to create an array of descriptors from this on the C side.
At the risk of asking a stupid question, why not expose a
COBOL-friendly API into some C code, and allow that C code to construct
the necessary descriptor for SMG or whatever. Then pass the address
or whatever back to the calling code, so it can be passed into "other"
API. Or as has been suggested previously here, expose a
variable-length argument list call to the users and stop trying to
recreate one of the most arcane APIs in OpenVMS? The
variable-argument call can then construct the "architecturally pure"
descriptor array, if that's deemed appropriate. These cases placing
more of a focus on the folks that have to create the glue code and to
figure out and call the routines in the API, and not so much on the
architectural astronautics and the complexity that parts of the OpenVMS
APIs have become infamous for. SMG is infamous for that
SMG$CREATE_MENU_WITH_GREAT_API_COMPLEXITY call, after all.

This whole mess makes me really appreciate how easy objects are to deal
with here, too. Where all of the shenanigans around descriptor
creation and access are managed for the developer, and where changes
don't ripple through the APIs, and where you can pass around different
sorts of data — a 32-bit descriptor, a 64-bit descriptor, an array of
descriptors, or the equivalent of an entry point and sharable image for
that matter, and with the string encoding and other metadata easily
encoded — and the called code can more easily deal with what gets
passed on. But we're not there yet with OpenVMS, and we still have to
hand-construct descriptors and the rest, and where the APIs and the
called code — even in the "descriptor-friendly" programming languages —
is far more brittle. Descriptors from C, C++, Bliss, Macro32 and ilk
all seem like using a crayon. Descriptors from BASIC and other
"descriptor-friendly" languages aren't all that much better, even
though (often) less work is involved. Then there are itemlists, which
are ugly in all of the languages. It's absurd that we're still futzing
around with those forty years on. Ah, well.
--
Pure Personal Opinion | HoffmanLabs LLC
Richard Maher
2017-12-27 00:11:13 UTC
Permalink
Post by Arne Vajhøj
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them --
it's NOT COBOL code but it IS called by them from their COBOL.
....
I know nothing about COBOL, but would it by an option to let them pass
a variable number of arguments of type descriptor to string?
...
It should be easy to create an array of descriptors from this on the C side.
At the risk of asking a stupid question, why not expose a COBOL-friendly
API into some C code, and allow that C code to construct the necessary
descriptor for SMG or whatever.   Then pass the address or whatever back
to the calling code, so it can be passed into "other" API.   Or as has
been suggested previously here, expose a variable-length argument list
call to the users and stop trying to recreate one of the most arcane
APIs in OpenVMS?   The variable-argument call can then construct the
"architecturally pure" descriptor array, if that's deemed appropriate.
These cases placing more of a focus on the folks that have to create the
glue code and to figure out and call the routines in the API, and not so
much on the architectural astronautics and the complexity that parts of
the OpenVMS APIs have become infamous for.   SMG is infamous for that
SMG$CREATE_MENU_WITH_GREAT_API_COMPLEXITY call, after all.
This whole mess makes me really appreciate how easy objects are to deal
with here, too.   Where all of the shenanigans around descriptor
creation and access are managed for the developer, and where changes
don't ripple through the APIs, and where you can pass around different
sorts of data — a 32-bit descriptor, a 64-bit descriptor, an array of
descriptors, or the equivalent of an entry point and sharable image for
that matter, and with the string encoding and other metadata easily
encoded  — and the called code can more easily deal with what gets
passed on.   But we're not there yet with OpenVMS, and we still have to
hand-construct descriptors and the rest, and where the APIs and the
called code — even in the "descriptor-friendly" programming languages —
is far more brittle.  Descriptors from C, C++, Bliss, Macro32 and ilk
all seem like using a crayon.   Descriptors from BASIC and other
"descriptor-friendly" languages aren't all that much better, even though
(often) less work is involved.  Then there are itemlists, which are ugly
in all of the languages.  It's absurd that we're still futzing around
with those forty years on.  Ah, well.
I have to agree that OO languages make most things easy. Having said
that there are some times when you want to just allocate a chunk of
memory and map it however you like,

Another slight problem with COBOL and descriptors is Rdb/SQL won't even
look for a dynamic string descriptor if you've told it the language is
COBOL.
DaveFroble
2017-12-27 00:16:54 UTC
Permalink
Post by Arne Vajhøj
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them --
it's NOT COBOL code but it IS called by them from their COBOL.
....
I know nothing about COBOL, but would it by an option to let them pass
a variable number of arguments of type descriptor to string?
...
It should be easy to create an array of descriptors from this on the C side.
At the risk of asking a stupid question, why not expose a COBOL-friendly
API into some C code, and allow that C code to construct the necessary
descriptor for SMG or whatever. Then pass the address or whatever back
to the calling code, so it can be passed into "other" API. Or as has
been suggested previously here, expose a variable-length argument list
call to the users and stop trying to recreate one of the most arcane
APIs in OpenVMS? The variable-argument call can then construct the
"architecturally pure" descriptor array, if that's deemed appropriate.
These cases placing more of a focus on the folks that have to create the
glue code and to figure out and call the routines in the API, and not so
much on the architectural astronautics and the complexity that parts of
the OpenVMS APIs have become infamous for. SMG is infamous for that
SMG$CREATE_MENU_WITH_GREAT_API_COMPLEXITY call, after all.
This whole mess makes me really appreciate how easy objects are to deal
with here, too. Where all of the shenanigans around descriptor
creation and access are managed for the developer, and where changes
don't ripple through the APIs, and where you can pass around different
sorts of data — a 32-bit descriptor, a 64-bit descriptor, an array of
descriptors, or the equivalent of an entry point and sharable image for
that matter, and with the string encoding and other metadata easily
encoded — and the called code can more easily deal with what gets
passed on. But we're not there yet with OpenVMS, and we still have to
hand-construct descriptors and the rest, and where the APIs and the
called code — even in the "descriptor-friendly" programming languages —
is far more brittle. Descriptors from C, C++, Bliss, Macro32 and ilk
all seem like using a crayon. Descriptors from BASIC and other
"descriptor-friendly" languages aren't all that much better, even though
(often) less work is involved. Then there are itemlists, which are ugly
in all of the languages. It's absurd that we're still futzing around
with those forty years on. Ah, well.
Yes, there are places where "objects" would be rather friendly.

Well, since you mentioned Basic, using item lists really isn't all that
difficult. What I found a bit difficult was understand the use of such
constructs. A bit different from just passing arguments. But the use of the
RECORD construct in Basic allows various item list structures to be defined and
easily used. User friendly is nice, but sometimes we have to do some things the
old fashioned way, it's called "work".

Since we're bashing VMS a bit, one of the rather inconsistencies is having the
common calling standard, well except for C, allowing the easy use of multiple
languages, but not supplying all the compilers as one package for development.
What good is being able to use one of the languages to do something that's easy
in that language, if that compiler is not available?

It would be rather trivial to set up a Basic routine with the required
constructs. I'm guessing that Brian's customer doesn't have a Basic compiler.
And to give Steve more ammunition, Basic doesn't (as far as I know) have a
pointer data type.

:-)
--
David Froble Tel: 724-529-0450
Dave Froble Enterprises, Inc. E-Mail: ***@tsoft-inc.com
DFE Ultralights, Inc.
170 Grimplin Road
Vanderbilt, PA 15486
Stephen Hoffman
2017-12-27 01:19:55 UTC
Permalink
Post by DaveFroble
Well, since you mentioned Basic, using item lists really isn't all that
difficult.
Sure, other than that itemlists are a complete waste of time and effort
and coding and debugging and the rest. Itemlists in BASIC are a joke.
Itemlists in COBOL are a joke. Itemlists in C are a joke.
Itemlists in Macro32 and Bliss are arguably slightly better than most
other languages and the explicit arrays, as the itemlist baggage can be
hidden behind some language-specific macros. Now if you're getting the
impression that I'm not fond of itemlists as an API data structure, you
might be right. (I've come around from my previous delight over that
particular API design, too.) Because whether itemlists are considered
simple or familiar or "just a little glue code" or the rest of why we
get to deal with the resulting morass, itemlists are a pile of code
that's been pushed from the frameworks developers up into the purview
of the app developers. Even more inexplicably, the platform
developers didn't provide themselves with APIs that allowed generic
access to pack and unpack itemlists. It's just absurd. Then we get
to debug the code when somebody misses a null or an index or whatever
the trigger for the usual sorts of itemlist bugs, and we get to ignore
the itemlist code when we're looking at the app-relevant code. If we
didn't have that code, we wouldn't have that code — we'd have common
code that dealt with the usual causes, allowing us to spend more time
on the apps or on the frameworks, and less on what tend to be very
complex APIs.
--
Pure Personal Opinion | HoffmanLabs LLC
DaveFroble
2017-12-27 02:53:50 UTC
Permalink
Post by Stephen Hoffman
Post by DaveFroble
Well, since you mentioned Basic, using item lists really isn't all
that difficult.
Sure, other than that itemlists are a complete waste of time and effort
and coding and debugging and the rest.
I agree, the scheme is rather archaic, and, was developed in the past when
memory was an issue. Today, where appropriate, one should just call the seytem
service, and get back all possible data. There may be some that that is labor
intensive, but, with today's CPUs, is that still an issue.

To be specific, I agree with you on item lists.
Post by Stephen Hoffman
Itemlists in BASIC are a joke.
Well, not if you set up a decent method to use them. If you have a structure
it's rather easy to populate it. I have developed user defined variables for
item lists.
Post by Stephen Hoffman
Itemlists in COBOL are a joke. Itemlists in C are a joke.
Itemlists in Macro32 and Bliss are arguably slightly better than most
other languages and the explicit arrays, as the itemlist baggage can be
hidden behind some language-specific macros. Now if you're getting the
impression that I'm not fond of itemlists as an API data structure, you
might be right. (I've come around from my previous delight over that
particular API design, too.) Because whether itemlists are considered
simple or familiar or "just a little glue code" or the rest of why we
get to deal with the resulting morass, itemlists are a pile of code
that's been pushed from the frameworks developers up into the purview of
the app developers. Even more inexplicably, the platform developers
didn't provide themselves with APIs that allowed generic access to pack
and unpack itemlists. It's just absurd. Then we get to debug the code
when somebody misses a null or an index or whatever the trigger for the
usual sorts of itemlist bugs, and we get to ignore the itemlist code
when we're looking at the app-relevant code. If we didn't have that
code, we wouldn't have that code — we'd have common code that dealt with
the usual causes, allowing us to spend more time on the apps or on the
frameworks, and less on what tend to be very complex APIs.
In general, I agree ...
--
David Froble Tel: 724-529-0450
Dave Froble Enterprises, Inc. E-Mail: ***@tsoft-inc.com
DFE Ultralights, Inc.
170 Grimplin Road
Vanderbilt, PA 15486
V***@SendSpamHere.ORG
2017-12-27 18:45:12 UTC
Permalink
Post by Stephen Hoffman
Post by Arne Vajhøj
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them --
it's NOT COBOL code but it IS called by them from their COBOL.
....
I know nothing about COBOL, but would it by an option to let them pass
a variable number of arguments of type descriptor to string?
...
It should be easy to create an array of descriptors from this on the C side.
At the risk of asking a stupid question, why not expose a
COBOL-friendly API into some C code, and allow that C code to construct
the necessary descriptor for SMG or whatever. Then pass the address
or whatever back to the calling code, so it can be passed into "other"
API.
There's no other code and has nothing to do with SMG. COBOL is the construct
arcane here. Fortran, for example, will create and pass an array descriptor.
SMG was mentioned because it's one of the VMS interfaces which accepts array
descriptors.
Post by Stephen Hoffman
Or as has been suggested previously here, expose a
variable-length argument list call to the users and stop trying to
recreate one of the most arcane APIs in OpenVMS? The
variable-argument call can then construct the "architecturally pure"
descriptor array, if that's deemed appropriate. These cases placing
more of a focus on the folks that have to create the glue code and to
figure out and call the routines in the API, and not so much on the
architectural astronautics and the complexity that parts of the OpenVMS
APIs have become infamous for. SMG is infamous for that
SMG$CREATE_MENU_WITH_GREAT_API_COMPLEXITY call, after all.
You really hate the hand that fed you.

The customer already has an API; I provided it to them. It takes 6 strings
passed by descriptor. They've asked me to augment it with new features but
they do NOT want to have to go back and modify their existing code to call
it. THerefore, I can check for a string descriptor or an array descriptor
and handle the passed data appropriately.
Post by Stephen Hoffman
This whole mess makes me really appreciate how easy objects are to deal
with here, too. Where all of the shenanigans around descriptor
creation and access are managed for the developer, and where changes
don't ripple through the APIs, and where you can pass around different
sorts of data — a 32-bit descriptor, a 64-bit descriptor, an array of
descriptors, or the equivalent of an entry point and sharable image for
that matter, and with the string encoding and other metadata easily
encoded — and the called code can more easily deal with what gets
passed on. But we're not there yet with OpenVMS, and we still have to
hand-construct descriptors and the rest, and where the APIs and the
called code — even in the "descriptor-friendly" programming languages —
is far more brittle. Descriptors from C, C++, Bliss, Macro32 and ilk
all seem like using a crayon. Descriptors from BASIC and other
"descriptor-friendly" languages aren't all that much better, even
though (often) less work is involved. Then there are itemlists, which
are ugly in all of the languages. It's absurd that we're still futzing
around with those forty years on. Ah, well.
Wow. Too bad the crap I have had to deal with at GIThub doesn't use any of
those wonderful objects.
--
VAXman- A Bored Certified VMS Kernel Mode Hacker VAXman(at)TMESIS(dot)ORG

I speak to machines with the voice of humanity.
Richard Maher
2017-12-23 01:30:57 UTC
Permalink
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
Salacious Saturnalia to all!!!
Yes it's very doable and I have some code that calls the smg$menu
routines lying around but I haven't booted my machines for some time.

I'm sure I've posted them here before so I'll look around. Basically you
just build the array descriptor yourself.

01 my_desc.
03 desc$_class_a_or_something pic 9(9) comp value external
desc$_class_a.
03 start_from_0_or_1 pic 9(9) comp value 0.
03 pointer value reference my_list_of_choices.
03 choice_len pic 9(4) comp value 20.
03 choice_cnt pic 9(4) comp value 2.

01 my_list_choices.
03 choice_one pic x(20) value "one".
03 choice_2 pic x(20) value "two".

Then call "your_routine" using by reference my_desc.

The above is obviously not accurate but look at the descriptor manual
and remember a longword is pic9(9) comp a word is pic 9(4) comp and for
a byte you use pic x(1) and can use hexadecimal literals value x"20".

I'll look for that real example now.

Merry Christmas and a happy New Year to one and all!

Richard Maher
Richard Maher
2017-12-23 01:40:34 UTC
Permalink
Post by Richard Maher
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them.  If it's possible to EASILY create an array of string
descriptors
using COBOL?  I can keep the present interface -- meaning they d/won't
need
to touch their existing code --  by allowing an array of descriptors
to be
passed, I can provide them with what they want me to augment.  I'll
need an
array of strings akin to that which would be passed to the
SMG$CREATE_MENU's
<choices> parameter.  I'm no COBOL programmer and I find PIC
statements mind-
numbing.  If there's a COBOL example calling SMG$CREATE_MENU, that'd
probably
get me  over the current hurdle if somebody can point me to it.
Salacious Saturnalia to all!!!
Yes it's very doable and I have some code that calls the smg$menu
routines lying around but I haven't booted my machines for some time.
I'm sure I've posted them here before so I'll look around. Basically you
just build the array descriptor yourself.
01  my_desc.
    03 desc$_class_a_or_something pic 9(9) comp value external
desc$_class_a.
    03 start_from_0_or_1 pic 9(9) comp value 0.
    03 pointer value reference my_list_of_choices.
    03 choice_len pic 9(4) comp value 20.
    03 choice_cnt pic 9(4) comp value 2.
01 my_list_choices.
   03  choice_one pic x(20) value "one".
   03  choice_2   pic x(20) value "two".
Then call "your_routine" using by reference my_desc.
The above is obviously not accurate but look at the descriptor manual
and remember a longword is pic9(9) comp a word is pic 9(4) comp and for
a byte you use pic x(1) and can use hexadecimal literals value x"20".
I'll look for that real example now.
Merry Christmas and a happy New Year to one and all!
Richard Maher
That didn't take long: -
https://groups.google.com/forum/#!searchin/comp.os.vms/smg$24create_menu%7Csort:date/comp.os.vms/fVC97mV-Vrk/dD6DQWL4BAAJ
Paul Sture
2017-12-23 10:55:46 UTC
Permalink
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
I see Richard has provided an example. It can sometimes be handy to go
the other way around and pass string descriptors when calling COBOL.

COBOL doesn't support BY DESCRIPTOR in the LINKAGE SECTION, everything
comes BY REFERENCE. LIB$ANALYZE_SDESC, LIB$ANALYZE_SDESC_64,
STR$ANALYZE_SDESC, or STR$ANALYZE_SDESC_64 are your friends here (or you
can unpick the descriptors yourself if that suits).
Post by V***@SendSpamHere.ORG
Salacious Saturnalia to all!!!
Have a good 'un everyone!
--
Never underestimate the bandwidth of sending the office gossip for the
coffee every day...
V***@SendSpamHere.ORG
2017-12-23 12:19:45 UTC
Permalink
Post by Paul Sture
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
I see Richard has provided an example. It can sometimes be handy to go
the other way around and pass string descriptors when calling COBOL.
I found an old post from Hein wherein he showed how to call SMG$CREATE_MENU.
I'll hand that off to the customer.
Post by Paul Sture
COBOL doesn't support BY DESCRIPTOR in the LINKAGE SECTION, everything
comes BY REFERENCE. LIB$ANALYZE_SDESC, LIB$ANALYZE_SDESC_64,
STR$ANALYZE_SDESC, or STR$ANALYZE_SDESC_64 are your friends here (or you
can unpick the descriptors yourself if that suits).
I'm not writing COBOL, the client is. I just need a list of strings from
their programs. I looked at Hein's and Richard's examples -- More PICs
than I can put on my 128GB CF cards -- and I still don't quite grasp all
of the lingo.
--
VAXman- A Bored Certified VMS Kernel Mode Hacker VAXman(at)TMESIS(dot)ORG

I speak to machines with the voice of humanity.
Arne Vajhøj
2017-12-23 16:30:37 UTC
Permalink
Post by V***@SendSpamHere.ORG
Post by Paul Sture
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
I see Richard has provided an example. It can sometimes be handy to go
the other way around and pass string descriptors when calling COBOL.
I found an old post from Hein wherein he showed how to call SMG$CREATE_MENU.
I'll hand that off to the customer.
Post by Paul Sture
COBOL doesn't support BY DESCRIPTOR in the LINKAGE SECTION, everything
comes BY REFERENCE. LIB$ANALYZE_SDESC, LIB$ANALYZE_SDESC_64,
STR$ANALYZE_SDESC, or STR$ANALYZE_SDESC_64 are your friends here (or you
can unpick the descriptors yourself if that suits).
I'm not writing COBOL, the client is. I just need a list of strings from
their programs. I looked at Hein's and Richard's examples -- More PICs
than I can put on my 128GB CF cards -- and I still don't quite grasp all
of the lingo.
If they are really good good at VMS COBOL then they will figure it out.

If they are just good at COBOL then I suggest you go with the variable
number of arguments and a little bit of shuffling on the C side.

Arne
Richard Maher
2017-12-24 00:15:50 UTC
Permalink
Post by V***@SendSpamHere.ORG
Post by Paul Sture
Post by V***@SendSpamHere.ORG
A client has asked me to augment some code I've written for them -- it's NOT
COBOL code but it IS called by them from their COBOL.
There are a number of arguments passed to this procedure that I have created
for them. If it's possible to EASILY create an array of string descriptors
using COBOL? I can keep the present interface -- meaning they d/won't need
to touch their existing code -- by allowing an array of descriptors to be
passed, I can provide them with what they want me to augment. I'll need an
array of strings akin to that which would be passed to the SMG$CREATE_MENU's
<choices> parameter. I'm no COBOL programmer and I find PIC statements mind-
numbing. If there's a COBOL example calling SMG$CREATE_MENU, that'd probably
get me over the current hurdle if somebody can point me to it.
I see Richard has provided an example. It can sometimes be handy to go
the other way around and pass string descriptors when calling COBOL.
I found an old post from Hein wherein he showed how to call SMG$CREATE_MENU.
I'll hand that off to the customer.
Post by Paul Sture
COBOL doesn't support BY DESCRIPTOR in the LINKAGE SECTION, everything
comes BY REFERENCE. LIB$ANALYZE_SDESC, LIB$ANALYZE_SDESC_64,
STR$ANALYZE_SDESC, or STR$ANALYZE_SDESC_64 are your friends here (or you
can unpick the descriptors yourself if that suits).
I'm not writing COBOL, the client is. I just need a list of strings from
their programs. I looked at Hein's and Richard's examples -- More PICs
than I can put on my 128GB CF cards -- and I still don't quite grasp all
of the lingo.
The reply immediate prior to the one I provided a pointer to has a
simple example.
Richard Maher
2017-12-24 02:49:57 UTC
Permalink
Post by V***@SendSpamHere.ORG
I found an old post from Hein wherein he showed how to call SMG$CREATE_MENU.
I'll hand that off to the customer.
I'm not writing COBOL, the client is. I just need a list of strings from
their programs. I looked at Hein's and Richard's examples -- More PICs
than I can put on my 128GB CF cards -- and I still don't quite grasp all
of the lingo.
Should be straight forward for anyone who's ever used smg$: -

identification division.
program-id. pull_down_menu.
data division.
working-storage section.
01 array_desc.
03 element_len pic 9(4) comp
value 16.
03 dtype pic x
value x"0e".
03 dclass pic x
value x"04".
03 data_pointer pointer
value reference choices.
03 pic 9(4) comp.
03 flags pic x
value low-value.
03 dimct pic x
value x"01".
03 total_bytes pic 9(9) comp
value 320.
03 element_zero pic 9(9) comp.
03 stride pic 9(9) comp
value 20.
03 lwr_b pic 9(9) comp
value 1.
03 upr_b pic 9(9) comp
value 20.
01 choices.
03 pic x(16)
value "one".
03 pic x(16)
value "two".
03 pic x(16)
value "three".
03 pic x(16)
value "four".
03 pic x(16)
value "five".
03 pic x(16)
value "six".
03 pic x(16)
value "seven".
03 pic x(16)
value "eight".
03 pic x(16)
value "nine".
03 pic x(16)
value "ten".
03 pic x(16)
value "eleven".
03 pic x(16)
value "twelve".
03 pic x(16)
value "thirteen".
03 pic x(16)
value "fourteen".
03 pic x(16)
value "fifteen".
03 pic x(16)
value "sixteen".
03 pic x(16)
value "seventeen".
03 pic x(16)
value "eighteen".
03 pic x(16)
value "nineteen".
03 pic x(16)
value "twenty".
*
01 tm_desc.
03 pic 9(9) comp
value 32.
03 pointer
value reference terminator_mask.
01 terminator_mask.
03 pic 9(9) comp
occurs 8.
*+
* COBOL is a bit untidy when it comes to byte data
*_
01 cvt_num pic 9(4) comp.
01 cvt_char redefines cvt_num.
03 active_byte pic x.
03 pic x.
*_
01 pasteboard_id pic 9(9)
comp.
01 keyboard_id pic 9(9) comp.
01 menu_display pic 9(9)
comp.
01 screen_display pic 9(9)
comp.
01 row_cnt pic 9(9)
comp.
01 col_cnt pic 9(9)
comp.
01 menu_rows pic 9(9) comp.
01 menu_cols pic 9(9) comp.
01 option pic 9(4)
comp.
01 option_string pic x(16).
01 default_choice pic 9(4)
comp value 15.
01 terminator pic 9(4) comp.
01 sys_status pic 9(9) comp.
01 ss$_normal pic 9(9) comp
value external ss$_normal.
01 lib$_strtru pic 9(9) comp
value external lib$_strtru.
01 smg$_eof pic 9(9) comp
value external smg$_eof.
01 smg$_invarg pic 9(9) comp
value external smg$_invarg.
01 smg$m_keep_contents pic 9(9) comp
value external smg$m_keep_contents.
01 smg$m_remove_item pic 9(9) comp
value external smg$m_return_immed.
01 smg$m_bold pic 9(9) comp
value external smg$m_bold.
01 smg$m_reverse pic 9(9)
comp value external smg$m_reverse.
01 smg$m_border pic 9(9)
comp value external smg$m_border.
01 smg$m_fixed_format pic 9(9) comp
value external smg$m_fixed_format.
01 smg$k_vertical pic 9(9)
comp value external smg$k_vertical.
01 smg$m_cursor_on pic 9(9)
comp value external smg$m_cursor_on.
01 smg$m_cursor_off pic 9(9) comp
value external smg$m_cursor_off.
01 ctrl_key pic x(4).
procedure division.
00.
subtract element_len from data_pointer giving element_zero.
call "smg$create_pasteboard"
using pasteboard_id, omitted, row_cnt,
col_cnt, smg$m_keep_contents
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$create_virtual_keyboard" using keyboard_id giving
sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$create_virtual_display"
using row_cnt, col_cnt, screen_display
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

move 1 to row_cnt, col_cnt.
call "smg$paste_virtual_display"
using screen_display, pasteboard_id,
row_cnt, col_cnt
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

move 20 to menu_cols.
move 10 to menu_rows.
call "smg$create_virtual_display"
using menu_rows, menu_cols,
menu_display, smg$m_border, smg$m_bold
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$label_border"
using by reference menu_display
by descriptor "selection window"
by value 0, 0
by reference smg$m_reverse, smg$m_bold
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

move 2 to menu_rows.
call "smg$create_menu"
using menu_display, array_desc, smg$k_vertical,
smg$m_fixed_format, menu_rows
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

move 10 to menu_cols.
call "smg$paste_virtual_display"
using menu_display, pasteboard_id,
menu_rows, menu_cols
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$set_cursor_mode" using pasteboard_id, smg$m_cursor_off
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

perform with test after until sys_status not = ss$_normal
call "smg$select_from_menu"
using by reference keyboard_id, menu_display, option,
by reference default_choice, smg$m_remove_item
by value 0, 0
by reference terminator
by descriptor option_string
by reference smg$m_reverse, smg$m_bold
giving sys_status
display "term = " terminator with conversion
end-perform.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.
* if sys_status not = smg$_eof and smg$_invarg call "lib$stop" using
by value sys_status.

call "smg$set_cursor_mode" using pasteboard_id, smg$m_cursor_on
giving sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$delete_virtual_display" using menu_display giving
sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

call "smg$delete_virtual_display" using screen_display giving
sys_status.
if sys_status not = ss$_normal call "lib$stop" using by value
sys_status.

stop run.

end program pull_down_menu.
V***@SendSpamHere.ORG
2017-12-24 16:40:49 UTC
Permalink
Post by Richard Maher
Post by V***@SendSpamHere.ORG
I found an old post from Hein wherein he showed how to call SMG$CREATE_MENU.
I'll hand that off to the customer.
I'm not writing COBOL, the client is. I just need a list of strings from
their programs. I looked at Hein's and Richard's examples -- More PICs
than I can put on my 128GB CF cards -- and I still don't quite grasp all
of the lingo.
Should be straight forward for anyone who's ever used smg$: -
SMG$ is straight forward, it's the COBOL that's not.
Post by Richard Maher
identification division.
program-id. pull_down_menu.
data division.
working-storage section.
01 array_desc.
03 element_len pic 9(4) comp
value 16.
03 dtype pic x
value x"0e".
%x0E => 14 => DSC$K_DTYPE_T
Post by Richard Maher
03 dclass pic x
value x"04".
%x04 => 4 => DSC$K_CLASS_A


Is there anyway to define these symbolically?
Post by Richard Maher
03 data_pointer pointer
value reference choices.
03 pic 9(4) comp.
03 flags pic x
value low-value.
03 dimct pic x
value x"01".
03 total_bytes pic 9(9) comp
value 320.
03 element_zero pic 9(9) comp.
03 stride pic 9(9) comp
value 20.
03 lwr_b pic 9(9) comp
value 1.
03 upr_b pic 9(9) comp
value 20.
01 choices.
03 pic x(16)
value "one".
03 pic x(16)
value "two".
03 pic x(16)
value "three".
03 pic x(16)
value "four".
03 pic x(16)
value "five".
03 pic x(16)
value "six".
03 pic x(16)
value "seven".
03 pic x(16)
value "eight".
03 pic x(16)
value "nine".
03 pic x(16)
value "ten".
03 pic x(16)
value "eleven".
03 pic x(16)
value "twelve".
03 pic x(16)
value "thirteen".
03 pic x(16)
value "fourteen".
03 pic x(16)
value "fifteen".
03 pic x(16)
value "sixteen".
03 pic x(16)
value "seventeen".
03 pic x(16)
value "eighteen".
03 pic x(16)
value "nineteen".
03 pic x(16)
value "twenty".
*
I think I can piece together these bits to see the array descriptor.

Thanks.
--
VAXman- A Bored Certified VMS Kernel Mode Hacker VAXman(at)TMESIS(dot)ORG

I speak to machines with the voice of humanity.
Richard Maher
2017-12-25 23:12:09 UTC
Permalink
Post by V***@SendSpamHere.ORG
Post by Richard Maher
01 array_desc.
03 element_len pic 9(4) comp
value 16.
03 dtype pic x
value x"0e".
%x0E => 14 => DSC$K_DTYPE_T
Post by Richard Maher
03 dclass pic x
value x"04".
%x04 => 4 => DSC$K_CLASS_A
Is there anyway to define these symbolically?
One of the view short-comings of COBOL is that it doesn't support Byte
Integers easily.

You can do it the long way: -

01 DSC$K_DTYPE_T pic 9(4) comp value external DSC$K_DTYPE_T.
01 DSC$K_CLASS_A pic 9(4) comp value external DSC$K_CLASS_A.
*+
* COBOL is a bit untidy when it comes to byte data
*_
01 cvt_num pic 9(4) comp.
01 cvt_char redefines cvt_num.
03 active_byte pic x.
03 pic x.
*
procedure division.
00.
move DSC$K_DTYPE_T to cvt_num.
move active_byte to dtype.
move DSC$K_CLASS_A to cvt_num.
move active_byte to dclass.

Or if you already have a small macro file you're linking in, you can
declare the descriptor as EXTERNAL in COBOL which will allow you to
overlay a global psect of the same name as you Macro definition.

01 menu_desc external.
03 cell_size pic 9(4) comp.
03 dtype pic x(1).
03 dclass pic x(1).
03 base_addr pointer.
03 pic 9(4) comp.
03 flags pic x(1).
03 dimct pic x(1).
03 bytes_allocated pic 9(9) comp.
03 element_zero pic 9(9) comp.
03 stride pic 9(9) comp.
03 lwr_b pic 9(9) comp.
03 line_count pic 9(9) comp.
*

Or you can define your own symbols

environment division.
configuration section.
special-names.
symbolic characters
carriage_return is 14
line_feed is 11.

data division.
working-storage section.

01 crlf.
03 pic x(1) value
carriage_return.
03 pic x(1) value
line_feed.

Or just stick with hexadecimal strings.
Neil Rieck
2017-12-25 16:40:38 UTC
Permalink
On Friday, December 22, 2017 at 4:40:44 PM UTC-5, VAXman- wrote:

[...snip...]

"I think" all so-called "DEC Languages" handle the passing of strings and arrays in a similar way (the main exceptions being C and C++ which do not "natively" employ VMS descriptors; but support for them can be easily enabled)

I previously had lots of experience passing "arrays of long" and "arrays of string" between VMS-BASIC programs and functions. But back in 2014 I needed to better understand this in order to pass arrays from VMS-BASIC to VMS-C and back.

So I wrote five hybrid demos in order to get a better grasp on the underlying data format. They all begin here:

http://neilrieck.net/demo_vms_html/openvms_demo_index.html#hybrid

Note: to learn how to declare your COBOL passing mechanisms just check out the declarations in the BASIC demos. No need to inspect the C demos unless you are a true masochist.

Neil Rieck
Waterloo, Ontario, Canada.
http://neilrieck.net
Loading...