BSD 4_4 release
[unix-history] / usr / src / lib / libc / stdio / mktemp.c
index eadd55f..6cedd6a 100644 (file)
 /*
 /*
- * Copyright (c) 1987 Regents of the University of California.
- * All rights reserved.
+ * Copyright (c) 1987, 1993
+ *     The Regents of the University of California.  All rights reserved.
  *
  *
- * Redistribution and use in source and binary forms are permitted
- * provided that the above copyright notice and this paragraph are
- * duplicated in all such forms and that any documentation,
- * advertising materials, and other materials related to such
- * distribution and use acknowledge that the software was developed
- * by the University of California, Berkeley.  The name of the
- * University may not be used to endorse or promote products derived
- * from this software without specific prior written permission.
- * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
- * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
- * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *     This product includes software developed by the University of
+ *     California, Berkeley and its contributors.
+ * 4. Neither the name of the University nor the names of its contributors
+ *    may be used to endorse or promote products derived from this software
+ *    without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
+ * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
+ * ARE DISCLAIMED.  IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE
+ * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
+ * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
+ * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
+ * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
+ * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
+ * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
+ * SUCH DAMAGE.
  */
 
 #if defined(LIBC_SCCS) && !defined(lint)
  */
 
 #if defined(LIBC_SCCS) && !defined(lint)
-static char sccsid[] = "@(#)mktemp.c   5.7 (Berkeley) %G%";
+static char sccsid[] = "@(#)mktemp.c   8.1 (Berkeley) 6/4/93";
 #endif /* LIBC_SCCS and not lint */
 
 #include <sys/types.h>
 #endif /* LIBC_SCCS and not lint */
 
 #include <sys/types.h>
-#include <sys/file.h>
 #include <sys/stat.h>
 #include <sys/stat.h>
+#include <fcntl.h>
 #include <errno.h>
 #include <stdio.h>
 #include <ctype.h>
 
 #include <errno.h>
 #include <stdio.h>
 #include <ctype.h>
 
-#define        YES     1
-#define        NO      0
+static int _gettemp();
 
 
-mkstemp(as)
-       char    *as;
+mkstemp(path)
+       char *path;
 {
 {
-       int     fd;
+       int fd;
 
 
-       return (_gettemp(as, &fd) ? fd : -1);
+       return (_gettemp(path, &fd) ? fd : -1);
 }
 
 char *
 }
 
 char *
-mktemp(as)
-       char    *as;
+mktemp(path)
+       char *path;
 {
 {
-       return(_gettemp(as, (int *)NULL) ? as : (char *)NULL);
+       return(_gettemp(path, (int *)NULL) ? path : (char *)NULL);
 }
 
 static
 }
 
 static
-_gettemp(as, doopen)
-       char    *as;
-       register int    *doopen;
+_gettemp(path, doopen)
+       char *path;
+       register int *doopen;
 {
 {
-       extern int      errno;
-       register char   *start, *trv;
-       struct stat     sbuf;
-       u_int   pid;
+       extern int errno;
+       register char *start, *trv;
+       struct stat sbuf;
+       u_int pid;
 
        pid = getpid();
 
        pid = getpid();
-
-       /* extra X's get set to 0's */
-       for (trv = as; *trv; ++trv);
+       for (trv = path; *trv; ++trv);          /* extra X's get set to 0's */
        while (*--trv == 'X') {
                *trv = (pid % 10) + '0';
                pid /= 10;
        }
 
        /*
        while (*--trv == 'X') {
                *trv = (pid % 10) + '0';
                pid /= 10;
        }
 
        /*
-        * check for write permission on target directory; if you have
-        * six X's and you can't write the directory, this will run for
-        * a *very* long time.
+        * check the target directory; if you have six X's and it
+        * doesn't exist this runs for a *very* long time.
         */
         */
-       for (start = ++trv; trv > as && *trv != '/'; --trv);
-       if (*trv == '/') {
-               *trv = '\0';
-               if (stat(as, &sbuf) || !(sbuf.st_mode & S_IFDIR))
-                       return(NO);
-               *trv = '/';
+       for (start = trv + 1;; --trv) {
+               if (trv <= path)
+                       break;
+               if (*trv == '/') {
+                       *trv = '\0';
+                       if (stat(path, &sbuf))
+                               return(0);
+                       if (!S_ISDIR(sbuf.st_mode)) {
+                               errno = ENOTDIR;
+                               return(0);
+                       }
+                       *trv = '/';
+                       break;
+               }
        }
        }
-       else if (stat(".", &sbuf) == -1)
-               return(NO);
 
        for (;;) {
                if (doopen) {
 
        for (;;) {
                if (doopen) {
-                   if ((*doopen = open(as, O_CREAT|O_EXCL|O_RDWR, 0600)) >= 0)
-                       return(YES);
-                   if (errno != EEXIST)
-                       return(NO);
+                       if ((*doopen =
+                           open(path, O_CREAT|O_EXCL|O_RDWR, 0600)) >= 0)
+                               return(1);
+                       if (errno != EEXIST)
+                               return(0);
                }
                }
-               else if (stat(as, &sbuf))
-                       return(errno == ENOENT ? YES : NO);
+               else if (stat(path, &sbuf))
+                       return(errno == ENOENT ? 1 : 0);
 
                /* tricky little algorithm for backward compatibility */
                for (trv = start;;) {
                        if (!*trv)
 
                /* tricky little algorithm for backward compatibility */
                for (trv = start;;) {
                        if (!*trv)
-                               return(NO);
+                               return(0);
                        if (*trv == 'z')
                                *trv++ = 'a';
                        else {
                        if (*trv == 'z')
                                *trv++ = 'a';
                        else {