Back to Compiler main page
Other programming languages like C and PL/1 support calls to procedures that have no declarations in the actual compile unit; they consider the undeclared procedure name to be an external name that will be resolved by the linkage editor.
When I tried the same with Pascal, I got syntax errors, because the compiler believed the identifier to be a variable; it complained already when the opening paranthese followed the procedure identifier (when calling the procedure).
This seemed unacceptable to me, so I first changed that.
The procedure SEARCHID inserted the unknown identifier into the ID list as a dummy var declaration; that's why there were more errors, when it was actually a procedure identifier (and a paranthese or a semicolon followed). Now the insert into the ID list is deferred until the next symbol has been read. (SEARCHID has to be extended with more parameters etc. to be able to do this).
In case of an undeclared procedure, the error code has been changed (from 104 "identifier not declared" to 184 "procedure not declared").
The error 184 has been changed to a warning, this way it is possible to generate code even for undeclared procedures and functions. The types of the parameters are taken from the types of the arguments, which will hopefully fit to the external definition of the procedure. If the arguments are variables, the args are passed by reference; if not, by value.
Note: it is possible that different calls to the same undeclared procedure generate different call sequences, if you provide different types of parameters, and if you mix expressions or constants with variables. The characteristics of one call are not recorded or compared with another call. If you call undeclared procedures, you do so at your own risk.
Another note: it is quite simple to force the compiler to generate a by-value call; if you put parantheses around the argument, it is an expression (no variable any more), and so a by-value parameter passing sequence will be generated ... BTW: much the same way as dummy arguments are created when using PL/1.
Undeclared functions, BTW, are supported in much the same way. Calls to undeclared functions produce the warning code 186 ("function not declared"); the function is supposed to return an integer result, and the parameters are passed according to the same rules as with undeclared procedures. If there is no opening paranthese following the function identifier, the identifier is (of course) considered to be an undeclared variable and will get an error 104, as before.
If you're not happy with all this, there is a simple solution: declare the procedure or function using the EXTERNAL directive.
BTW: when testing this, I discovered that external modules which contain global static variables (which are global inside the external modules, but local to them) use the same CSECT name (#PASMAI#) to store them, so there was a name conflict at linkage time, if two or more modules used this feature. This was resolved by creating a new attribute CSTNAME for declared procedures (which is the name of their STATIC CSECT) and by computing a CSTNAME (derived from the module name) for the dummy main program of an external module, too.
Back to Compiler main page