walls@killer.Dallas.TX.US (Monty Walls) (05/01/89)
-------------------------------------------------------------------------- I recently finished recovering from trashing my libc sources (bad disk recovery). In the process of recovering I had to reconstruct some of my routines. So here are my versions of mktemp.c, tmpnam.c, tempnam.c, and a patch to cytpe.* for toupper & tolower as macros without side affects. -Monty Walls --------------------------CUT HERE---------------------------------------- echo x - manifest sed '/^X/s///' > manifest << '/' X-rw-r--r-- 1 root 1561 Apr 30 13:24 ctype.c.cdif X-rw-r--r-- 1 root 1635 Apr 30 13:27 ctype.h.cdif X-rw-r--r-- 1 root 480 Apr 30 14:06 mktemp.3 X-rw-r--r-- 1 bin 753 Apr 30 13:59 mktemp.c X-rw-r--r-- 1 root 323 Apr 30 13:28 stdio.h.cdif X-rw-r--r-- 1 root 841 Apr 30 14:28 tempnam.3 X-rw-r--r-- 1 bin 1760 Apr 30 13:39 tempnam.c X-rw-r--r-- 1 root 677 Apr 30 14:27 tmpnam.3 X-rw-r--r-- 1 bin 891 Apr 30 13:08 tmpnam.c / echo x - mktemp.c sed '/^X/s///' > mktemp.c << '/' X/* mktemp - make a name for a temporary file */ X/* fixed for conformance to v7 - (mrw) */ X/* note - we could have problems if key > 26 */ X Xextern int getpid(); X Xchar *mktemp(template) Xchar *template; X{ X int pid; X char *p; X static int key; X static int lastpid = 0; X X pid = getpid(); /* get process id as semi-unique number */ X if (pid != lastpid) { /* restart sequence on new pid */ X key = 0; X lastpid = pid; X } X X p = template; X while (*p++) ; /* find end of string */ X p--; /* backup to last character */ X X /* Replace XXXXXX at end of template with pid + unique Letter. */ X if (*--p == 'X') X *p = 'a' + key++; /* lower case */ X X while (*--p == 'X') { X *p = '0' + (int)(pid % 10); X pid = pid/10; X } X return(template); X} / echo x - tempnam.c sed '/^X/s///' > tempnam.c << '/' X/* author: Monty Walls X * written: 4/17/89 X * Copyright: Copyright (c) 1989 by Monty Walls. X * Not derived from licensed software. X * X * Permission to copy and/or distribute granted under the X * following conditions: X * X * 1). This notice must remain intact. X * 2). The author is not responsible for the consequences of use X * this software, no matter how awful, even if they X * arise from defects in it. X * 3). Altered version must not be represented as being the X * original software. X */ X#include <stdio.h> X#include <unistd.h> X X#define MAXPREFIX 5 X#define TMPNAME "tmp" X#ifndef P_tmpdir X#define P_tmpdir "/tmp" X#define L_tmpnam 14 X#endif X Xextern char *mktemp(); Xextern char *strcat(); Xextern char *strcpy(); Xextern char *getenv(); X Xchar * Xtempnam(dir, name) Xchar *dir; Xchar *name; X{ X char *buf, *tmpdir; X X /* X * This is kind of like the chicken & the egg. X * Do we use the users preference or the programmers? X */ X#ifdef USE_ENV_VAR X if ((tmpdir = getenv("TMPDIR")) == (char *)NULL) { X if ((tmpdir = dir) == (char *)NULL) X tmpdir = P_tmpdir; X } X#else X if ((tmpdir = dir) == (char *)NULL) { X if ((tmpdir = getenv("TMPDIR")) == (char *)NULL) X tmpdir = P_tmpdir; X } X#endif X /* now lets check and see if we can work there */ X if (access(tmpdir, R_OK+W_OK+X_OK) < 0) X return ((char *)NULL); X X if (name == (char *)NULL) X name = TMPNAME; X else if (strlen(name) > MAXPREFIX) X name[5] = '\0'; /* this is according to SYS5 */ X X /* the magic value 2 is for '\0' & '/' */ X if ((buf = (char *)malloc(L_tmpnam + strlen(tmpdir) + 2)) == (char *)NULL) X return ((char *)NULL); X X strcpy(buf, tmpdir); X strcat(buf, "/"); X strcat(buf, name); X strcat(buf, ".XXXXXX"); X X /* pass our completed pattern to mktemp */ X return (mktemp(buf)); X} / echo x - tmpnam.c sed '/^X/s///' > tmpnam.c << '/' X/* author: Monty Walls X * written: 4/17/89 X * Copyright: Copyright (c) 1989 by Monty Walls. X * Not derived from licensed software. X * X * Permission to copy and/or distribute granted under the X * following conditions: X * X * 1). This notice must remain intact. X * 2). The author is not responsible for the consequences of use X * this software, no matter how awful, even if they X * arise from defects in it. X * 3). Altered version must not be represented as being the X * original software. X */ X#include <stdio.h> X X#ifndef P_tmpdir X#define P_tmpdir "/tmp" X#define L_tmpnam 14 X#endif X Xextern char *mktemp(/*template*/); Xextern char *strcpy(); Xextern char *strcat(); X Xchar * Xtmpnam(buf) Xchar *buf; X{ X static char our_buf[2*L_tmpnam]; X register char *dest; X X dest = (buf == (char *)NULL ? our_buf: buf); X strcpy(dest, P_tmpdir); X strcat(dest, "/tmp.XXXXXX"); X return(mktemp(dest)); X} / echo x - mktemp.3 sed '/^X/s///' > mktemp.3 << '/' XNAME X mktemp(3) - make a unique file name X XSYNOPSIS X char *mktemp( template ) X char *template; X XDESCRIPTION X Make a unique filename given a template in the format of X "name.XXXXXXX", where the 6 X's are replaced by the your pid X and a unique letter. X X XSEE ALSO X getpid(2), tempnam(3), tmpnam(3) X XBUGS X If the number of calls to mktemp(3), tempnam(3), or tmpnam(3) X exceed 26 for a single process-id the last character may be X unprintable. / echo x - tempnam.3 sed '/^X/s///' > tempnam.3 << '/' XNAME X tempnam(3) - make a unique file name X XSYNOPSIS X char *tempnam( dir, basename ) X char *dir, *basename; X XDESCRIPTION X Tempnam(3) returns a pointer to a unique filename given the X 'dir' and 'basename' to use. X If 'dir' is a NULL pointer the environment variable X TMPDIR is used. If TMPDIR is not defined the value of the X preprocessor define in stdio.h for 'P_tmpdir' is used instead. X If 'basename' is a NULL pointer, "tmp" is used for 'basename'. X By convention 'basename' should be nolonger than 5 characters. X The resulting temporary filename will have a format like X "/dir/basen.00213c". X XSEE ALSO X getpid(2), tempnam(3), tmpnam(3) X XBUGS X If the number of calls to mktemp(3), tempnam(3), or tmpnam(3) X exceed 26 for a single process-id the last character may be X unprintable. / echo x - tmpnam.3 sed '/^X/s///' > tmpnam.3 << '/' XNAME X tmpnam(3) - make a unique file name X XSYNOPSIS X char *tmpnam( buffer ) X char *buffer; X XDESCRIPTION X Make a unique temporary filename in "/tmp". 'buffer' is a X storage buffer you provide tmpnam(3) to work in. If a NULL X pointer is passed instead, tmpnam(3) will use an internal X static buffer that will be overwritten on every call to X tmpnam(3). tmpnam(3) returns the address of the name X buffer it used(yours or the static one). X X XSEE ALSO X getpid(2), tempnam(3), tmpnam(3) X XBUGS X If the number of calls to mktemp(3), tempnam(3), or tmpnam(3) X exceed 26 for a single process-id the last character may be X unprintable. / echo x - ctype.c.cdif sed '/^X/s///' > ctype.c.cdif << '/' X*** ctype.c.old X--- ctype.c.new X************** X*** 2,7 X X /* Included ^I..^M in iscntrl(3). Added toupper(3) and */ X /* tolower(3) Terrence W. Holm Oct. 1988 */ X X X #include <ctype.h> X--- 2,9 ----- X X /* Included ^I..^M in iscntrl(3). Added toupper(3) and */ X /* tolower(3) Terrence W. Holm Oct. 1988 */ X+ /* Added _c_ as a work variable for inline toupper(3) */ X+ /* and tolower(3) Monty R. Walls April 1989 */ X X #include <ctype.h> X #include <stdio.h> X************** X*** 3,9 X /* Included ^I..^M in iscntrl(3). Added toupper(3) and */ X /* tolower(3) Terrence W. Holm Oct. 1988 */ X X- X #include <ctype.h> X #include <stdio.h> X X--- 5,10 ----- X /* Added _c_ as a work variable for inline toupper(3) */ X /* and tolower(3) Monty R. Walls April 1989 */ X X #include <ctype.h> X #include <stdio.h> X X************** X*** 7,12 X #include <ctype.h> X #include <stdio.h> X X char _ctype_[] = { X 0, X _C, _C, _C, _C, _C, _C, _C, _C, X--- 8,15 ----- X #include <ctype.h> X #include <stdio.h> X X+ int _c_; /* hidden work variable */ X+ X char _ctype_[] = { X 0, X _C, _C, _C, _C, _C, _C, _C, _C, X************** X*** 26,42 X _L, _L, _L, _L, _L, _L, _L, _L, X _L, _L, _L, _P, _P, _P, _P, _C X }; X- X- X- toupper( c ) X- int c; X- { X- return( islower(c) ? _toupper(c) : c ); X- } X- X- X- tolower( c ) X- int c; X- { X- return( isupper(c) ? _tolower(c) : c ); X- } X--- 29,31 ----- X _L, _L, _L, _L, _L, _L, _L, _L, X _L, _L, _L, _P, _P, _P, _P, _C X }; / echo x - ctype.h.cdif sed '/^X/s///' > ctype.h.cdif << '/' X*** ctype.h.old X--- ctype.h.new X************** X*** 2,7 X X /* Added isgraph(3) and toascii(3); renamed _toupper(3) */ X /* and _tolower(3) Terrence W. Holm Oct. 1988 */ X X extern char _ctype_[]; X X--- 2,9 ----- X X /* Added isgraph(3) and toascii(3); renamed _toupper(3) */ X /* and _tolower(3) Terrence W. Holm Oct. 1988 */ X+ /* Added tolower(3) and toupper(3) that have no /* X+ /* side-affects. Monty R. Walls April 1989 */ X X extern int _c_; X extern char _ctype_[]; X************** X*** 3,8 X /* Added isgraph(3) and toascii(3); renamed _toupper(3) */ X /* and _tolower(3) Terrence W. Holm Oct. 1988 */ X X extern char _ctype_[]; X X #define _U 0001 X--- 5,11 ----- X /* Added tolower(3) and toupper(3) that have no X /* side-affects. Monty R. Walls April 1989 */ X X+ extern int _c_; X extern char _ctype_[]; X X #define _U 0001 X************** X*** 29,32 X X #define _toupper(c) ((c) - 'a' + 'A') X #define _tolower(c) ((c) - 'A' + 'a') X #define toascii(c) ((c) & 0177) X--- 32,38 ----- X X #define _toupper(c) ((c) - 'a' + 'A') X #define _tolower(c) ((c) - 'A' + 'a') X+ #define toupper(c) (islower((_c_ = (c))) ? _toupper(_c_) : _c_) X+ #define tolower(c) (isupper((_c_ = (c))) ? _tolower(_c_) : _c_) X #define toascii(c) ((c) & 0177) X X************** X*** 30,32 X #define _toupper(c) ((c) - 'a' + 'A') X #define _tolower(c) ((c) - 'A' + 'a') X #define toascii(c) ((c) & 0177) X--- 35,38 ----- X #define toupper(c) (islower((_c_ = (c))) ? _toupper(_c_) : _c_) X #define tolower(c) (isupper((_c_ = (c))) ? _tolower(_c_) : _c_) X #define toascii(c) ((c) & 0177) X+ / echo x - stdio.h.cdif sed '/^X/s///' > stdio.h.cdif << '/' X*** /usr/include/stdio.h X--- stdio.h X************** X*** 16,21 X #define PERPRINTF 64 X #define STRINGS 128 X X #ifndef FILE X X extern struct _io_buf { X--- 16,24 ----- X #define PERPRINTF 64 X #define STRINGS 128 X X+ #define P_tmpdir "/tmp" X+ #define L_tmpnam 14 X+ X #ifndef FILE X X extern struct _io_buf { / --------------------------CUT HERE---------------------------------------- Work: Home: MIS Division, Tech. Support 2224 Houston Apt #8 Oklahoma Tax Commission Norman, OK, 73701 2501 N. Lincoln USA OKC, OK, 73194 Phone - 405-364-5123 USA uucp - killer!walls Phone - 405-521-4300