Calling Subprograms [ Micro Focus COBOL for UNIX COBOL User Guide ] MPE/iX 5.0 Documentation
Micro Focus COBOL for UNIX COBOL User Guide
Calling Subprograms
This section looks in more detail at how to call subprograms. It
provides information on writing subprograms and passing parameters
between them.
You can write subprograms or your main programs in the COBOL language or
in some other language, such as C. You can mix these subprograms freely
in an application. However, before you call a non-COBOL subprogram from
a COBOL program, you must link it to either the dynamic loader run-time
support module or to your statically or dynamically linked COBOL
application.
Calling COBOL Subprograms
A COBOL subprogram can be:
* Statically or dynamically linked using the cob command
* Dynamically loaded at run time.
A statically linked program is an executable object module, while a
dynamically loadable module is either a COBOL intermediate code (.int)
file or a COBOL native code (.gnt) file.
You can call a COBOL subprogram by using one of the following formats of
the call statement:
call "literal" using ...
or:
call data-name using ...
For any COBOL programs, the literal string or the contents of the
alphanumeric data item contains the Program-ID, the entry point name, or
the base-name of the source file (that is, the file-name without any
extension). The path and file-name for a module can also be specified
when referencing a COBOL program. We do not recommend you do this as
unexpected results can occur where the referenced module exists in more
than one file or type of format, or if the application is ported to other
environments.
For statically linked modules the native code generator converts calls
with literal strings to subroutine calls which refer to external symbols.
If the symbol has not been defined when linking is performed, it is
assumed to be the name of a file to be dynamically loaded, provided you
specify the -d flag on the cob command line (see your COBOL System
Reference for details of cob flags). This COBOL system automatically
creates a routine to define the symbol and to load the associated file if
it is entered at run-time.
NOTE Programs that are called at link time must have names that the
system assembler and linker can accept; that is, they must not
contain characters other than 0-9, A-Z, a-z, underscore (_), or
hyphen (-). See the section Entry-point Naming Conventions later
in this chapter.
Calling Statically or Dynamically Linked Programs.
Use a CALL literal statement to call a statically or dynamically linked
program directly.
Calling Dynamically Loadable Programs.
To make the dynamic loader run-time support module search for the called
program at run time, use a CALL literal statement to a dynamically
loadable program, or a CALL data-name statement.
The dynamic loader run-time support module searches the following for the
called name:
1. The entry points contained in all loaded programs
2. The disk in order to find a suitable file from which the program
could be loaded.
If the COBOL program is referenced as a file-name, then before starting
this search operation, the dynamic loader run-time support module splits
the required program name into its component parts - path, base-name, and
extension.
The dynamic loader run-time support module does not use the path portion
of the program name in its search of loaded programs. It compares the
base-name with the entry point names of all loaded programs. If you
specify no extension, then the first matching name that the dynamic
loader run-time support module finds is assumed to be the program which
you want to call. If you do specify an extension, then the extension of
the loaded program must be the same if a match is to be made. Alternate
entry points to programs are treated as if they had the extension of the
file from which they were loaded.
If the dynamic loader run-time support module has to search for a file on
disk, it searches for it directory by directory, then extension by
extension in each directory. If you specify a directory path, the
dynamic loader run-time support module searches for the file only in the
named directory.
When a call specifies a file with no path name, then the search order is
as follows:
1. The directories specified by the COBPATH environment variable. If
COBPATH is not set, theis is the current directory.
2. The directory from which the calling program was loaded for the
named file
3. The directory specified by the COBDIR environment variable.
The order of searching is different on previous COBOL systems. The first
two items are searched in the opposite order. A cobconfig tunable is
available to maintain compatibility with older systems. See your COBOL
System Reference for more details.
You can set COBPATH to a value of the form:
[:] path-name [:path-name] ...
For example:
COBPATH=/u:/v:/cdw/srclib:/cdw/otherlib
export COBPATH
If you include the optional colon (:) at the beginning of the string,
the dynamic loader run-time support module assumes the current directory
is the first one to be searched.
See your COBOL System Reference for further details on COBPATH and
COBDIR.
If you specify a file extension, the dynamic loader run-time support
module searches only for a file with a matching extension. However, you
are not recommended to include the extensions .int and .gnt in the
file-names you specify to the CALL statement. If you specify a file
without an extension, the dynamic loader run-time support module uses the
following algorithm to search for it:
1. If the file is not linked with the COBOL libraries, the dynamic
loader run-time support module adds the extension .gnt to the
base-name of the file and tries to find the corresponding native
code file on disk.
2. If it cannot find the native code file on disk, it adds the
extension .int to the base-name of the file, and searches the disk
for the corresponding intermediate code file.
The dynamic loader run-time support module always assumes that the first
matching program name which it finds is the program you require to call.
If no matching program is found a run-time error occurs.
If the first character of a file-name which is to be dynamically loaded
at run time is the dollar sign ($), the first element of the file-name is
checked for file-name mapping. The first element of the file-name
consists of all the characters before the first forward slash character
(/). See the chapter File Handling in your COBOL System Reference for
details. For example, if the statement:
call "$MYLIB/a"
is found in the source program, the file a is loaded from the path as
defined by the MYLIB environment variable at run-time.
Calling Dynamically Loadable COBOL Programs via Entry Points.
Micro Focus COBOL enables you to define multiple entry points to a
dynamically loaded program using the ENTRY statement. You can call a
program either via the main entry point (at the start of the Procedure
Division) or via one of the points in the program marked by an ENTRY
statement. See your Language Reference for a description of the ENTRY
statement. This facility is designed primarily for compatibility with
other COBOL environments; we do not recommend you use it for other
purposes because of the special considerations listed in the remainder of
this section.
Command Line Syntax.
You can call a dynamically loadable program via an entry point in the
same way that you would call it via its main entry point; that is:
call name using parameters
where the parameters are:
name The name defined in the ENTRY statement that defines
the entry point you are using
parameters A list of parameters in the range 0 to 127. You can
specify different parameters at different entry
points in the same program.
There are certain features that you need to be aware of when calling
dynamically loadable programs via entry points. To illustrate these
features we will use as an example a program structured as follows:
procedure division using param-1,param-2.
first-para.
. . .
. . .
entry "other" using param-3,param-4,param-5.
. . .
. . .
via main entry point.
If you call this program via its main entry point, as follows:
call "mainprog" using par-1,par-2.
the dynamic loader run-time support module loads the program and notes
the names of any other entry points it contains. When you subsequently
call the same program via its other entry point, as follows:
call "other" using par-3,par-4,par-5.
the dynamic loader run-time support module detects that the program
containing this entry point is already loaded (assuming that you have not
canceled the program).
via "other" entry point.
If your first entry to a program is via the entry point "other" rather
than by the main entry point, the dynamic loader run-time support module
is not able to associate the entry point "other" with the program
"mainprog.int", so it is unable to load the program. You can solve this
problem by creating a link between mainprog.int and the entry point
"other", using the UNIX command ln, as follows:
ln mainprog.int other.int
via entry point in a segment.
If you are calling via an entry point in an overlay segment, you must
also establish a link between the intermediate code overlay file and the
entry point. For example, if you are calling via an entry point "other"
in mainprog.int, that is located in a section with segment number 52, you
would have to create a link as follows:
ln mainprog.i52 other.i52
Similarly, if you have a generated code version of mainprog you can link
this version of the program with the entry point "other", as follows:
ln mainprog.gnt other.gnt
If you are calling via an entry point in an overlay segment, you must
also establish a link between the generated code overlay file and the
entry point. For example:
ln mainprog.g52 other.g52
If you are animating a program that is being entered initially by an
entry point other than the main entry point, you must establish a link
between the .idy file used by Animator and the entry point. For example:
ln mainprog.idy other.idy
avoiding duplicate copies.
However, you might still experience problems if you want to call the
program again later using the main entry point rather than "other". When
you call a program via any of its entry points, the dynamic loader
run-time support module picks up the references to all its other entry
points. Unless your program has a program name assigned to it in the
Program-ID paragraph, the main entry point does not have a name
associated with it. The consequence is that if you call the above
program by:
call "other" using...
and later call the same program again by:
call "mainprog" using...
the dynamic loader run-time support module, not being aware of a "main"
entry point, does not detect that the program is already loaded and loads
a duplicate copy. This wastes memory unnecessarily. However, the
dynamic loader run-time support module does detect that the program it
has just loaded duplicates the names of some entry points of which it was
already aware, and so outputs error 119 "symbol redefined". See your
Error Messages manual for details of this message.
Although loading duplicate copies of programs wastes memory, it also
causes you another problem. When the dynamic loader run-time support
module loads a program, it initializes the area of memory holding the
program's data so that the data is initially either undefined or has the
initial values assigned to it by the VALUE clauses in the Data Division.
If you exit from the program without canceling the memory it occupies,
when you reenter the program, its data is in the state in which the
program left it.
You can make the dynamic loader run-time support module aware of the main
entry point of a program that you enter via another entry point
by including a program name in the Program-ID paragraph in the
Identification Division of your program. For example:
identification division.
program-id. mainprog.
Now when you call the program, the dynamic loader run-time support module
is aware of the entry point mainprog. Consequently, to reenter the
program successfully via the main entry point after having entered it
first via the "other" entry point, you would have to use:
call "mainprog" using...
via the Program-ID entry point
If you call a program via the Program-ID entry point, then this is case
sensitive. By default, you must specify the program name in lower case
in the Program-ID paragraph as shown in the above example; you could not
call this program with:
call "MAINPROG" using...
You should be aware when using multiple entry points in programs that
this is regarded in many circles as bad programming practice. We
recommend that if you do use multiple entry points, you avoid entering a
program for the first time via an entry point other than the main entry
point.
Entry-point Naming Conventions.
Following the IBM conventions and in order to ensure complete portability
of your applications, we recommend you use only digits and upper-case
letters in your Program-ID and entry point names. If the first character
of a program name (that is the file-name of the source code, the
Program-ID name and any entry point name defined in an ENTRY statement)
is not alphabetical, it is mapped to an alphabetical character as
follows, so that it can be referenced either by its original name or by
the name resulting from this conversion:
0 converts to J
1-9 converts to A-I
This applies only if the digit is in the first character position of the
program-name. If your program-name contains a hyphen, this is mapped to
zero such that it can be referenced with either a hyphen or a zero,
regardless of it position in the name.
The dynamic loader run-time support module converts the names of all
calls before searching for the program in memory. If the program is not
found in memory, an attempt is made to load it from disk using the
unmapped name. Hence, the first time a program is called, you must use
the program file-name; that is, the Program-ID. A hyphen, therefore,
might be accepted. After loading, however, the program name and entry
point names are held by the dynamic loader run time support module in
their unmapped format.
You must not use entirely numeric call names as COBOL Program-IDs as
these are reserved by the COBOL system. This is for compatibility with
the way in which non-COBOL programs were called in previous Micro Focus
COBOL systems. See the chapter Portability Issues for full details.
MPE/iX 5.0 Documentation