/* New module MKNAME.C  FOR BORLAND C++ VERSION'S 2.0, 3.0 
     and Turboc 2.0

   for WG7J 911229 version 1.0 and up

BCC C++ 3.0 mods and addition of tmpfile() by WA7TAS

CAVEAT:   This module does not include the tempnam() module.  Therefore
	  the tempname() function call probably won't work the way
	  you think it should.  NOS doesn't use tempnam(), so I
	  consider this to be a moot point.

NOTE:  This module wouldn't be necessary if Borland BCC C++ 3.0 actually
       used the TMP environment variable as stated in the Borland manual
       set, but it doesn't.  The manual is in error for tmpfile() and
       tmpnam().  If the next version corrects the library code to conform
       to the manual then this module can be removed. If the manual set
       is corrected then this code will still be necessary.  

--- Ron Henderson WA7TAS
    crh@cv.hp.com
    March 31, 1992

   This module MUST be compiled in such a way that it is forced into
   the _TEXT segment.  This can be accomplished by using the "-zC_TEXT"
   compiler switch with the Borland C++ 3.0 compiler.  I have put this
   switch in a special compilation rule in MAKEFILE for reasons explained
   below.  It is possible to make all of PC.C go into the _TEXT segment,
   but that might put too much in there and cause trouble for the compiler.
   The best way is to put in only what we need, and that is why this must
   be a new and separate module.

   To compile this module right, there must be a special compilation rule
   included in MAKEFILE:

!if (($(CC) == bcc) || ($(CC) == BCC) || ($(CC) == bccx) || ($(CC) == BCCX)) 
mkname.obj: mkname.c
	$(CC) -c $(MODEL) $(CFLAGS) -zC_TEXT $*.c
!endif

   The MAKEFILE must be modified to add MKNAME.OBJ to the list of PCOBJS.
   The file PC.TL must be modified to include MKNAME.OBJ in the list of
   files that are bound into PC.LIB by the librarian.

   The tmpnam() and __MKNAME() functions in the run-time library are in
   the same object module, so both have to replaced together.  Those below
   must be used instead of the ones in PC.C; therefore, both tmpnam() and
   __MKNAME() in PC.C should be removed, as should the declaration of the
   variable _tmpnum.  Since these functions are never called from within
   NOS, this module will be preprocessed to have no compilable code in it
   if the compiler is not the right one.

   The pascal calling convention specifies that symbols are converted to
   upper case and an underscore character is not automatically prepended.
   It is intended that the __MKNAME() DIRECTLY replace the function of the
   same name in the run-time library.  This __MKNAME() function is called
   from run-time library modules tmpnam(), which is being replaced, and
   from fclose(), which is not.  The whole point of this awful kludge is
   to avoid rewriting fclose(), which would be a lot worse than this.

   -- Mike Bilow, 9 July 1991
      N1BEE @ KA1RCI.RI.USA.NA  (AX.25)
      mikebw@idsvax.ids.com  (Internet)

*/

#ifdef __TURBOC__  /* defined in all turboc versions thru BCC C++ 3.0 */

#include <stdio.h>		/* for sprintf() */
#include <stdlib.h>
#include <string.h>		/* for strlen() */
#include "global.h"

char *getnenv (char *name);	/* In pc.c */
char *tmpnam(char *);
unsigned int _tmpnum = 0;

#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
  char far * near pascal __MKNAME(char far *, char * prefix, unsigned int);
#else  /* it's not BCC C++ 3.0, use older form */
#ifdef __BORLANDC__
  char far * near pascal __MKNAME __ARGS((char far *tmpname,unsigned int tmpnum));
#else
  char *pascal __MKNAME __ARGS((char *tmpname,unsigned int tmpnum));
#endif
#endif /* __BORLANDC__ == 0x0400 */

#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
  char far * near pascal 
  __MKNAME(char far * tmpname,char * prefix, unsigned int tmpnum)
#else
#ifdef __BORLANDC__
  char far * near pascal __MKNAME (tmpname,tmpnum)  /* Turbo C++ acc. n1bee */
  char far *tmpname;
#else
  char *pascal __MKNAME (tmpname,tmpnum)		  /* The "standard compiler" */
  char *tmpname;
#endif
  unsigned int tmpnum;
#endif  /* __BORLANDC__ == 0x0400 */
{

	char *tmpdir,*p;
	static char staticname[80];

#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
	char pre[4];


	if (prefix == NULL) 
		strcpy(pre,"TMP");
	else {
		strncpy(pre,prefix,3);
		pre[3]=0;
	}
#endif
	if (tmpname == NULL)
		tmpname = staticname;

	p = tmpdir = getnenv("TMP");		/* get tempdir name */
	if (p[0] != '\0')
		p += strlen(p) - 1;		/* point to last character */

/* Note that the default is to use root if TMP= is not specified */
#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
	sprintf(tmpname,"%s%s%s%u.$$$",tmpdir,
			((*p != '/' && *p != '\\')? "\\":""),pre,tmpnum);
#else
	sprintf(tmpname,"%s%sTMP%u.$$$",tmpdir,
			((*p != '/' && *p != '\\')? "\\":""),tmpnum);
#endif
	return tmpname;
} /* __MKNAME */

char *tmpnam (char *name)		/* Converted to modern C style */
{
	do
	{
		if (_tmpnum == 0xffff)
			 _tmpnum = 2;
		else
			 ++_tmpnum;

#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
		name = __MKNAME(name,"TMP",_tmpnum);
#else
		name = __MKNAME(name,_tmpnum);
#endif
	}
	while (access(name,0) != -1);

	return name;
} /* tmpnam */

#if __BORLANDC__ == 0x0400  /* Borland C++ Version 3.0 */
FILE * tmpfile(void)
{
    char    s[80];
    FILE    *tmpf;

    tmpnam(s); /* Get a unique file name */

    if ((tmpf = fopen(s, "w+b")) != NULL)
            tmpf->istemp = _tmpnum;
    return (tmpf);
} /* tmpfil */
#endif  /* __BORLANDC__ == 0x0400 */
#endif  /* ifdef __TURBOC__ */
