PRB: Reference to _pgmptr in CRTEXE.OBJ Is Invalid

ID Number: Q66290

6.00 6.00a 6.00ax

OS/2

buglist6.00 buglist6.00a buglist6.00ax

Summary:

SYMPTOMS

In Microsoft C versions 6.0, 6.0a, and 6.0ax, if build options are

set to "PM multithreaded EXE with runtime in DLL" for a program

that uses _pgmptr to find the path of the executable program, the

resulting .EXE will show _pgmptr containing all zeros.

CAUSE

This problem occurs because while _pgmptr exists in CDLLOBJS.DLL,

there is no reference to _pgmptr in CDLLOBJS.DEF, and there is an

invalid reference to it in CRTEXE.OBJ. Because of this, you are

unable to access it from your program. The first problem is easily

corrected by adding _pgmptr to the .DEF file. The second is not

possible to correct because Microsoft does not release the source

code to CRTEXE.OBJ.

RESOLUTION

There is a workaround if a DLL is used to access _pgmptr.

Fortunately, the .OBJ file that links the startup code into the DLL

does have the correct code to perform the function. The sample code

below gives an example of how this is done.

STATUS

Microsoft has confirmed this to be a problem in C versions 6.0,

6.0a, and 6.0ax. We are researching this problem and will post new

information here as it becomes available.

More Information:

Sample Code

-----------

//In your main application, prototype a function to take the place of

//_pgmptr. For instance:

//

//char *DLLpgmptr(void); // returns _pgmptr from DLL

//

//The function itself will be defined as follows:

/* func.c */

extern char *_pgmptr;

char *_export _loadds DLLpgmptr(void);

char *_export _loadds DLLpgmptr(void)

{

return(_pgmptr);

}

There is also a required .DEF file that may be defined as follows:

; func.def

LIBRARY FUNC INITINSTANCE

PROTMODE

DESCRIPTION '_pgmptr replacement function'

HEAPSIZE 8192

STACKSIZE 2048

DATA MULTIPLE

The compile line to make this into a DLL is as follows:

cl /c /MD /Gs /W4 func.c

The link line is as follows:

link crtdll func.obj, func.dll cexample os2, func.def;

implib func.lib func.dll

Move the resulting DLL to your LIBPATH, call DLLpgmptr() wherever you

would normally use _pgmptr, and link the library that results from

running IMPLIB into the final .EXE.

Additional reference words: 6.00 6.00a 6.00ax