I only have a couple of hints and tips for rexx users. They are just ways of doing things that I've found useful.
First of all, you should take a look at my startup model member. This is what I use to create all but the simplest of programs.
I establish the Error, Failure and Syntax signal routines as early as possible. Why? As I understand it, when a signal routine gets tripped, the rexx interpreter starts at the top of the program and scans through to the end looking for the named routine. If they are tucked toward the end of the program, intervening syntax errors can make the error handling routines impossible to find by the interpreter, so they will never get control. If these routines are parked at the top, it will almost always find them, despite whatever gross syntax errors are encountered further on.
Each of the "standard" signal routines in the model merely tell you the line that the error occured on, then they call a common cleanup routine. This is very useful to fix up the environment before returning to TSO. It can contain such things reflecting the source program name to the user (in case the program is nested), freeing allocated files, purging the data stack, nullifying outstanding ISPF LIBDEF's, or anything else that will gracefully recover from an error. An example cleanup routine of a really "messy" program that needs a good cleaning:
Cleanup:
Parse Pull Source /* to tell user which program died */
Say Source
Address TSO
"QSTACK"; Stacks = RC; /* to clean up the external data queue */
Do Stacks; "DELSTACK"; End;
x = Msg('OFF')
"FREE F(SOMEFILE)" /* to free up a file */
x = Msg(x)
Address ISPEXEC
"CONTROL ERRORS RETURN" /* in case there's no active libdef yet */
"LIBDEF ISPTLIB"
Return
Doing the above will help ensure that you can rerun the exec even if you encounter problems in a previous run.
A quick and dirty way to pass a complex set of parameters to an exec is to code this short routine:
SomeRoutine:
Arg Vars .
Do While Length(Vars) > 0
Parse Var Vars Var '=' Val ',' Vars
Interpret Var '= "'Val'"'
End
Return
This is pretty minor, but another general rule I try to follow is to always include a null token at the end of parse instructions to accept any arguments that I'm not expecting to receive. It also ensures that any trailing blanks are discarded. So instead of coding "Arg OneParm", I code "Arg OneParm .". I've always found this makes the code more robust. You never know when someone is going to add a comment to the args they are passing you!
I will add tips and hints to this page as I think of them.
Return to the Rexx Home page.