How to use the binder language to manage service programs -- Part 1: Service program signatures
Learning to use the ILE binder language is essential to managing all but the simplest service programs. True, you can create service programs without using the binder language, but when you start modifying and updating existing service programs, careful use of the binder language can save you hours of work recreating programs that use those service programs.
Understanding service program signaturesBefore discussing the binder language, it is important to understand the role of service program signatures and how they affect ILE applications. When you create a service program, the binder (a.k.a. the linker) creates one or more signatures for the service program -- one current signature and zero or more previous signatures (more on this later). The signatures are stored with/in the service program object.
When an ILE program that uses a service program is created, the service program's current-level signature (or current signature) is stored in the ILE program. When the ILE program is subsequently executed, the signature in the ILE program is checked against all the signatures (current and previous) stored in the service program. If the copy of the signature stored in the program does not match any of the signatures in the service program, the program will receive an error.
This signature matching is the functional equivalent to the level checking that takes place for files and, in fact, is called level checking. It allows the system to ensure that the ILE program and the service programs it uses are still compatible before the ILE program starts running.
Current-level vs. previous-level signaturesWhen a service program is first created, it has one signature -- a current signature. If, for example, you later add a new procedure to the service program and do not use the binder language, the current signature will be replaced with a new, but different, current signature and any existing programs that were linked using the original version of the service program will generate level-check errors when run.
This can be avoided by using the binder language to save the original current signature as a previous-level signature (or previous signature) -- along with the new current signature -- in the modified service program. The service program will then have two signatures. This way any existing programs that were linked using the original service program -- those programs that have the original current signature stored in them -- will run without error because the signature will match one of the service program's two signatures. They will match the previous level signature.
SummaryService program signatures are used to verify service program compatibility. Similar to file and record level IDs, and file and record level-checking.
Service programs can contain many signatures, one current signature and zero or more previous signatures. This allows the designer to maintain a number of different compatibility levels for a single service program.
How to use the binder language to manage service programs -- Part 2: Understanding the binder language
In Part 1, we discussed service program signatures and defined the differences between current and previous signature levels. In this installment, we will discuss the very simple binder language and how you use it to create service program signatures.
How to use the binder language to manage signaturesThe primary purpose of the binder language is to allow you to manage a service program's signatures. The language is made up of only three commands that must be entered in a strict sequence to make up logical units called export blocks. One signature is generated for each export block that you define. The binder language commands are listed below in the required sequence:
STRPGMEXP. The Start Program Export command is used to start the definition of a new export block (i.e., a block of Export commands). It is also used to control the generation and type of the signature associated with the export block.
EXPORT. The Export command is used to specify that a procedure or data item in the associated service program should be exported, that is made available to other programs and service programs. Procedures and data items that are not exported are considered private and cannot be used by other programs. The order in which the exports are listed is paramount in signature generation; system-generated signatures are created from the names and the order of exported items.
ENDPGMEXP. The End Program Export command is used to end an export block.
Of the three binder language commands, the STRPGMEXP command is the only one that is even remotely complex. (EXPORT has only one parameter, and ENDPGMEXP doesn't have any.) The STRPGMEXP command has three parameters:
Program level (PGMLVL). This parameter lets you specify whether the signature generated for this export block is the current signature or a previous signature. Valid values are *CURRENT and *PRV.
Signature level check (LVLCHK). This parameter is inappropriately named. It does not control in any way the signature matching that the system does when the program is activated. When *NO is specified for this parameter, the system simply generates a signature consisting of all hex zeros -- a valid signature that must still match the signature in the client program. Specifying LVLCHK(*NO) is the equivalent to specifying LVLCHK(*YES) and SIGNATURE(x'00').
Signature (SIGNATURE). This parameter lets you specify the signature value associated with this export block. The default value is *GEN, which instructs the system to generate the signature. The result is a hash of the names and order of the exports, producing a unique value that can be used to verify interface compatibility.
When you specify your own signature (or when you specify *NO for the LVLCHK parameter), it becomes your responsibility to make sure the programs that use the service program are compatible with its interface. The value *GEN is required when LVLCHK(*NO) is specified so that the system can guarantee that the special signature value of all hex zeros is properly generated.
I cannot emphasize enough that specifying LVLCHK(*NO) or hard-coding your own signature should be done only in extraordinary circumstances.
Understanding the importance of export blocksThe items listed in an export block (i.e., those procedures and data items specified on Export commands) are used not only to generate signatures but also to create a cross-reference table in the associated service program. Created solely from the *CURRENT level export block, this cross-reference table is known by many names, including export resolution table, exported symbol table and public interface. No matter what you call it, this table contains the names of all the items specified on the EXPORT commands in the order they were specified.
Remember: Only the *CURRENT level export block (not any of the *PRV level export blocks) is used to generate this table, which contains the names of the data items and procedures that are currently available for use from the associated service program.
The table also contains the addresses of (i.e., pointers to) all the exported items. For example, if a procedure called P1 is exported, its name is placed in the table along with a pointer to the actual procedure within the service program.
When a program that uses a service program is created (i.e., linked/bound), the export resolution table is searched to try to resolve procedure calls (and external data items). When a match is found, the index of that matching table entry is stored in the program. When the program is later run, the index is used to locate the associated pointer in the table. Access to the exported procedure (or data item) is then made through the pointer.
Using the P1 procedure as an example, suppose P1 is the fourth item in the export resolution table. When a program that calls P1 is created, the number 4 is stored in the program. When the program is run, that number 4 is used to locate the table entry that contains the pointer to the actual P1 procedure. The process is actually a bit more complicated, but the important thing to remember is that the name "P1" is not used after the linking process. Only the table index numbers and the pointers are used at run-time.
That is important because you can rename a service program procedure without needing to recreate the programs that call the procedure, as long as the new name remains in the same ordinal position within the *CURRENT export block.
How to create and edit binder language sourceAs with most iSeries languages, you create and edit binder language source using SEU. The default source file name for the binder language is QSRVSRC, and the source type (i.e., the member type) is BND. Prompting for the binder language commands is supported using a CL-type prompting method. That is, you type the command and then press F4 to prompt for the associated command parameters.
The names of the source file and member containing the binder language source for a particular service program are specified on the CRTSRVPGM command when you create the service program (or when you use the UPDSRVPGM command to update a service program).
To use binder language source when creating a service program, specify *SRCFILE on the EXPORT parameter on the CRTSRVPGM command. Then specify the source file name and member name on the SRCFILE and SRCMBR parameters, respectively. Since the default for the SRCMBR parameter is *SRVPGM, it is advisable to give the binder language source member the same name as the associated service program.
How to use the binder language to manage service programs -- Part 3: Examples and pitfalls
Learning to use the ILE binder language is essential to managing all but the simplest service programs. True, you can create service programs without using the binder language, but when you start modifying and updating existing service programs, the careful use of the binder language can save you hours of work recreating the programs that use those service programs.
In Part 1, we discussed service program signatures and defined the differences between current and previous signature levels. In Part 2, we discussed the very simple binder language and how you use it to create service program signatures. In this final installment, we will look at some specific examples, along with some pitfalls you need to be aware of.
Examples: Service programs and the binder languageSince there is only one export resolution table per service program (and not one per signature), care must be taken when adding new procedures or data items (or modifying existing ones) to an existing service program. Note: This applies only to procedures and data items that are exported. For example, consider a simple service program that contains a single procedure TOUPPERCASE that converts a character string to all upper case. TOUPPERCASE accepts two parameters: String, which contains the string to be converted, and StringLen, which contains the length of the string. The binder language source for this service program is shown below: STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) ENDPGMEXP
Now suppose that after creating some applications that use the TOUPPERCASE procedure, you want to add a TOLOWERCASE procedure to the service program, which of course will convert a character string to all lower case. To do this without having to relink all the programs that already use the service program, you need to perform the following steps by editing the binder language source code shown above:
Copy the existing export block. You should then have two identical export blocks, one right after the other.
In the second export block, change the PGMLVL parameter from *CURRENT to *PRV.
Add the new TOLOWERCASE procedure to the end of the export list in the first export block, which will be the new *CURRENT export block. It is very important that you add new exports to the end of the export list in order to maintain compatibility with existing applications that use this service program.
The updated binder language source is shown below: STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) EXPORT SYMBOL(TOLOWERCASE) ENDPGMEXP STRPGMEXP PGMLVL(*PRV) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) ENDPGMEXP
The level-checking delusionLet's take a quick look at the trap you can fall into if you take the LVLCHK parameter literally. Suppose in the course of adding the new TOLOWERCASE procedure to our service program, we decide that we don't care about the level checking and we just "turn it off."
Although the binder language source shown below appears to do this and seems to be an alternative method for adding a new procedure, it is not! That is because a new current signature of all hex 00s will be generated for the service program, and it will not match the signatures stored in the programs that already use the service program. Remember: The LVLCHK parameter does not control whether level checking is done; it controls only whether the signature generated is all zeros or a unique identifier. STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*NO) EXPORT SYMBOL(TOUPPERCASE) EXPORT SYMBOL(TOLOWERCASE) ENDPGMEXP
Changing procedure namesNow let's suppose we want to shorten the names of the procedures in the service program so they are more convenient to call (or for whatever other reason). The new binder language source code shown below is an example of how that can be done without having to recreate the programs that already use the service program. The important point here is that the procedure names in the export list must remain in the same ordinal position so that the pointers in the resulting export resolution table will point to the same procedures, even though the procedure names have been changed. STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*YES) EXPORT SYMBOL(TOUPPER) EXPORT SYMBOL(TOLOWER) ENDPGMEXP STRPGMEXP PGMLVL(*PRV) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) EXPORT SYMBOL(TOLOWERCASE) ENDPGMEXP STRPGMEXP PGMLVL(*PRV) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) ENDPGMEXP
It is also important to remember that while existing programs that use the old names will work just fine as is, they will not if you ever have to change them for any other reason. That is, if you have to relink a program for any reason, you will have to update the source members for that program with the new procedure names. That is because when you relink a program, the linker won't be able to find the old names. You could get around that by making a new set of procedures (with the shorter names) and making them "shells" of the original set; that is, the new, shorter-name procedures would simply call the original procedures. Then you would have two sets of procedures to maintain backward link compatibility. The binder language source for this alternative is shown below: STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) EXPORT SYMBOL(TOLOWERCASE) EXPORT SYMBOL(TOUPPER) EXPORT SYMBOL(TOLOWER) ENDPGMEXP STRPGMEXP PGMLVL(*PRV) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) EXPORT SYMBOL(TOLOWERCASE) ENDPGMEXP STRPGMEXP PGMLVL(*PRV) LVLCHK(*YES) EXPORT SYMBOL(TOUPPERCASE) ENDPGMEXP
Adding new parameters to an existing procedureSince signatures validate service programs only at the program level and not at the procedure level, you can add parameters to an existing procedure without requiring any change in the binder language source. This assumes, of course, that the language in which the procedure is written supports a variable number of parameters. This way, existing programs that call the procedure with the original number of parameters will not require relinking.
SummaryService program signatures are used to verify service program compatibility. Similar to file/record level IDs and file/record level-checking.
Service programs can contain many signatures, one current signature and one or more previous signatures. This allows the designer to maintain a number of compatibility levels for a single service program.
The primary role of the binder language is to maintain service program signatures. It is also used to define which procedures and data items are exported from (i.e., allowed to be used by other programs) the service program.
Export blocks define signatures. The list of the procedures and data items exported from the service program make up an export block. The list is also used to generate the signature.
SEU is used to edit binder language source. Prompting and syntax-checking is available when you use source type BND.
************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************************
MAIN MODULE ( TYPE RPGLE , COMPILE WITH 15 )
DPROC11 PR
DDATA1 5 0
DDATA2 5 0
*
DDATA1 S 5 0
DDATA2 S 5 0
C EVAL DATA1=5
C CALLP PROC11(DATA1:DATA2)
C SETON LR
SUB MODULE ( TYPE RPGLE , COMPILE WITH 15 )
H NOMAIN
DPROC11 PR
DDATA1 5 0
DDATA2 5 0
DPROC21 PR
DDATA1 5 0
DDATA2 5 0
DPROC31 PR
DDATA1 5 0
DDATA2 5 0
PPROC11 B export
DPROC11 PI
DDATA1 5 0
DDATA2 5 0
DRESULT S 5 0
C EVAL DATA1=5
C EVAL DATA2=5
C EVAL RESULT = DATA1 * DATA2
C RESULT DSPLY '*EXT'
PPROC11 E
PPROC21 B export
DPROC11 PI
DDATA1 5 0
DDATA2 5 0
DRESULT S 5 0
C EVAL DATA1=5
C EVAL DATA2=5
C EVAL RESULT = DATA1 * DATA2
C RESULT DSPLY '*EXT'
PPROC21 E
PPROC31 B export
DPROC31 PI
DDATA1 5 0
DDATA2 5 0
DRESULT S 5 0
C EVAL DATA1=5
C EVAL DATA2=5
C EVAL RESULT = DATA1 * DATA2
C RESULT DSPLY '*EXT'
PPROC31 E
Bindry Language obj( TYPE bnd , never COMPILE it )
( How to create (1)open SEU ( 2) then write like Cl pgm as below:
STRPGMEXP PGMLVL(*CURRENT) LVLCHK(*YES)
EXPORT SYMBOL(PROC11)
ENDPGMEXP
Now we have three
Amod (Main) , Amod1(Sub module) , BND1 ( is bindry language)
Then first create srivice pgm as below1
Then:-
CRTPGM
Important Commands:-
(1) DSPSRVPGM to see description about SERVICE PROGRAM.
DSPSRVPGM SRVPGM(SRV1) DETAIL(*SIGNATURE)
(2) RTVBNDRSC to retrive binder source
Wednesday, July 8, 2009
Subscribe to:
Posts (Atom)