ILE COBOL – Procedures
CALL Statements
In ILE COBOL, the CALL statement transfers control to another program or procedure, which is defined in the ‘PROCEDURE DIVISION USING’ phrase of the called program to receive parameters. The called program returns control to the calling program using an EXIT PROGRAM or GOBACK statement.
Syntax
There are mainly two syntax formats of CALL statement categorized via linkage type.
FORMAT1
FORMAT 2
Explanation of terms used in CALL statements:
There are multiple terms used in both formats that are inseparable part of the CALL statements.
-
Literal-1 (CALL Literal-1).
e.g. CALL ‘PGM01’
Here, `Literal-1` specifies the name of the target OPM or ILE COBOL subprogram. With the *PGM object type, it is mandatory that this object exists within the current library list. If a program object named ‘PGM01’ (with the *PGM object type) is not found in the library list, the program will abort. It will end with the error MCH3401 – Cannot resolve to object PGM01.
Example:
PROCESS APOST. IDENTIFICATION DIVISION. *-----------------------* PROGRAM-ID. ERRHNDL31A. AUTHOR. PROGRAMMER. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. CALL 'PGM01' STOP RUN.Error:
Cannot resolve to object PGM01. Type and Subtype X'0201' Authority X'0000'. Function check. MCH3401 unmonitored by ERRHNDL31A at statement 0000000005, instruction X'0000'.
-
Identifier (CALL Identifier).
e.g.MOVE ‘PGM02’ TO WS-PGM-NAME
CALL WS-PGM-NAME
Here, ‘Identifier’ holds the name of the target OPM or ILE COBOL subprogram. With the *PGM object type, it is mandatory that this object exists within the current library list. If a program object named ‘PGM02’ (with the *PGM object type) is not found in the library list, the program will abort. It will end with the error MCH3401 – Cannot resolve to object PGM02.
Example:
PROCESS APOST. IDENTIFICATION DIVISION. *-----------------------* PROGRAM-ID. ERRHNDL31B. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* WORKING-STORAGE SECTION. 01 WS-PGM-NAME PIC X(10) VALUE 'PGM02'. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. CALL WS-PGM-NAME. STOP RUN.Error:
Cannot resolve to object PGM02. Type and Subtype X'0201' Authority X'0000'. Function check. MCH3401 unmonitored by ERRHNDL31B at statement 0000000007, instruction X'0000'.
-
EXCEPTION or OVERFLOW Phrase.
e.g. CALL ‘PGM01’
ON EXCEPTION DISPLAY ‘CANNOT RESOLVE TO OBJECT PGM01’.
e.g. CALL ‘PGM02’
ON OVERFLOW DISPLAY ‘CANNOT RESOLVE TO OBJECT PGM02’.
EXCEPTION or OVERFLOW phrase is used to trap & handle the error – specifically MCH3401 (Cannot resolve to object).
Example:
PROCESS APOST. IDENTIFICATION DIVISION. *-----------------------* PROGRAM-ID. ERRHNDL31B. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* WORKING-STORAGE SECTION. 01 WS-PGM-NAME PIC X(10) VALUE 'PGM02'. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. CALL 'PGM01' ON OVERFLOW DISPLAY 'CANNOT RESOLVE TO OBJECT PGM01'. CALL WS-PGM-NAME ON EXCEPTION DISPLAY 'CANNOT RESOLVE TO OBJECT PGM02'. STOP RUN.Output:
CANNOT RESOLVE TO OBJECT PGM01 CANNOT RESOLVE TO OBJECT PGM02
-
LINKAGE TYPE Phrase.
In ILE COBOL, there are two primary linkage types when using the CALL literal statement to call an external program, internal procedure or external procedure:
- PROGRAM (*PGM) (dynamic program calls)
- PROCEDURE (*MODULE). (statis procedure calls)
Examples: For dynamic program calls
CALL ‘PROG01’.
CALL PROGRAM ‘PROG01’.
CALL LINKAGE PROGRAM ‘PROG01’.
CALL LINKAGE TYPE IS PROGRAM ‘PROG01’.PROG01(*PGM):
IDENTIFICATION DIVISION. *-----------------------* PROGRAM-ID. PROG01. AUTHOR. PROGRAMMER. DATA DIVISION. *---------------------* WORKING-STORAGE SECTION. 01 WS-DATE PIC 9(08). PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. ACCEPT WS-DATE FROM DATE YYYYMMDD. DISPLAY 'WS-DATE:' WS-DATE. STOP RUN.CALL02(*PGM):
PROCESS APOST. IDENTIFICATION DIVISION. *-----------------------* PROGRAM-ID. CALL02. AUTHOR. PROGRAMMER. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. CALL PROGRAM 'PROG01' ON EXCEPTION DISPLAY 'ERROR IN CALL - PROG01'. STOP RUN.Examples: For status procedure calls.
CALL ‘MODULE01’.
CALL PROCEDURE ‘MODULE01’.
CALL LINKAGE PROCEDURE ‘MODULE01’.
CALL LINKAGE TYPE IS PROCEDURE ‘MODULE01’.
(This part is explained in static procedure call section). -
‘IN LIBRARY’ Phrase.
‘IN LIBRARY’ Phrase is used within a CALL statement to perform a dynamic program call to a specific library on the IBM i system. This phrase does not work with static procedure call.
e.g.
CALL ‘PROG01’ IN LIBRARY ‘TESTLAB’.
e.g.
01 PGM-NAME PIC X(10) VALUE ‘PROG1’.
01 LIB-NAME PIC X(10) VALUE ‘TESTLAB’
CALL PGM-NAME IN LIBRARY LIB-NAM.
-
‘END-CALL’ Phrase
The END-CALL phrase in ILE COBOL is a scope terminator used to explicitly end a CALL statement.
e.g.
CALL ‘PROG01’ IN LIBRARY ‘TESTLAB’
END-CALL.
-
‘USING’ Phrase
In ILE COBOL, the USING phrase is used in the CALL statement of the calling program and the PROCEDURE DIVISION header of the called program. The data items are matched by their position in the list, data type and data length, not by their names. USING Phrase is typically for passing multiple parameters, data items or data structures.
Example:
PROCESS APOST. IDENTIFICATION DIVISION. *------------------------* PROGRAM-ID. MAINPGM. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* WORKING-STORAGE SECTION. 01 WS-LAST-CARD-NBR PIC 9(10) VALUE 4000600001. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. *> Calling the subprogram using the USING phrase CALL ‘SUBPGM’ USING WS-LAST-CARD-NBR END-CALL. STOP RUN.PROCESS APOST. IDENTIFICATION DIVISION. *------------------------* PROGRAM-ID. SUBPGM. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* LINKAGE SECTION. 01 LK-CARD-NBR PIC 9(10). *> The USING phrase to match the order in the CALL statement PROCEDURE DIVISION USING LK-CARD-NBR. *------------------* MAIN-LOGIC. ADD 1 TO LK-CARD-NBR. EXIT PROGRAM. -
‘GIVING’ or ‘RETURNING’ Phrase
In ILE COBOL, the GIVING and RETURNING phrases are used interchangeably to return a single value from a called program back to the caller.
Example:
PROCESS APOST. IDENTIFICATION DIVISION. *------------------------* PROGRAM-ID. MAINPGM1. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* WORKING-STORAGE SECTION. 01 WS-LAST-CARD-NBR PIC 9(10) VALUE 4000600001. 01 WS-NEXT-CARD-NBR LIKE WS-LAST-CARD-NBR. PROCEDURE DIVISION. *-------------------* MAIN-LOGIC. *> Calling the subprogram using the USING phrase CALL ‘SUBPGM1’ USING WS-LAST-CARD-NBR RETURNING WS-NEXT-CARD-NBR END-CALL. STOP RUN.PROCESS APOST. IDENTIFICATION DIVISION. *------------------------* PROGRAM-ID. SUBPGM1. AUTHOR. PROGRAMMER. DATA DIVISION. *--------------* LINKAGE SECTION. 01 LK-LAST-CARD-NBR PIC 9(10). 01 LK-NEXT-CARD-NBR LIKE LK-LAST-CARD-NBR. *> The USING phrase to match the order in the CALL statement PROCEDURE DIVISION USING LK-LAST-CARD-NBR RETURNING LK-NEXT-CARD-NBR. *------------------* MAIN-LOGIC. COMPUTE LK-NEXT-CARD-NBR = LK-LAST-CARD-NBR + 1. EXIT PROGRAM.
Parameter Passing
In ILE COBOL, parameter passing is governed by how memory is shared between a calling program and a called subprogram or an internal sub procedure or external sub procedure (modules and service programs).
The Call statement of the calling program or procedure and procedure division of called programs or procedures are almost parallel.
Syntax of CALL for Calling programs or procedures
CALL "program-name"/"internal sub procedure"/"external sub procedure"
[USING {BY REFERENCE} (identifier-1 | literal-1) ...
{BY CONTENT} (identifier-2 | literal-2) ...
{BY VALUE} (identifier-3 | literal-3) ...
[RETURNING] (identifier-4|literal-4)
[ON OVERFLOW/EXCEPTION] {statement…}
[NOT ON OVERFLOW/EXCEPTION] {statement…}
[END-CALL].
Syntax of PROCEDURE DIVISION statement for Called programs or procedures
PROCEDURE DIVISION
[USING] {BY REFERENCE} (identifier-1|literal-1) ...
{BY VALUE} (identifier-3|literal-3) ...
[RETURNING] (identifier-4|literal-4)).
In ILE COBOL, data can be passed between programs or procedures using three primary methods with the CALL statement: BY REFERENCE, BY CONTENT, and BY VALUE.
| Methods | Description | Called Program’s Ability to Change Original Data |
|---|---|---|
| BY REFERENCE (Default in RPGLE Programming) | BY REFERENCE (Default in RPGLE Programming) The address of the original data item in the calling program’s memory is passed. This is also the default mechanism if nothing is specified. Called program can modify the data value. And original data item is affected in the calling program. | BY REFERENCE (Default in RPGLE Programming) The address of the original data item in the calling program’s memory is passed. This is also the default mechanism if nothing is specified. Called program can modify the data value. And original data item is affected in the calling program. |
| BY CONTENT (CONST in RPGLE Programming) | Passes an address but prevents the called program from changing the value. | Called program cannot change the data value. The original data item in the calling program remains unchanged. |
| BY VALUE (VALUE in RPGLE Programming) | The value of the data item is placed directly into the parameter list. | BY VALUE (VALUE in RPGLE Programming) The value of the data item is placed directly into the parameter list. Called program can modify the data value. But the original data item is not affected. |
BY REFERENCE Phrase
When an ILE COBOL program or procedure passes a parameter BY REFERENCE, the address of the parameter’s memory location is passed to the called program or procedure. The called program or procedure receives the pointer to the parameter’s memory location when the programmer passes the parameters using BY REFERENCE. If the called program or procedure modifies the value of the parameter, the new value will be reflected in the calling program or procedure.
Example: BY REFERENCE
PROCESS APOST, FLAG(29), LINKPRC, NOMONOPRC.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. CALLPARM1.
AUTHOR. PROGRAMMER.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 WS-NUM PIC 9(9)V9(2) VALUE 10.
PROCEDURE DIVISION.
*-------------------*
000-MAINLINE-PARA.
DISPLAY 'BEFORE PROGRAM:' WS-NUM.
CALL 'SUBPROG1' USING BY REFERENCE WS-NUM.
DISPLAY 'AFTER PROGRAM:' WS-NUM.
STOP RUN.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. SUBPROG1.
DATA DIVISION.
*--------------*
LINKAGE SECTION.
01 LS-NUM PIC 9(9)V9(2).
PROCEDURE DIVISION USING BY REFERENCE LS-NUM.
*---------------------------------------------*
000-SP-PARA.
COMPUTE LS-NUM = LS-NUM + 2 * 10.
EXIT PROGRAM.
END PROGRAM 'SUBPROG1'.
END PROGRAM ‘CALLPARM1’.
Output:
BEFORE PROGRAM:00000001000 AFTER PROGRAM:00000003000
BY CONTENT Phrase
When an ILE COBOL program or procedure passes a parameter BY CONTENT, the copy of the data is passed to the called program or procedure. The called program or procedure receives a copy of the variable’s data at the time of execution when the programmer passes the parameters using BY CONTENT. If the called program or procedure modifies the value of the parameter, the new value will be reflected in the calling program or procedure.
Example: BY CONTENT
PROCESS APOST, FLAG(29), LINKPRC, NOMONOPRC.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. CALLPARM2.
AUTHOR. PROGRAMMER.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 WS-NUM PIC 9(02) VALUE 20.
PROCEDURE DIVISION.
*-------------------*
000-MAINLINE-PARA.
DISPLAY 'BEFORE PROGRAM:' WS-NUM.
CALL 'SUBPROG2' USING BY CONTENT WS-NUM.
DISPLAY 'AFTER PROGRAM:' WS-NUM.
STOP RUN.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. SUBPROG2.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 LS-NUM1 PIC 9(02) VALUE 50.
LINKAGE SECTION.
01 LS-NUM PIC 9(02).
PROCEDURE DIVISION USING LS-NUM.
*---------------------------------*
000-SP-PARA.
ADD LS-NUM1 TO LS-NUM.
DISPLAY 'IN PROCEDURE :' LS-NUM.
EXIT PROGRAM.
END PROGRAM 'SUBPROG2'.
END PROGRAM 'CALLPARM2'.
Output:
BEFORE PROGRAM:20 IN PROCEDURE :70 AFTER PROGRAM:20
Important:
- In PROCEDURE DIVISION, BY CONTENT does not work, it gives compilation error.
- It does not pass CONSTANT variables. In RPGLE CONST can be passed.
BY VALUE Phrase
When an ILE COBOL program or procedure passes a parameter BY VALUE, the copy of the data is passed to the called program or procedure. The called program or procedure receives a copy of the variable’s data at the time of execution when the programmer passes the parameters using BY CONTENT. If the called program or procedure modifies the value of the parameter, the new value will be reflected in the calling program or procedure. This almost similar to BY CONTENT phrase.
Example: BY VALUE
PROCESS APOST, FLAG(29), LINKPRC, NOMONOPRC.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. CALLPARM3.
AUTHOR. PROGRAMMER.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 WS-NUM PIC 9(02) VALUE 20.
PROCEDURE DIVISION.
*-------------------*
000-MAINLINE-PARA.
DISPLAY 'BEFORE PROGRAM:' WS-NUM.
CALL 'SUBPROG3' USING BY VALUE WS-NUM.
DISPLAY 'AFTER PROGRAM:' WS-NUM.
STOP RUN.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. SUBPROG3.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 LS-NUM1 PIC 9(02) VALUE 12.
LINKAGE SECTION.
01 LS-NUM PIC 9(02).
PROCEDURE DIVISION USING LS-NUM.
*---------------------------------*
000-SP-PARA.
ADD LS-NUM1 TO LS-NUM.
DISPLAY 'IN PROCEDURE :' LS-NUM.
EXIT PROGRAM.
END PROGRAM 'SUBPROG3'.
END PROGRAM 'CALLPARM3'.
Output:
BEFORE PROGRAM:20 IN PROCEDURE :32 AFTER PROGRAM:20
Type of Call Statements
In ILE COBOL, the primary difference between dynamic and static calls is when the connection between the calling program and the called subprogram is resolved. These calls are specifically referred to as dynamic program calls and static procedure calls. A dynamic program call transfers control to a separate program object (a *PGM). A static procedure call transfers control to a procedure bound into the same program object, or a module(*MODULE) or potentially from a service program (*SRVPGM).
Key Differences
| Feature | Dynamic Program Call (*PGM) | Static Procedure Call (*SRVPGM / *MODULE) |
|---|---|---|
| Binding Time | Run time: Resolved by searching the library list (*LIBL) when the call is made. | Link-edit time: Resolved when the program is created; the code is “bound” together. |
| Load Module | Separate objects: The caller and the called are two different objects on the system. | Single object: The called code is physically part of the caller’s program or service program object. |
| Performance | Slower: Initial call has overhead for object searching, security checks, and activation. | Faster: Minimal overhead; it is essentially a “jump” to a memory address already in the program. |
| Maintenance | Easy: We can replace the called *PGM without re-creating the caller. | Complex: Changes to the subprogram often require a rebind (though Service Programs help mitigate this). |
| Memory | On-demand: Loaded only when called; can be removed from memory via CANCEL. | All-at-once: Everything is loaded into the Activation Group when the program starts. |
Dynamic Calls
In ILE COBOL, a dynamic program call transfers control to a separate program object (*PGM) at runtime, rather than a procedure bound into the same executable. This allows you to update the called program without recompiling or rebinding the calling program.
1. Calling Program (MAINPGM)
This program uses a variable to store the name of the program it needs to call dynamically.
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. MAINPGM.
AUTHOR. PROGRAMMERS.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 WS-PROGRAM-NAME PIC X(10) VALUE "SUBPGM".
01 WS-DATA-AREA.
05 WS-INPUT-1 PIC 9(03) VALUE 100.
05 WS-INPUT-2 PIC 9(03) VALUE 200.
05 WS-RESULT PIC 9(04).
PROCEDURE DIVISION.
*-------------------*
MAIN-LOGIC.
*> The CALL identifier is always a dynamic call in ILE COBOL
CALL WS-PROGRAM-NAME USING WS-DATA-AREA.
DISPLAY "MAINPGM: Result from subprogram: " WS-RESULT.
STOP RUN.
2. Called Subprogram (SUBPGM)
The subprogram must be compiled into a separate program object (*PGM). It receives data via the LINKAGE SECTION.
POST APOST, FLAG(29).
IDENTIFICATION DIVISION.
*------------------------*
PROGRAM-ID. SUBPGM.
AUTHOR. PROGRAMMERS.
DATA DIVISION.
*--------------*
LINKAGE SECTION.
01 LS-DATA-AREA.
05 LS-INPUT-1 PIC 9(03).
05 LS-INPUT-2 PIC 9(03).
05 LS-RESULT PIC 9(04).
PROCEDURE DIVISION USING LS-DATA-AREA.
*----------------------------------------*
SUB-LOGIC.
ADD LS-INPUT-1 TO LS-INPUT-2 GIVING LS-RESULT.
GOBACK.
Output:
MAINPGM: Result from subprogram: 300
Static Calls
In ILE COBOL, “bind by copy” and “bind by reference” are methods for creating program objects from modules, determining how the code for sub-procedures is included and accessed. These methods are called as:
- Bind by Copy
- Bind by Reference
Bound by Copy
Mechanism: The object code of the called sub procedures is physically copied into the calling program object (*PGM) at creation time.
Object Type: Used when binding *MODULE objects into a *PGM object.
Execution: The called code is an integral part of the program, making calls as fast as a traditional EXSR (internal subroutine call).
Maintenance: If the source code of the called module is revised and the module recompiled, the *PGM object that uses it is not automatically updated and must be re-created to incorporate the changes. Best Use Case: Ideal for modules used by only one program, where performance is critical and maintenance of multiple programs is not an issue.
Bound by Reference
Mechanism: The program object (*PGM) does not contain the actual code for the sub-procedures. Instead, it stores a reference to a *Service Program (*SRVPGM) object, which contains the code. The service program is then loaded and shared at runtime when the program is activated.
Object Type: Used when binding *SRVPGM objects into a *PGM object.
Execution: The initial activation of the service program has a slight overhead, but subsequent calls to its procedures are efficient.
Maintenance: Changes to the service program require only updating the *SRVPGM object; the *PGM objects that use it do not need to be re-created, as they dynamically link to the latest version at runtime.
Best Use Case: Essential when a set of sub-procedures is shared by many programs, simplifying maintenance and reducing the number of code copies across the system.
Summary of Differences
| Aspect | Bind by Copy | Bind by Reference |
|---|---|---|
| Object Type | *MODULEs bound into a *PGM | *SRVPGMs linked to a *PGM |
| Code Location | Code is copied into the calling *PGM | Code resides in a shared *SRVPGM |
| Runtime Behaviour | Faster calls, but larger program size | Slightly more initial overhead, shared memory access |
| Maintenance | Requires recompiling/re-creating all calling programs when the module changes | Only the *SRVPGM needs updating; calling programs use the new version automatically |
Example – Bound by Copy – Internal sub procedure
PROCESS APOST, FLAG(29), NOMONOPRC.
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEMAINPGM.
AUTHOR. PROGRAMMER.
DATA DIVISION.
WORKING-STORAGE SECTION.
01 WS-IN-NUM1 PIC S9(9)V99 VALUE 250.
01 WS-IN-NUM2 PIC S9(9)V99 VALUE 25.
01 WS-OP-RES PIC S9(9)V99 VALUE 0.
PROCEDURE DIVISION.
MAINLINE.
CALL 'PROCADD' USING WS-IN-NUM1, WS-IN-NUM2,
WS-OP-RES.
CANCEL 'PROCADD'.
DISPLAY 'RESULT:' WS-OP-RES.
CALL 'PROCSUB' USING WS-IN-NUM1, WS-IN-NUM2,
WS-OP-RES.
CANCEL 'PROCSUB'.
DISPLAY 'RESULT:' WS-OP-RES.
CALL 'PROCMUL' USING WS-IN-NUM1, WS-IN-NUM2,
WS-OP-RES.
CANCEL 'PROCMUL'.
DISPLAY 'RESULT:' WS-OP-RES.
CALL 'PROCDIV' USING WS-IN-NUM1, WS-IN-NUM2,
WS-OP-RES.
CANCEL 'PROCDIV'.
DISPLAY 'RESULT:' WS-OP-RES.
STOP RUN.
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. PROCADD.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 + P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM PROCADD.
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. PROCSUB.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 - P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM PROCSUB.
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. PROCMUL.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 * P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM PROCMUL.
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. PROCDIV.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 / P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM PROCDIV.
*----------------------------------------------------------------*
- ‘ILEMAINPGM’ is a single COBOL source that consists of 5 ‘ID DIVISION’. The ‘ILEMAINPGM’ is main program and others (PROCADD, PROCSUB, PROCMUL, PROCDIV) internal sub procedures.
- In this source writing ‘LINKAGE TYPE’ clause of ‘SPECIAL-NAMES’ is not important as these procedures are internal to the program.
- ‘ILEMAINPGM’ is ended with ‘STOP RUN’ but other procedures have been ended with a ‘EXIT PROGRAM’ which acts as ending procedures.
- In ILE COBOL, there are two distinct ways to handle program termination: using the END PROGRAM header to define source boundaries and using execution statements to return control or end the run unit (GOBACK, EXIT PROGRAM).
- WS-* variables are global variables and P-* variable are local variables (parameters).
- This program has been directly compiled by CRTBNDCBL program, it generates a single *PGM (ILEMAINPGM) object.
CRTBNDCBL PGM(PIOLIB/ILEMAINPGM)
SRCFILE(PIOLIB/QCBLLESRC)
SRCMBR(ILEMAINPGM)
DBGVIEW(*SOURCE)
FLAG(29)
Output
RESULT:00000027500 RESULT:00000022500 RESULT:00000625000 RESULT:00000001000
Modules
ILE (Integrated Language Environment) Modules in COBOL/400 (IBM i) are non-runnable, compiled objects (*MODULE) created using the CRTCBLMOD command. They represent the fundamental building block for modular programming, allowing COBOL code to be bound together into runnable program objects (*PGM) or service programs (*SRVPGM), enabling reusability and language interoperability.
Example – Bound by Copy
External sub procedures (*MODULE) (Multiple source)
PROCESS APOST, FLAG(29), LINKPRC,
NOPRTCORR, NOMONOPRC.
IDENTIFICATION DIVISION.
*-----------------------*
PROGRAM-ID. MTHPGM01.
AUTHOR. PROGRAMMERS.
ENVIRONMENT DIVISION.
*-----------------------*
CONFIGURATION SECTION.
SOURCE-COMPUTER. IBMi-Series.
OBJECT-COMPUTER. IBMi-Series.
SPECIAL-NAMES.
LINKAGE TYPE IS PROCEDURE FOR 'ILEADD'.
LINKAGE TYPE IS PROCEDURE FOR 'ILESUB'.
LINKAGE TYPE IS PROCEDURE FOR 'ILEMUL'.
LINKAGE TYPE IS PROCEDURE FOR 'ILEDIV'.
DATA DIVISION.
WORKING-STORAGE SECTION.
01 NUM1 PIC S9(9)V99 VALUE 250.
01 NUM2 PIC S9(9)V99 VALUE 25.
01 RES PIC S9(9)V99 VALUE 0.
PROCEDURE DIVISION.
000-MAIN.
CALL PROCEDURE 'ILEADD' USING NUM1, NUM2, RES.
CANCEL 'ILEADD'.
DISPLAY ‘ILEADD:’ RES.
CALL PROCEDURE 'ILESUB' USING NUM1, NUM2, RES.
CANCEL 'ILESUB'.
DISPLAY ‘ILESUB:’ RES.
CALL PROCEDURE 'ILEMUL' USING NUM1, NUM2, RES.
CANCEL 'ILEMUL'.
DISPLAY ‘ILEMUL:’ RES.
CALL PROCEDURE 'ILEDIV' USING NUM1, NUM2, RES.
CANCEL 'ILEDIV'.
DISPLAY ‘ILEDIV:’ RES.
STOP RUN.
PROCESS APOST.
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEADD.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 + P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEADD.
PROCESS APOST.
IDENTIFICATION DIVISION.
PROGRAM-ID. ILESUB.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 - P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILESUB.
PROCESS APOST.
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEMUL.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 * P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEMUL.
PROCESS APOST.
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEDIV.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
COMPUTE P-OP-RES = P-IN-NUM1 / P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEDIV.
- ‘MTHPGM01’ is main COBOL source. ‘ILEADD’, ‘ILESUB’, ‘ILEMUL’ and ‘ILEDIV’ are 4 other COBOL sources.
- In the ‘PROCESS’ statement ‘LINKPRC’ is used to specify compiler that program will force all external CALL literal statements to use static procedure calls (*PRC) instead of dynamic program calls (*PGM). This allows for direct binding to sub procedures in other modules or service programs within the same activation group, improving call performance.
- In this source writing ‘LINKAGE TYPE’ clause of ‘SPECIAL-NAMES’ is very important as it describes that these
- In CALL statement PROCEDURE is to specify that ILEADD etc are either module, or a procedure of service program.
-
Steps to compile to generate all modules (*MODULE) objects.
CRTCBLMOD MODULE(PIOLIB/ILEADD) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEADD) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILESUB) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILESUB) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEMUL) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEMUL) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEDIV) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEDIV) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/MTHPGM01) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHPGM01) REPLACE(*YES)After compilation, ILEADD, ILESUB, ILEMUL, ILEDIV and MTHPGM01 *MODULE objects are generated. These modules cannot be called using CALL CL command in command line.
-
Steps to bind the modules to generate single program. (*** BIND BY COPY ***)
CRTPGM PGM(PIOLIB/MATHPGM01) MODULE(PIOLIB/MATHPGM01 PIOLIB/ILEADD PIOLIB/ILESUB PIOLIB/ILEMUL PIOLIB/ILEDIV)After binding, MTHPGM01 *PGM object is generated. This program can be called using CALL CL command in command line.
Output (CALL PIOLIB/MTHPGM01)
ILEADD:00000027500 ILESUB:00000022500 ILEMUL:00000625000 ILEDIV:00000001000
Important:
- In CRTPGM CL command, up to 300 module names can be specified.
- If duplicate module and library specifications are found, only the first instance of the duplicate, module and library is used.
- Once the program object is created, all modules are copied into the program object. And it does not check modules are present in specific library or not.
- If there is need to change module, then compile changed module and then re-create program object using CRTPGM program step.
- If there is need to add a new module or remove an existing module, then re-create program object using CRTPGM program step.
- Maintenance becomes very complex when number of modules increases for a single program.
- It also requires multiple COBOL source.
Example – Bound by Reference
Adding modules to a Service Program
- Similar effect can be found if all modules are added into a service program.
-
Steps to compile to generate all modules (*MODULE) objects.
CRTCBLMOD MODULE(PIOLIB/ILEADD) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEADD) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILESUB) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILESUB) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEMUL) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEMUL) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEDIV) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEDIV) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/MTHPGM01) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHPGM01) REPLACE(*YES) -
Steps to create a service program.
CRTSRVPGM SRVPGM(PIOLIB/MTHSRV01) MODULE(PIOLIB/ILEADD PIOLIB/ILESUB PIOLIB/ILEMUL PIOLIB/ILEDIV) EXPORT(*ALL)
-
DSPSRVPGM
Display Service Program Information Display 3 of 10 Service program . . . . . . . . . . . . : MTHSRV01 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *MODULE Type options, press Enter. 5=Display description 6=Print description Creation Optimization Debug Opt Module Library Attribute Date Level Data ILEADD PIOLIB CBLLE 04/24/26 *NONE *YES ILESUB PIOLIB CBLLE 04/24/26 *NONE *YES ILEMUL PIOLIB CBLLE 04/24/26 *NONE *YES ILEDIV PIOLIB CBLLE 04/24/26 *NONE *YESSteps to bind the modules to generate single program. (*** BIND BY REFERENCE ***)
CRTPGM PGM(PIOLIB/MTHPGM01) MODULE(PIOLIB/MTHPGM01) ENTMOD(*FIRST) BNDSRVPGM((PIOLIB/MTHSRV01)) ACTGRP(*CALLER)
Output (CALL PIOLIB/MTHPGM01)
ILEADD:00000027500 ILESUB:00000022500 ILEMUL:00000625000 ILEDIV:00000001000
Important:
- In CRTPGM CL command, up to 300 service program names can be specified.
- If duplicate service program and library specifications are found, only the first instance of the duplicate, service program and library is used.
- Once the program object is created, all service program can be accessed from the program object.
- If there is need to change module, then compile changed module and then re-create service program object using CRTSRVPGM step. Re-create program object using CRTPGM program step.
Example – Bound by Reference
Adding modules to a Binding Directory
-
Similar effect can be found if all modules are added into a binding directory.
-
Steps to compile to generate all modules (*MODULE) objects.
CRTCBLMOD MODULE(PIOLIB/ILEADD) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEADD) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILESUB) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILESUB) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEMUL) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEMUL) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/ILEDIV) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(ILEDIV) REPLACE(*YES) CRTCBLMOD MODULE(PIOLIB/MTHPGM01) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHPGM01) REPLACE(*YES) -
Steps to create binding directory.
CRTBNDDIR BNDDIR(PIOLIB/MATH01) ADDBNDDIRE BNDDIR(PIOLIB/MATH01) OBJ((PIOLIB/ILEADD *MODULE) (PIOLIB/ILESUB *MODULE) (PIOLIB/ILEMUL *MODULE) (PIOLIB/ILEDIV *MODULE))
-
WRKBNDDIRE BNDDIR(PIOLIB/MATH01)
Work with Binding Directory Entries Binding Directory: MATH01 Library: PIOLIB Type options, press Enter. 1=Add 4=Remove -------Creation-------- Opt Object Type Library Activation Date Time ILEADD *MODULE PIOLIB *IMMED ILESUB *MODULE PIOLIB *IMMED ILEMUL *MODULE PIOLIB *IMMED ILEDIV *MODULE PIOLIB *IMMED -
Steps to bind the modules to generate single program. (*** BIND BY REFERENCE ***)
CRTPGM PGM(PIOLIB/MTHPGM01) MODULE(PIOLIB/MTHPGM01) ENTMOD(*FIRST) BNDDIR(PIOLIB/MATH01) ACTGRP(*CALLER)
Output (CALL PIOLIB/MTHPGM01)
ILEADD:00000027500 ILESUB:00000022500 ILEMUL:00000625000 ILEDIV:00000001000
Binder Language
A Service Program (*SRVPGM) is a group of sub procedures that other programs can use. Programs connect to a service program through something called a signature. When a service program is created using the CRTSRVPGM command, it gets a unique 16 byte or 32 characters hexadecimal signature. This signature depends on how many procedures the service program has, the names of those procedures, and the order in which they are listed. If any of this change, the signature also changes. Users can see the signature via CL Command – DSPSRVPGM command with DETAIL(*SIG- NATURE).
Example: DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02) DETAIL(*SIGNATURE)
Display Service Program Information
Display 1 of 1
Service program . . . . . . . . . . . . : MTHSRV02
Library . . . . . . . . . . . . . . . : PIOLIB
Owner . . . . . . . . . . . . . . . . . : AKUMAR
Service program attribute . . . . . . . : CBLLE
Detail . . . . . . . . . . . . . . . . . : *SIGNATURE
Signatures:
A328CA4F453CA845DD514373686A5859
Signature Violation
One service program can be used by many programs. If a programmer adds a new procedure, removes or comments out an existing one, changes a procedure name, or changes the order of procedures, the signature will change. When this happens, programs that use the service program will no longer match it and may fail with an error like MCH4431 (signature violation).
For this reason, once a service program is in use, programmers should not rename procedures, change their order, or remove procedures. If the signature does change, all programs that use the service program must be recompiled.
Whenever any new requirement comes, new procedures are added at the bottom of the service program source. Due to this, new signature is generated. Hence, we need to recompile all programs using these service programs. It is a complex task.
Binder Language
Binder language is coded in a separate source member from the rest of the service program. This is typically placed in a source file name and source member name that matches the service program’s name. The type of the source is always BND referring binder language source.
STRPGMEXP PGMLVL(*CURRENT)
EXPORT SYMBOL("ILEADD2")
EXPORT SYMBOL("ILESUB2")
EXPORT SYMBOL("ILEMUL2")
EXPORT SYMBOL("ILEDIV2")
ENDPGMEXP
Binder language consists of following commands:
- STRPGMEXP – (Start Program Export) is a command used in IBM i Binder Language to mark the beginning of a list of procedures or data that a service program makes available to other programs.
- PGMLVL(*CURRENT or *PRV)
- *CURRENT: Identifies the newest list of exports. There can only be one “current” block.
- *PRV: Identifies a previous version of the export list. Using this allows older programs to still work without being recompiled, even after you’ve added new features.
- LVLCHK(*YES or *NO)
- LVLCHK(*YES): This is the default. When a program calls the service program, the system compares the signature stored in the program with the one in the service program. If they don’t match, the system issues a signature violation (MCH4437 or CPF4131) and prevents the program from running.
- LVLCHK(*NO): The system ignores signature mismatches. While this avoids immediate errors, it is generally not recommended because it can lead to unpredictable behavior if a program tries to call a procedure that has moved or no longer exists.
- SIGNATURE – For hardcoding signature.
- EXPORT SYMBOL – EXPORT SYMBOL is a command in IBM i Binder Language used to name the specific sub procedures that a service program makes available to other programs.
- ENDPGMEXP – ENDPGMEXP (End Program Export) is the command that marks the end of a specific export block in your binder language.
Compilation of service program with binder language
Steps to create service program using binder language:
-
When COBOL source MTHSRV02 is compiled using below CL command then, it generates following modules:
CRTCBLMOD MODULE(PIOLIB/MTHSRV02) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHSRV02) REPLACE(*YES) -
DSPJOBLOG
Module MTHSRV02 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILESUB2 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILEMUL2 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILEDIV2 created in library PIOLIB on 04/27/26 at 07:49:13. Member MTHSRV02 in file PIOLIB /QCBLLESRC changed with 57 records. AUT parameter ignored. Replaced object MTHSRV02 type *MODULE was moved to QRPLOBJ. Module MTHSRV02 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILESUB2 type *MODULE was moved to QRPLOBJ. Module ILESUB2 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILEMUL2 type *MODULE was moved to QRPLOBJ. Module ILEMUL2 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILEDIV2 type *MODULE was moved to QRPLOBJ. Module ILEDIV2 created in library PIOLIB on 04/27/26 at 07:42:09.
- It creates 4 modules MTHSRV02 (which has reference of ILEADD2), ILESUB2, ILEMUL2, ILEDIV2.
-
When service program MTHSRV02 is created using below CL command then, it generates service program. In CRTSRVPGM CL command, MODULE can hold up to 300 modules names can be specified.
CRTSRVPGM SRVPGM(PIOLIB/MTHSRV02) MODULE(PIOLIB/MTHSRV02 PIOLIB/ILESUB2 PIOLIB/ILEMUL2 PIOLIB/ILEDIV2) EXPORT(*SRCFILE) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHBND02) -
DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02)
Display Service Program Information Display 3 of 10 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *MODULE Type options, press Enter. 5=Display description 6=Print description Creation Optimization Debug Opt Module Library Attribute Date Level Data MTHSRV02 PIOLIB CBLLE 04/28/26 *NONE *YES ILESUB2 PIOLIB CBLLE 04/28/26 *NONE *YES ILEMUL2 PIOLIB CBLLE 04/28/26 *NONE *YES ILEDIV2 PIOLIB CBLLE 04/28/26 *NONE *YES -
Signature – DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02) DETAIL(*SIGNATURE)
Display Service Program Information Display 1 of 1 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *SIGNATURE Signatures: 000000000000000F1D1D540432215859 -
Steps to bind the modules to generate single program.
CRTCBLMOD MODULE(PIOLIB/MTHPGM02) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHPGM02) REPLACE(*YES) CRTPGM PGM(PIOLIB/MTHPGM02) MODULE(PIOLIB/MTHPGM02) ENTMOD(*FIRST) BNDSRVPGM((PIOLIB/MTHSRV02)) ACTGRP(*CALLER)
After binding, MTHPGM02 *PGM object is generated. This program can be called using CALL CL command in command line.
Output (CALL PIOLIB/MTHPGM02)
00000027500 00000022500 00000625000 00000001000
Solution 1- Multiple signatures for adding new procedures.
New requirement – Introduction of new procedure in MTHSRV02 service program – ‘ILEREM2’.
-
Source change code in – PIOLIB/MTHSRV02
*----------------------------------------------------------------* * Procedure: ILEREM2* *----------------------------------------------------------------* IDENTIFICATION DIVISION. PROGRAM-ID. ILEREM2. DATA DIVISION. LINKAGE SECTION. 01 P-IN-NUM1 PIC S9(9)V99. 01 P-IN-NUM2 PIC S9(9)V99. 01 P-OP-RES PIC S9(9)V99. PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES. 000-MAINLINE. COMPUTE P-OP-RES = FUNCTION REM(P-IN-NUM1, P-IN-NUM2). EXIT PROGRAM. END PROGRAM ILEREM2. -
Binder language source change
STRPGMEXP PGMLVL(*CURRENT) EXPORT SYMBOL("ILEADD2") EXPORT SYMBOL("ILESUB2") EXPORT SYMBOL("ILEMUL2") EXPORT SYMBOL("ILEDIV2") EXPORT SYMBOL("ILEREM2") ENDPGMEXP STRPGMEXP PGMLVL(*PRV) EXPORT SYMBOL("ILEADD2") EXPORT SYMBOL("ILESUB2") EXPORT SYMBOL("ILEMUL2") EXPORT SYMBOL("ILEDIV2") ENDPGMEXP -
DSPSRVPGM SRVPGM(PIOLIB /MTHSRV02)
Display Service Program Information Display 3 of 10 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *MODULE Type options, press Enter. 5=Display description 6=Print description Creation Optimization Debug Opt Module Library Attribute Date Level Data MTHSRV02 PIOLIB CBLLE 04/28/26 *NONE *YES ILESUB2 PIOLIB CBLLE 04/28/26 *NONE *YES ILEMUL2 PIOLIB CBLLE 04/28/26 *NONE *YES ILEDIV2 PIOLIB CBLLE 04/28/26 *NONE *YES ILEREM2 PIOLIB CBLLE 04/28/26 *NONE *YES -
Signature – DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02) DETAIL(*SIGNATURE)
Display Service Program Information Display 1 of 1 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *SIGNATURE Signatures: 00000000000000F1D1C71408FBDA5859 000000000000000F1D1D540432215859 - Because number of ‘PGMLVL’ used was two times in the binder language, two signatures were created. New programs that need ILEREM2 will use the first signature, so they must be recompiled. Other programs will use the second signature, which is the same as the old one, so they do not need recompilation.
- Adding new procedures multiple times results in multiple signatures.
Solution 2- Hardcoded single signature always.
-
Binder language source without procedure ILEREM2 but hardcoded signature
STRPGMEXP PGMLVL(*CURRENT) PGMLVL(*CURRENT) SIGNATURE(“MTHSRV02 V1.0”) EXPORT SYMBOL("ILEADD2") EXPORT SYMBOL("ILESUB2") EXPORT SYMBOL("ILEMUL2") EXPORT SYMBOL("ILEDIV2") ENDPGMEXP -
Signature – DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02) DETAIL(*SIGNATURE)
Display Service Program Information Display 1 of 1 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *SIGNATURE Signatures: D4E3C8E2D9E5F0F240E5F14BF0404040 -
Binder language source without procedure ‘ILEREM2’ but hardcoded signature.
STRPGMEXP PGMLVL(*CURRENT) PGMLVL(*CURRENT) SIGNATURE(“MTHSRV02 V1.0”) EXPORT SYMBOL("ILEADD2") EXPORT SYMBOL("ILESUB2") EXPORT SYMBOL("ILEMUL2") EXPORT SYMBOL("ILEDIV2") EXPORT SYMBOL("ILEREM2") ENDPGMEXP -
Signature – DSPSRVPGM SRVPGM(PIOLIB/MTHSRV02) DETAIL(*SIGNATURE)
Display Service Program Information Display 1 of 1 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *SIGNATURE Signatures: D4E3C8E2D9E5F0F240E5F14BF0404040 - Because signature does not even change after adding new procedure, no recompilation is used required for programs.
- This logic should be applied whenever new procedure is created.
Service Programs
ILE COBOL, Service Programs (*SRVPGM) are Integrated Language Environment (ILE) objects on the IBM i platform that package reusable procedures and data items for other programs to access.
Example – Bound by Reference – External Sub procedures (*SRVPGM) Main Program – MTHPGM02
PROCESS APOST, FLAG(29), LINKPRC,
NOPRTCORR, NOMONOPRC.
IDENTIFICATION DIVISION.
*-----------------------*
PROGRAM-ID. MTHPGM02.
AUTHOR. PROGRAMMERS.
ENVIRONMENT DIVISION.
*-----------------------*
CONFIGURATION SECTION.
SOURCE-COMPUTER. IBMi-Series.
OBJECT-COMPUTER. IBMi-Series.
SPECIAL-NAMES.
LINKAGE TYPE IS PROCEDURE FOR 'ILEADD2'.
LINKAGE TYPE IS PROCEDURE FOR 'ILESUB2'.
LINKAGE TYPE IS PROCEDURE FOR 'ILEMUL2'.
LINKAGE TYPE IS PROCEDURE FOR 'ILEDIV2'.
DATA DIVISION.
*--------------*
WORKING-STORAGE SECTION.
01 NUM1 PIC S9(9)V99 VALUE 250.
01 NUM2 PIC S9(9)V99 VALUE 25.
01 RES PIC S9(9)V99 VALUE 0.
PROCEDURE DIVISION.
*-------------------*
000-MAIN.
CALL PROCEDURE 'ILEADD2' USING NUM1, NUM2, RES.
CANCEL 'ILEADD2'.
DISPLAY RES.
CALL PROCEDURE 'ILESUB2' USING NUM1, NUM2, RES.
CANCEL 'ILESUB2'.
DISPLAY RES.
CALL PROCEDURE 'ILEMUL2' USING NUM1, NUM2, RES.
CANCEL 'ILEMUL2'.
DISPLAY RES.
CALL PROCEDURE 'ILEDIV2' USING NUM1, NUM2, RES.
CANCEL 'ILEDIV2'.
STOP RUN.
1. ‘MTHPGM02’ is main COBOL source. ‘ILEADD’, ‘ILESUB’, ‘ILEMUL’ and ‘ILEDIV’ are 4 other sub procedure into another COBOL source.
Service Program – MTHSRV02
*----------------------------------------------------------------*
* Procedure: ILEADD2 *
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEADD2.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
000-MAINLINE.
COMPUTE P-OP-RES = P-IN-NUM1 + P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEADD2.
*----------------------------------------------------------------*
* Procedure: ILESUB2 *
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. ILESUB2.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
000-MAINLINE.
COMPUTE P-OP-RES = P-IN-NUM1 - P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILESUB2.
*----------------------------------------------------------------*
* Procedure: ILEMUL2 *
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEMUL2.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
000-MAINLINE.
COMPUTE P-OP-RES = P-IN-NUM1 * P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEMUL2.
*----------------------------------------------------------------*
* Procedure: ILEDIV2 *
*----------------------------------------------------------------*
IDENTIFICATION DIVISION.
PROGRAM-ID. ILEDIV2.
DATA DIVISION.
LINKAGE SECTION.
01 P-IN-NUM1 PIC S9(9)V99.
01 P-IN-NUM2 PIC S9(9)V99.
01 P-OP-RES PIC S9(9)V99.
PROCEDURE DIVISION USING P-IN-NUM1, P-IN-NUM2, P-OP-RES.
000-MAINLINE.
COMPUTE P-OP-RES = P-IN-NUM1 / P-IN-NUM2.
EXIT PROGRAM.
END PROGRAM ILEDIV2.
*----------------------------------------------------------------*
-
When COBOL source MTHSRV02 is compiled using below CL command then, it generates following modules:
CRTCBLMOD MODULE(PIOLIB/MTHSRV02) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHSRV02) REPLACE(*YES) -
DSPJOBLOG
Module MTHSRV02 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILESUB2 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILEMUL2 created in library PIOLIB on 04/27/26 at 07:49:13. + Module ILEDIV2 created in library PIOLIB on 04/27/26 at 07:49:13. Member MTHSRV02 in file PIOLIB/QCBLLESRC changed with 57 records. AUT parameter ignored. Replaced object MTHSRV02 type *MODULE was moved to QRPLOBJ. Module MTHSRV02 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILESUB2 type *MODULE was moved to QRPLOBJ. Module ILESUB2 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILEMUL2 type *MODULE was moved to QRPLOBJ. Module ILEMUL2 created in library PIOLIB on 04/27/26 at 07:42:09. AUT parameter ignored. Replaced object ILEDIV2 type *MODULE was moved to QRPLOBJ. Module ILEDIV2 created in library PIOLIB on 04/27/26 at 07:42:09.
- It creates 4 modules MTHSRV02 (which has reference of ILEADD2), ILESUB2, ILEMUL2, ILEDIV2.
-
When service program MTHSRV02 is created using below CL command then, it generates service program. In CRTSRVPGM CL command, MODULE can hold up to 300 modules names can be specified.
CRTSRVPGM SRVPGM(PIOLIB/MTHSRV02) MODULE(PIOLIB/MTHSRV02 PIOLIB/ILESUB2 PIOLIB/ILEMUL2 PIOLIB/ILEDIV2) EXPORT(*ALL) -
DSPSRVPGM PIOLIB/MTHSRV02
Display Service Program Information Display 3 of 10 Service program . . . . . . . . . . . . : MTHSRV02 Library . . . . . . . . . . . . . . . : PIOLIB Owner . . . . . . . . . . . . . . . . . : AKUMAR Service program attribute . . . . . . . : CBLLE Detail . . . . . . . . . . . . . . . . . : *MODULE Type options, press Enter. 5=Display description 6=Print description Creation Optimization Debug Opt Module Library Attribute Date Level Data MTHSRV02 PIOLIB CBLLE 04/27/26 *NONE *YES ILESUB2 PIOLIB CBLLE 04/27/26 *NONE *YES ILEMUL2 PIOLIB CBLLE 04/27/26 *NONE *YES ILEDIV2 PIOLIB CBLLE 04/27/26 *NONE *YES -
Steps to bind the modules to generate single program.
CRTCBLMOD MODULE(PIOLIB/MTHPGM02) SRCFILE(PIOLIB/QCBLLESRC) SRCMBR(MTHPGM02) REPLACE(*YES) CRTPGM PGM(PIOLIB/MTHPGM02) MODULE(PIOLIB/MTHPGM02) ENTMOD(*FIRST) BNDSRVPGM((PIOLIB/MTHSRV02)) ACTGRP(*CALLER)After binding, MTHPGM02 *PGM object is generated. This program can be called using CALL CL command in command line.
Output (CALL PIOLIB/MTHPGM02)
00000027500 00000022500 00000625000 00000001000
Important:
- In CRTPGM CL command, BNDSRVPGM can hold up to 300 service program names can be specified.
- If duplicate module and library specifications are found, only the first instance of the duplicate, module and library is used.
- Once the program object is created, all modules are copied into the program object. And it does not check modules are present in specific library or not.
Adding service program to a Binding Directory
- Similar effect can be found if all service programs are added into a binding directory.
-
Steps to create binding directory.
CRTBNDDIR BNDDIR(PIOLIB/MATH02) ADDBNDDIRE BNDDIR(PIOLIB/MATH02) OBJ((PIOLIB/MTHSRV02 *SRVPGM))
-
WRKBNDDIRE PIOLIB/MATH02
Work with Binding Directory Entries Binding Directory: MATH02 Library: PIOLIB Type options, press Enter. 1=Add 4=Remove -------Creation-------- Opt Object Type Library Activation Date Time MTHSRV02 *SRVPGM PIOLIB *IMMED 04/27/26 08:14:07 -
Steps to bind the module to generate single program.
CRTPGM PGM(PIOLIB/MTHPGM02) MODULE(PIOLIB/MTHPGM02) ENTMOD(*FIRST) BNDDIR(PIOLIB/MATH02) ACTGRP(*CALLER)
Output (CALL PIOLIB/MTHPGM02)
00000027500 00000022500 00000625000 00000001000
Difference between RPGLE and CBLLE modules
| Feature | RPGLE | CBLLE |
|---|---|---|
| Compilation Command | CRTRPGMOD | CRTCBLMOD |
| Module Output | Generates a single module containing all procedures. | Generates multiple modules (one for each procedure). |
| Service Program Creation | Requires referencing only one module in CRTSRVPGM. | Requires hardcoding/listing every generated module in CRTSRVPGM. |
| Maintenance Effort | Lower: Binding remains simple even as procedures are added. | Higher: New procedures require updating the binding command with new module names. |