PDA

View Full Version : nicht deklarierte Variable QTIME lässt sich fehlerfrei compilieren?



hteufl
02-09-18, 10:21
Hallo!
Ich habe ein für mich unerklärbares Phänomen von CL Variablen gefunden. Und zwar habe ich irrtümlich in einer IF Abfrage eine Variable QTIME verwendet die so nicht im Programm deklariert war. Beim Compilieren wurde das Programm mit einem 00 Fehlercode korrekt umgewandelt. Ich wollte daher wissen warum das Programm die Variable akzeptiert hat. Das Programm hat natürlich nicht funktioniert, weshalb ich erst beim Programmdebug auf diesen Umstand gestoßen bin. Vielleicht hat einer von Euch Spezialisten eine Erklärung für mich!
Anbei ein Ausschnitt aus dem CL Code:

PGM
DCL VAR(&ENDSTS) TYPE(*CHAR) LEN(1)
DCL VAR(&ERROR) TYPE(*CHAR) LEN(1) VALUE('0')
DCL VAR(&QDATETIME) TYPE(*CHAR) LEN(20)
DCL VAR(&QTIME) TYPE(*CHAR) LEN(6)
DCL VAR(&SYSNAME) TYPE(*CHAR) LEN(8)
DCL VAR(&USER) TYPE(*CHAR) LEN(10)
DCL VAR(&WS) TYPE(*CHAR) LEN(10)
/*-------------------------------------------------------------------*/
/* Standardfehlerbehandlung */
/*-------------------------------------------------------------------*/
/* CPF0001 .. Fehler im Befehl xxx gefunden. */
MONMSG MSGID(CPF0001) +
EXEC(GOTO CMDLBL(PROTOK))
/*-------------------------------------------------------------------*/
RTVJOBA JOB(&WS) USER(&USER)
RTVNETA SYSNAME(&SYSNAME)
/*-------------------------------------------------------------------*/
/* Kontrolle ob ein Systemabschluss erfolgt */
/*-------------------------------------------------------------------*/
START:
RTVJOBA ENDSTS(&ENDSTS)
RTVSYSVAL SYSVAL(QTIME) RTNVAR(&QTIME)
RTVSYSVAL SYSVAL(QDATETIME) RTNVAR(&QDATETIME)

IF COND(&ENDSTS *NE '1') +
THEN(DO)
/*-------------------------------------------------------------------*/
/* Daten in TSPL02/TSPL07 korrigieren */
/*-------------------------------------------------------------------*/
SELECT
WHEN COND((&QTIME *GT '000000') *AND +
(&QTIME *LT '080000')) +
THEN(DO)
DLYJOB RSMTIME('08:01:00')
GOTO CMDLBL(START)
ENDDO

WHEN COND((&QTIME *GE '080000') *AND +
(QTIME *LT '090000')) +
THEN(DO)
TSPL02E UPDATE(J)
DLYJOB RSMTIME('09:01:00')
GOTO CMDLBL(START)
ENDDO

WHEN COND((&QTIME *GE '090000') *AND +
(&QTIME *LT '100000')) +
THEN(DO)
TSPL02E UPDATE(J)
DLYJOB RSMTIME('10:01:00')
GOTO CMDLBL(START)
ENDDO

WHEN COND((&QTIME *GE '200000')) +
THEN(DO)
TSPL02E UPDATE(J)
ENDDO

ENDSELECT
/*-------------------------------------------------------------------*/
ENDDO /* enddo &ENDSTS *NE '1' */
ENDPGM

Wie beschrieben lässt sich das Programm trotz Fehler (meine Meinung) compilieren und ausführen. Natürlich funktioniert die Zeitabfrage 08:00:00/09:00:00 nicht!
Das Ganze läuft unter dem Betriebssystem V7R3M0 und allen aktuellen PTFs!

Vielen Dank im Voraus

Hermann

holgerscherer
02-09-18, 10:50
Hallo!
Ich habe ein für mich unerklärbares Phänomen von CL Variablen gefunden.

It's not a bug, it's a feature :)

QTIME wird hier als non-quoted Character String erkannt, und hat genau diesen Wert: "QTIME"...

Und neu ist das auch nicht, gerade eben auf V5R3 getestet:


PGM
IF COND(QTIME *EQ 'QTIME') THEN(SNDMSG +
MSG('hallo!') TOUSR(*REQUESTER))
ENDPGM

liefert als Ergebnis "hallo!" in die msgq

Nachtrag: in MI umgewandelt steht das auch schön brav als Literal drin - ist also Absicht:

CMPBLAP(I) <0005!QTIME>,<0005!QTIME>,' '/ EQ(?4TEMP0001)

siehe auch https://www.ibm.com/support/knowledgecenter/en/ssw_i5_54/rbam6/rbam6charstrngexp.htm

-h

Fuerchau
02-09-18, 12:03
Das hat noch nicht mal was mit CL's zu tun sondern ist Bestandteil der CMD-Syntax.
Stell dir vor, alle Namen und Werte die man so verwendet müssten immer in Hochkommata, wobei diese Werte dann noch casesensitive wären.

Die Eingabe "cAlL pgM(MyPgm)" macht automatisch einen "CALL PGM(MYPGM)" draus, da alle Zeichen die nicht zwischen Hochkommata stehen, in Großbuchstaben gewandelt werden.

Stand (bei mir seit) V2R1!

RPG/COBOL können das nicht, bei SQL wurde das mit den "globalen Variablen" wieder eingeführt. Man kann sich auf den SQL-Compiler einfach nicht mehr verlassen.
Damit ist auch Birgitta's Aussage klar, nach jedem SQL den SQLCODE abzufragen, denn der -206 deutet in 99,997% aller Fälle auf einen Runtime-Tippfehler hin (hatten wir früher nicht), den man sonst kaum bemerkt und sich nur wundert warum es denn nicht klappt.

hteufl
04-09-18, 07:15
Guten Morgen!

Erst einmal vielen Dank für die umfassenden Antworten! Jetzt ist es klar, dass wenn QTIME mit 090000 verglichen wird, dass die Routine danach abläuft (im EBCDIC Code sind meiner Meinung nach Zahlen hinter den Buchstaben gereiht). Man lernt eben nie aus!!

Vielen Dank für Eure Antworten und
liebe Grüße aus Österreich

Hermann