On 6/24/2010 7:15 PM, Craig A. Berry wrote:

On Jun 24, 2010, at 5:54 PM, John E. Malmberg wrote:

On 6/24/2010 2:03 PM, Mark Berryman wrote:

Link /NoTrace/NoMap/Trace/Exe=MINIPERL.EXE miniperlmain.obj,
libperlmini.olb/Library/Include=globals ,[]crtl.opt/Options
%ILINK-W-NOSUCHMOD, module GLOBALS not found
in library USERS:[BERRYMAN.PERL-5_12_1]LIBPERLMINI.OLB;1
%ILINK-W-NUDFSYMS, 8 undefined symbols:
%ILINK-I-UDFSYM, lib$find_image_symbol
%ILINK-I-UDFSYM, lib$initialize
%ILINK-I-UDFSYM, lib$rename_file
%ILINK-I-UDFSYM, sys$filescan
%ILINK-I-UDFSYM, sys$get_security
%ILINK-I-UDFSYM, sys$getdviw
%ILINK-I-UDFSYM, sys$set_security
%ILINK-I-UDFSYM, sys$sigprc

Those undefined symbols should be easy to fix, they just need to be
declared in upper case in the source file. I am trying to remember if
I submitted a patch to do that before.

Unfortunately the system header files for defining those routines is
generated by a program that has not been updated to properly generate
function prototypes from the source file it uses. That is why I never
use that file, and instead manually prototype the system services. The
proper prototypes make several common programming errors to be
detected by the compiler.


Well, whatever the "proper" prototypes are, several of the prototypes in
[.vms]vms.c have type mismatches compared to the prototypes in the
system-supplied headers. The only reason we don't see the mismatches all
the time is because the system headers have #defines to make the routine
names upper case as seen by the compiler and vms.c doesn't. If we add
#defines like that in vms.c, then the compiler sees that the functions
are the same ones already prototyped in lib$routines.h or starlet.h and
knows that we're providing incompatible prototypes.

So I think these home-rolled prototypes have to go. It's the system's
job to prototype system-supplied routines in the system-supplied
headers. Trying to second guess that just makes the code more fragile. I
don't know of any way to undo a prototype the compiler has already seen,
and I'm not about to take on the maintenance burden of keeping up our
own versions of starlet.h and lib$routines.h so that we can prevent the
compiler from seeing the system-supplied prototypes.

Unfortunately the system prototypes for lib$* and sys$* are not much better than no prototypes at all. They tend to use void * and '__unknown_params' instead of the type that the program is likely to supply, and they are missing the const qualifiers.

Unfortunately that tool was written to generate headers for K & R, and has never been updated to generate proper ANSI definitions.

It may be the systems job to provide the correct headers, and it does for the structures and the constants, but in my opinion it is not doing the job correctly for the sys$* and lib$* routines. Setting the __NEW_STARLET macro fixes some but not all the issues for starlet.h, however code that needs to build on older versions of VMS can not depend on that macro working.

Those definitions are limited to header files named starlet.h and *$routines.h and with the home rolled definitions, there is no reason to include them, as all they have is almost useless prototypes.

If the home rolled ones are generating errors, then either they should be fixed or the code calling them is not using the correct types and should be fixed. When used properly they will catch programming errors, and they can also help the compiler create more optimal code, even when building on the oldest version of VMS that perl can be built on.

I filed an enhancement request to get the tool that generates the system headers fixed, but have no idea if or when VMS engineering will get to it. The source file used to generate the headers has the needed information, and the tool generates the prototype equivalent for other languages correctly.

One reason given for not enhancing the tool is that there is existing code depending on the incomplete prototypes. But that can be handled by having a macro definition similar to the NEW_STARLET.

The code that currently uses LIB$FIND_IMAGE_SYMBOL needs to be updated
to do the following:

1. If the symbol is over 31 characters:
a. Try loading it in exact case but CRC shortened the way the
C compiler does.
b. Try loading it in upper case but CRC shortened the way the
C compiler does.
c. Try loading it in exact case but truncated to 31 characters.
d. Try loading it in upper case but truncated to 31 characters.
2. For symbols 31 characters or less, try looking for it in exact case
first and then in all upper case.

We have complete control over how the symbols are created at build time.
I can't see any good reason to add this level of complexity and
processing at run time.

It gives us more flexibility in what images that we can dynamically load. It will also allow the eventual retirement of VMS specific code in the XS generation instead of trying to keep it in sync when there are changes, and it avoids issues like Mark is seeing.

-John
wb8...@qsl.network
Personal Opinion Only

Reply via email to