Rational Developer for System z
Enterprise PL/I for z/OS, Version 3.8, Language Reference Manual

Example 1

If the preprocessor input contains:

%DECLARE A CHARACTER, B FIXED;
%A = 'B+C';
%B = 2;
X = A;

the following is inserted into the preprocessor output:

X = 2+C;

The preprocessor statements activate A and B with the default RESCAN, assign the character string 'B+C' to A, and assign the constant 2 to B.

The fourth line is input text. The current value of A, which is 'B+C', replaces A in the preprocessor output. But this string contains the preprocessor variable B. Upon rescanning B, the preprocessor finds that it has been activated. Hence, the value 2 replaces B in the preprocessor output. The preprocessor variable B has a default precision of (5,0) and, therefore, actually contains 2 preceded by four zeros. When this value replaces B in the string 'B+C' it is converted to a character string and becomes 2 preceded by seven blanks.

Further rescanning shows that 2 cannot be replaced; scanning resumes with +C which, again, cannot be replaced.

If, in the above example, the preprocessor variable A was activated by this statement:

%ACTIVATE A NORESCAN;

the preprocessor output would be:

X = B+C;

Example 2

If the preprocessor input contains:

%DECLARE I FIXED, T CHARACTER;
%DEACTIVATE I;
%I = 15;
%T = 'A(I)';
S  = I*T*3;
%I = I+5;
%ACTIVATE I;
%DEACTIVATE T;
R  = I*T*2

the preprocessor output would be as follows (replacement blanks are not shown):

S = I*A(I)*3;
R = 20*T*2;

Example 3

This example illustrates how preprocessor facilities can be used to speed up the execution of a DO-group, such as:

DO I=1 TO 10;
Z(I)=X(I)+Y(I);
END;

The following would accomplish the same thing, but without the requirements of incrementing and testing during execution of the compiled program:

%DECLARE I FIXED;
%DO I = 1 TO 10;
Z(I)=X(I)+Y(I);
%END;
%DEACTIVATE I;

The third line is input text and is scanned for replacement activity. The first time that this line is scanned, I has the value 1 and has been activated. Therefore, the following is inserted into the preprocessor output:

Z(       1)=X(       1)+Y(       1);

Each 1 is preceded by seven blanks.

For each increment of I, up to and including 10, the input text is scanned and each occurrence of I is replaced by its current value. As a result, the following is inserted into the preprocessor output:

Z(       1)=X(       1)+Y(       1);
Z(       2)=X(       2)+Y(       2);
         .
         .
         .
Z(      10)=X(      10)+Y(      10);

When the value of I reaches 11, control falls through to the %DEACTIVATE statement.

Example 4

In the preprocessor input below, VALUE is a preprocessor function procedure that returns a character string of the form 'arg1(arg2)', where arg1 and arg2 represent the arguments that are passed to the function:

DECLARE (Z(10), Q) FIXED;
%A='Z';
%ACTIVATE A, VALUE;
Q = 6 + VALUE(A,3);
%DECLARE A CHARACTER;
%VALUE: PROC(ARG1,ARG2) RETURNS(CHAR);
        DCL ARG1 CHAR, ARG2 FIXED;
        RETURN(ARG1||'('||ARG2||')');
        %END VALUE;

When the scan encounters the fourth line, A is active and is thus eligible for replacement. Since VALUE is also active, the reference to it in the fourth line invokes the preprocessor function procedure of that name.

However, before the arguments A and 3 are passed to VALUE, A is replaced by its value Z (assigned to A in a previous assignment statement), and 3 is converted to fixed-point to conform to the attribute of its corresponding parameter. VALUE then performs a concatenation of these arguments and the parentheses and returns the concatenated value, that is, the string Z (3), to the point of invocation. The returned value replaces the function reference and the result is inserted into the preprocessor output. Thus, the preprocessor output generated is:

DECLARE (Z(10),Q) FIXED;
Q = 6+Z(       3);

Example 5

The preprocessor function procedure GEN defined below can generate a GENERIC declaration for up to 99 entry names with up to 99 parameter descriptors in the parameter descriptor lists. Only four are generated in this example.

 %DCL GEN ENTRY;
 DCL A GEN (A,2,5,FIXED);
   %GEN: PROC(NAME,LOW,HIGH,ATTR) RETURNS (CHAR);
 DCL (NAME, SUFFIX, ATTR, STRING) CHAR, (LOW, HIGH, I, J) FIXED;
 STRING='GENERIC(';
 DO I=LOW TO HIGH;                      /* ENTRY NAME LOOP*/
    IF I>9 THEN
       SUFFIX=SUBSTR(I, 7, 2);
                                        /* 2 DIGIT SUFFIX*/
    ELSE SUFFIX=SUBSTR(I, 8, 1);
                                        /* 1 DIGIT SUFFIX*/
    STRING=STRING||NAME||SUFFIX||' WHEN (';
    DO J=1 TO I;                        /* DESCRIPTOR LIST*/
       STRING=STRING||ATTR;
       IF J<I                           /* ATTRIBUTE SEPARATOR*/
          THEN STRING=STRING||',';
          ELSE STRING=STRING||')';
                                        /* LIST SEPARATOR */
    END;
    IF I<HIGH THEN                      /* ENTRY NAME SEPARATOR*/
       STRING=STRING||',';
    ELSE STRING=STRING||')';
                                       /* END OF LIST /*
 END;
 RETURN (STRING)
 % END;

The preprocessor output produced is:

 DCL A GENERIC(A2 WHEN (FIXED,FIXED),
               A3 WHEN (FIXED, FIXED, FIXED),
               A4 WHEN (FIXED, FIXED, FIXED, FIXED),
               A5 WHEN (FIXED, FIXED, FIXED, FIXED, FIXED));

Example 6

This example shows a preprocessor procedure that implements a statement of the form:

 SEARCH TABLE(array) FOR(value)
 USING(variable) AND(variable);

This statement searches a specified two-dimensional array for a specified value, using specified or default variables for the array subscripts. After execution of the statement, the array subscript variables identify an element that contains the specified value. If no element contains the specified value, both subscript variables are set to -22222.

The preprocessor procedure that implements this statement is:

 %SEARCH:
 PROC(TABLE,FOR,USING,AND) STATEMENT RETURNS(CHARACTER);

   DECLARE(TABLE,FOR,USING,AND,LABL, DO1,DO2) CHARACTER,
       (PARMSET,COUNTER) BUILTIN;

   IF PARMSET(TABLE) & PARMSET(FOR) THEN;
   ELSE SERR:DO;
   NOTE ('MISSING OR INVALID ARGUMENT(S)'||'FOR ''SEARCH''',4);
   RETURN ('/*INVALID SEARCH STATEMENT*/');
   END;

   IF ¬PARMSET(USING) THEN
     USING='I';
   IF ¬PARMSET(AND)   THEN
     AND='J';
   IF USING = AND  THEN
     GO TO SERR;

   LABL='SL'||COUNTER;
   DO1=LABL||': DO '||USING||'=LBOUND('||TABLE||',1)
     TO HBOUND('||TABLE||',1);';
   DO2='DO '||AND||'=LBOUND('||TABLE||',2)
     TO HBOUND ('||TABLE||',2);';

   RETURN(DO1||DO2||'SELECT('||TABLE
     ||'('||USING||','||AND||'));
   WHEN('||FOR||') LEAVE '||LABL||';
   OTHER;
   END '||LABL||';
   IF '||AND||' > H  BOUND('||TABLE||',2) THEN
     '||USING||','||AND||.' = -22222;');
 %END SEARCH;

The PARMSET built-in function is used to determine which parameters are set when the procedure is invoked. If USING is not set, the default array subscript variable I is used. If AND is not set, J is used. If TABLE or FOR is not set, or if the invocation results in the same variable being used for both subscripts, a preprocessor diagnostic message is issued and a comment is returned in the preprocessor output.

The COUNTER built-in function is used to generate unique labels for the preprocessor output returned by the procedure.

The procedure can be invoked with keyword arguments or positional arguments, or a combination of the two. The following invocations of the procedure produce identical results:

SEARCH TABLE(LIST.NAME) FOR('J.DOE') USING(I) AND(J);

SEARCH TABLE(LIST.NAME) FOR('J.DOE');

SEARCH(LIST.NAME) FOR('J.DOE');

SEARCH(LIST.NAME,'J.DOE');

SEARCH(,'J.DOE') TABLE(LIST.NAME);

The preprocessor output returned by any of these invocations is:

SL00001:
DO I=LBOUND(LIST.NAME,1) TO HBOUND(LIST.NAME,1);
   DO J=LBOUND(LIST.NAME,2) TO HBOUND(LIST.NAME,2);
      SELECT(LIST.NAME(I,J));
   WHEN('J.DOE') LEAVE SL00001;
   OTHER;
END SL00001;
IF J > HBOUND(LIST.NAME,2) THEN
   I,J = -22222;

The label SL00001 is returned only for the first invocation. A new unique label is returned for each subsequent invocation.


Terms of use | Feedback

This information center is powered by Eclipse technology. (http://www.eclipse.org)