Page 1 of 1

Test for missing DD statement from ALC

PostPosted: Wed Oct 13, 2021 10:33 pm
by JimStout
I wrote a tool in assembler that is used by a large group of people. Recently, I made a change to the code to allow for passing parameters using a SYSIN DD statement in the JCL. Unfortunately, old versions of the JCL will abend with a S0C4 if the SYSIN DD statement is missing. I would prefer to have the program terminate "gracefully" and issue a message that tells the user that they must code the SYSIN DD statement. Is there a was to programmatically test for the presence of a DD statement in Assembler? Thanks in advance.

Re: Test for missing DD statement from ALC

PostPosted: Wed Oct 13, 2021 11:26 pm
by sergeyken
You may need to organize a loop (looking for 'SYSIN' name) across the TIOT table, which includes one element per each DD statement of the job step.

The address of TIOT location can be obtained using IBM macro:
  EXTRACT results,'S',FIELDS=(TIOT)


https://www.ibm.com/docs/en/zos/2.1.0?topic=uemfua-procedures
Procedures

1. Issue the EXTRACT macro with the FIELDS=TIOT parameter to extract the TIOT from the TCB.
2. Search the TIOT for the DD name associated with the shared data set.

Re: Test for missing DD statement from ALC

PostPosted: Wed Oct 13, 2021 11:51 pm
by sergeyken
Another way might be - using the RDJFCB macro.

Take a look at the example by steve-myers from this topic: https://ibmmainframes.com/about64733.html

Re: Test for missing DD statement from ALC

PostPosted: Thu Oct 14, 2021 12:05 am
by steve-myers
In my opinion, the easiest way is the the DEVTYPE macro.
         DEVTYPE =CL8'DDNAME',OUTPUT
         LTR   15,15
         BZ    DDOK
         ...
DDOK     ...
         ...
OUTPUT   DC    XL16'0'
Rather than use =CL8'DDNAME' I generally point to the DD name character string in the DCB: DCBDDNAM-IHADCB+DCB.

Searching the TIOT as proposed by sergeyken is another way to do it, but it's more involved and requires a loop. The exit from the loop is not exactly obvious to a beginner, and requires rather detailed understanding of the structure of the TIOT.

Another alternative is to test the DCB after the OPEN to see if it is open.
         OPEN  (DCB,...)
         TM    (DCBOFLGS-IHADCB)+DCB,DCBOFOPN
         BO    DDOK
         ...
DDOK     ...
         ...


The DCB symbols are all defined in the DCBD macro.

The RDJFCB macro proposed by sergeykeyn is another option, but it also requires setup that is not immediately obvious to a beginner.
         RDJFCB  (DCB,...)
         LTR   15,15
         BZ    DDOK
         ...
DDOK     ...
         ...
DCB      DCB   EXLST=XLIST,...
         ...
XLIST    DC    0A(0),AL1(X'80'+7),AL3(JFCB)
JFCB     DC    XL176'0'


I've used all these methods at various times in my career; use the one that seems simpler and more understandable to you. FWIW, while I've scanned the TIOT, it has been for other reasons, not to see if a single DD is defined in it.

Re: Test for missing DD statement from ALC

PostPosted: Thu Oct 14, 2021 12:28 am
by sergeyken
Those are very elegant solutions proposed by steve-myers.

The only disadvantage is: there may be multiple reasons for them to produce non-zero RC, not only "missing DD statement".

Re: Test for missing DD statement from ALC

PostPosted: Thu Oct 14, 2021 1:05 am
by JimStout
I just coded the DEVTYPE macro as Steve suggested. Immediately after the DEVTYPE macro, I code a halfword of zeros to force a S0C1 abend (a sledgehammer approach but it works!) and looked at R15. When the SYSIN DD is present, R15=0 which is expected. With the SYSIN DD missing, R15=4! The return codes in the DEVTYPE macro list this as "DD Name Not Defined"! This is perfect! Thank you Steve!

Re: Test for missing DD statement from ALC

PostPosted: Thu Oct 14, 2021 1:43 am
by steve-myers
sergeyken wrote:Those are very elegant solutions proposed by steve-myers.

The only disadvantage is: there may be multiple reasons for them to produce non-zero RC, not only "missing DD statement".
Well, maybe. RDJFCB will ABEND if the setup is not correct.

According to the manual, DEVTYPE returns 0 & 4. 4 has a variety of meanings depending on options in the macro that are not used in the example, which leaves no DD statement.

According to the manual, RDJFCB returns 0, 4 and 8. 4, too, has multiple meanings, none of which should apply to an innocent user checking for DD name. 8 applies to a different use of the RDJFCB macro than used in the example. As with DEVTYPE, you would hard pressed to interpret non-zero as anything other than missing DD.

This leaves testing DCBOFOPN after OPEN, which is either on or off; there is no "return code."

Re: Test for missing DD statement from ALC

PostPosted: Thu Oct 14, 2021 1:47 am
by steve-myers
sergeyken wrote:Those are very elegant solutions proposed by steve-myers.

The only disadvantage is: there may be multiple reasons for them to produce non-zero RC, not only "missing DD statement".
Well, maybe. RDJFCB will ABEND if the setup is not correct.

According to the manual, DEVTYPE returns 0 & 4. 4 has a variety of meanings depending on option in the macro that are not used in the example, which leaves no DD statement.

According to the manual, RDJFCB returns 0, 4 and 8. 4, too, has multiple meanings, none of which should apply to an innocent user checking for DD name. 8 applies to a different use of the RDJFCB macro than used in the example. As with DEVTYPE, you would hard pressed to interpret non-zero as anything other than missing DD.

This leaves testing DCBOFOPN, which is either on or off; there is no "return code."

Re: Test for missing DD statement from ALC

PostPosted: Sat Oct 16, 2021 8:59 pm
by steve-myers
Scanning the TIOT for a specific DD name is possible, but it requires detailed knowledge of the structure of the TIOT, and the method to exit the scan loop is not obvious to a beginner
         L     15,CVTPTR           Load address of the CVT
         L     15,CVTTCBP-CVTMAP(,15)  Load address of the TCB pointers
         L     15,4(,15)           Load address of the current TCB
         L     2,TCBTIO-TCB(,15)   Load address of the TIOT
         LA    2,TIOENTRY-TIOT1(,2)  Compute address of the first
*                                     DD entry in the TIOT
         SR    0,0                 Init reg 0
NEXTDD   CLC   =CL8'DDNAME',TIOEDDNM-TIOENTRY(2)  Test DD name
         JE    DDOK                Br if DD name in TIOT
         ICM   0,B'0001',TIOELNGH-TIOENTRY(2)  Load length of the DD
*                                               entry
         JZ    DDBAD               Br if DD not in TIOT
         AR    2,0                 Compute address of next DD entry
         J     NEXTDD
DDBAD    NOPR  0
DDOK     NOPR  0
         CVT   DSECT=YES
         IKJTCB ,
         IEFTIOT1 ,
I have never liked the EXTRACT macro for several reasons I won't discuss here. The code to find the TIOT address in the example works on every OS/360 derived system through z/OS 2.5. In some systems the TIOT is above the line, so this code should be run AMODE 31.

The last three lines call macros that define the CVT, TCB and TIOT data areas used in the code fragment.