Rexx is a very flexible language. You can call other Rexx programs, you can call z/OS functions, or you can call functions written in C or assembler.
Programming a C function was not straight forward because it involved twisting and bending to get it to work – one of the downsides of being flexible.
See
What options are there?
You can use
- call function(p1,p2,p3) This gets passed an array of parameters, and has to return data in and an EVALBLOCK. See here.
- address link program “p1 p2 p3” where “p1 p2 p3” is a literal string which is passed to your program
- address linkmvs program “p1 p2 p3” where p1, p2, p3 are variable names, whose values are substituted before being passed to the program. If the parameter is not a variable – the parameter is passed through as is. The program gets passed a list
- length p1 value, p1 value
- length p2 value, p2 value
- length p3 value, p3 value
- address linkpgm program “p1 p2 p3” where p1, p2, p3 is a variable names, whose values are substituted before being passed to the program. If the parameter is not a variable – the parameter is passed through as is. The program gets passed a list of (null terminated values)
- p1 value
- p2 value
- p3 value
If you have code
a = "COLIN A"
address linkpgm CPQUERY "A B C"
The parameters received by the program are
- “COLIN A”
- “B”
- “C”
If you pass a string with hex value in it – it may have a 0x00 – which would look like an end of string. This means the linkpgm is not a good interface for passing non character data.
Passing back values
With address link you can pass back a return code. You can also use Rexx services to get and set variables in the calling rexx programs.
With address linkmvs and address linkpgm you can update the values passed in (this is non trivial). You can set a return code and use Rexx services to get and set variables in the calling rexx programs.
Which should I use?
address link
The simplest, where you have greatest control is address link. Your program gets passed a string which it can process.
address linkmvs and address linkpgm
These are similar, and you need to be careful.
A = "COLINA"
B = ""
P = "A B C"
(1) address linkmvs CPLINKM "A B C "
(2) address linkmvs CPLINKM "P"
(3) address linkmvs CPLINKM P
With the above, my program produces.
(1)
parm 0 >COLINA<
parm 1 is Null
parm 2 >C<
(2)
parm 0 >A B C<
(3)
parm 0 >COLINA<
parm 1 is Null
parm 2 >C<
If you are using linkpgm or linkmvs, the parameter specified will be substituted (if there is a variable with the same name).
my_stem. = "used for variables"
address linkmvs CPMVS "my_stem. "
If you want to specify a stem to your program so you can set my_stem.0, my_stem.1 etc you will not be using the value you specify, it will be used for variables.0 etc.
Using
address linkmvs CPLINKM "A 'B' C "
gives return code -2.
The return code set in RC may be -2, which indicates that processing of the variables was not successful. Variable processing may have been unsuccessful because the host command environment could not: Perform variable substitution before linking to or attaching the program.
noble! 8 2025 Chaining through control blocks with C. The terrible, the right and the difficult. excellent
LikeLike