Call Binding [ HP COBOL II/XL Programmer's Guide ] MPE/iX 5.0 Documentation
HP COBOL II/XL Programmer's Guide
Call Binding
The process of matching a subprogram call or an intrinsic call to its
definition is called call binding. Call binding can occur at compile
time, link time, load time, or execution time. Different subprograms
called by the same program can be bound differently.
Subprogram Libraries
If your program contains a subprogram that other programs call, you may
decide to put the subprogram in a library, making it available to other
programs.
If you decide to put the subprogram in a library, you must decide what
kind of library. The kinds of libraries are relocatable library (RL) and
executable library (XL). In deciding, you should ask yourself:
1. How important is the size of the calling program?
If you want the calling program to be as small as possible, you
should use the executable library or XL.
2. How important is the execution speed of the calling program?
If you want the calling program to execute as fast as possible,
you should use the relocatable library or RL.
3. Will the subprogram need changes -- fixes or updates -- that are
independent of the calling program?
If the subprogram will need changes that are independent of the
calling program, put it in an executable library. Then, when you
change the subprogram, you will not have to relink every program
that calls it.
It is recommended that you use the XL parameter (of the RUN command or
Link Editor) to specify the name of the executable library that contains
the subprogram. The alternative, which is only available if the
executable library name is XL, is not portable (it is to let the RUN
command reference the library with LIB=S (the default), LIB=P, or LIB=G).
Compile-Time Binding
Compile-time binding is performed by the compiler. It can only happen
when the CALL or CANCEL target is a nested or concatenated program in the
current source file.
The advantages of compile-time binding are:
* Calls to subprograms bound at compile time are faster than calls
to subprograms bound at load time or execution time (but are the
same speed as calls bound at link time).
* The program file is portable.
The program file contains all the information that it needs to
resolve calls to the subprogram. Other programmers can use your
program without additional executable libraries.
The disadvantages of compile-time binding are:
* The program file is larger than it would be if it were bound at
load time or execution time (but the same size as it would be if
it were bound at link time).
* If you change any nested program, you must recompile and relink
the program that contains it.
Terminology.
The call rules that apply to subprograms bound at compile time require
the introduction of new terminology, which is most easily explained with
an example.
Example.
IDENTIFICATION DIVISION.
PROGRAM-ID. OUTER. Outermost program.
PROCEDURE DIVISION.
BEGIN-OUTER.
IDENTIFICATION DIVISION.
PROGRAM-ID. MIDDLE. Nested program.
PROCEDURE DIVISION.
BEGIN-MIDDLE.
IDENTIFICATION DIVISION.
PROGRAM-ID. INNER.
Nested program.
PROCEDURE DIVISION.
BEGIN-INNER.
END PROGRAM INNER.
END PROGRAM MIDDLE.
END PROGRAM OUTER.
IDENTIFICATION DIVISION.
PROGRAM-ID. NEXT. Concatenated program.
PROCEDURE DIVISION.
BEGIN-NEXT.
END PROGRAM NEXT.
In the above program, OUTER is the outermost program, MIDDLE and INNER
are nested programs, and NEXT is a concatenated program. OUTER directly
contains MIDDLE, which directly contains INNER. OUTER indirectly contains
INNER. NEXT, the concatenated program, is not contained in any other
program, and is considered to be a separately compiled program (although
it is in the same source file as OUTER).
Call Rules.
The call rules that apply to subprograms bound at compile time are the
following:
* Any program can call a concatenated program (except the program
itself).
* Normally, a program can only call a nested program if it directly
contains the nested program. However, if the nested program is
COMMON, descendants of the program that contains the COMMON
program can call it also. Only recursion is prohibited; that is,
neither the COMMON program itself nor its descendants can call it.
* COMMON is valid only for nested programs.
* COMMON programs have access to all GLOBAL data that is valid at
their nesting level (this applies to non-COMMON nested programs
too).
Example.
The following example illustrates the call rules.
IDENTIFICATION DIVISION.
PROGRAM-ID. A.
PROCEDURE DIVISION.
BEGIN-A.
*Program A can call any program it directly contains: programs B and D.
*Program A cannot call any program it indirectly contains: program C.
CALL "B".
CALL "D".
IDENTIFICATION DIVISION.
PROGRAM-ID. B.
PROCEDURE DIVISION.
BEGIN-B.
*Program B can call any program it directly contains: program C.
*Program B can call any COMMON program directly contained by
*program A: program D.
CALL "C".
CALL "D".
IDENTIFICATION DIVISION.
PROGRAM-ID. C.
PROCEDURE DIVISION.
BEGIN-C.
*Program C can call any COMMON program directly contained
*by program A: program D.
CALL "D".
END PROGRAM C.
END PROGRAM B.
*Program D IS COMMON and is nested within program A.
IDENTIFICATION DIVISION.
PROGRAM-ID. D IS COMMON.
PROCEDURE DIVISION.
BEGIN-D.
DISPLAY "SUCCESSFUL CALL TO COMMON PROGRAM".
END PROGRAM D.
END PROGRAM A.
Make a program COMMON when programs at various nesting levels need the
function that it performs. For example:
* An application has a single program that reads and examines user
data entered on-line. Many other routines call this program to
read the next user input. Make the reading-and-examining program
COMMON.
* A program handles a variety of error conditions that could happen
anywhere in the execution flow. Make the error-handling program
COMMON.
Link-Time Binding
Link-time binding is performed by the link editor. Subprogram code
becomes part of the program file.
The advantages of link-time binding are:
* Calls to subprograms bound at link time are faster than calls to
subprograms bound at load time or execution time.
* The program file is portable. The program file contains all the
information that it needs to resolve calls to the subprogram.
Other programmers can use your program without additional
executable libraries.
The disadvantages of link-time binding are:
* The program file is larger.
* If you change the subprogram, you must relink all the programs
that call it.
A subprogram can be input to the linker in either a relocatable object
file or a relocatable library. The default is a relocatable object file,
but the compiler can create a file of either type (see Chapter 6 for
details on the RLFILE and RLINIT control options, which create
relocatable libraries).
If only one program calls the subprogram, leave it in this relocatable
object file. If more than one program calls the subprogram, or if the
program that calls it also calls other subprograms, put it in a
relocatable library.
Examples.
This example uses a relocatable object file, SUBP, to hold the subprogram
until it is linked with the main program. UPDPGM contains both the main
program and the subprogram.
:COB85XL SUBPROG,SUBP;INFO="$CONTROL DYNAMIC"
:COB85XL MAINPROG,MAINP
:LINK FROM=MAINP,SUBP; TO=UPDPGM
The subprogram's relocatable object file can also be added to a specified
relocatable library. The following adds a subprogram to the RL file
named RLFILE:
:COB85XL SUBPROG,SUBP;INFO="$CONTROL SUBPROGRAM"
:LINKEDIT
BUILDRL RLFILE;LIMIT=10
ADDRL FROM=SUBP
EXIT
If you run this example, use the BUILDRL command only if an RL file does
not already exist.
If a subprogram resides in a relocatable library, the subprogram can be
linked with many different main programs. The subprograms are linked to
the main program if it references the library (it need not specify the
names of individual subprograms in the library). For more information on
linking, see Chapter 6 .
:LINK FROM=MAINP; TO=UPDPGM;RL=RLFILE
Load-Time Binding
Load-time binding is performed by the loader, which is invoked by the RUN
command immediately before it executes the program. The subprogram must
reside in an executable library (not in a relocatable object file or
relocatable library). Subprogram code does not become part of the
program file. Intrinsics are bound at load time.
The advantages of load-time binding are:
* Calls to subprograms bound at load time are thousands of times
faster than calls to subprograms bound at execution time.
* You can update a subprogram in an executable library without
having to relink the programs that call it. The more programs
that call the subprogram, the more time saved.
The disadvantages of load-time binding are:
* Calls to subprograms bound at load time are slightly slower than
calls to subprograms bound at link time (this only slows program
execution significantly if the program calls the subprogram many
times)
* To run your program, you (or another user) must have both the
program file and the executable library.
Examples.
The following commands create an executable library:
:LINKEDIT
BUILDXL XLFILE;LIMIT=10
EXIT
The following commands compile a subprogram and add the relocatable file
to the executable library:
:COB85XL SUBPGM,SUBP;INFO="$CONTROL ANSISUB"
:LINKEDIT
ADDXL FROM=SUBP; TO=XLFILE; SHOW; MERGE
EXIT
Any main program calling this subprogram is compiled and linked
separately. At execution time the executable library is searched, the
externals are resolved, and the main program and subprogram are loaded
for execution. The following commands accomplish these events:
:COB85XL MAINPGM,MAINP
:LINK FROM=MAINP; TO=UPDPGM
:RUN UPDPGM;XL="XLFILE"
Execution-Time Binding
Execution-time binding is performed by a calling program that contains a
CALL identifier statement or an ON EXCEPTION[REV BEG] or ON OVERFLOW
phrase.[REV END] The value of identifier, a subprogram name, is not
available until execution time. At that time, the program calls a
special routine that checks to see if the called program is contained in
the calling program. If so, the subprogram is nested, and the special
routine binds it to the calling program that contains it. If not, the
subprogram is separately compiled, and the program calls HPGETPROCPLABEL,
which binds the separately compiled subprogram. The subprogram must
reside in an executable library[REV BEG] specified by the XL=parameter of
the link or run command,[REV END] or in the program file.
The advantage of execution-time binding is:
* You specify the value of identifier and you can assign different
subprogram names to identifier under different conditions.
The disadvantages of execution-time binding are:
* Calls to subprograms bound at execution time are thousands of
times slower than calls to subprograms bound at compile time, link
time, or load time.
[REV BEG]
* To run the program, you must have access to both the program[REV
END] file and the executable library that contains the subprogram.
The compiling and linking for the main program and subprogram is the same
for load-time execution.
Examples.
When coding the CALL statement in the main program, the identifier
contains the subprogram name:
01 SUBP PIC X (8).
:
CALL SUBP USING VAR-A.
This allows the entry point to remain unresolved until execution time.
During execution, the value of the field SUBP can be modified by the
program based on input. When the CALL statement is executed, it issues a
call for the value of SUBP. The following CALL statement calls the
subprogram DATESUB1:
MOVE "DATESUB1" TO SUBP.
CALL SUBP USING VAR-A.
The subprograms must reside in the executable library specified by the
XL=parameter of the link or run command, or in the program file.
NOTE Using the ON EXCEPTION or ON OVERFLOW phrase with the CALL literal
statement slows the CALL statement by approximately .01 seconds and
prevents the loader from catching missing subprograms.[REV BEG] The
ON EXCEPTION or ON OVERFLOW[REV END] phrase defers checking for
missing subprograms until execution time.
MPE/iX 5.0 Documentation