1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/security/nss/lib/dbm/src/mktemp.c Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,149 @@ 1.4 +/* 1.5 + * Copyright (c) 1987, 1993 1.6 + * The Regents of the University of California. All rights reserved. 1.7 + * 1.8 + * Redistribution and use in source and binary forms, with or without 1.9 + * modification, are permitted provided that the following conditions 1.10 + * are met: 1.11 + * 1. Redistributions of source code must retain the above copyright 1.12 + * notice, this list of conditions and the following disclaimer. 1.13 + * 2. Redistributions in binary form must reproduce the above copyright 1.14 + * notice, this list of conditions and the following disclaimer in the 1.15 + * documentation and/or other materials provided with the distribution. 1.16 + * 3. ***REMOVED*** - see 1.17 + * ftp://ftp.cs.berkeley.edu/pub/4bsd/README.Impt.License.Change 1.18 + * 4. Neither the name of the University nor the names of its contributors 1.19 + * may be used to endorse or promote products derived from this software 1.20 + * without specific prior written permission. 1.21 + * 1.22 + * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 1.23 + * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1.24 + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1.25 + * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 1.26 + * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 1.27 + * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 1.28 + * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 1.29 + * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 1.30 + * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 1.31 + * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 1.32 + * SUCH DAMAGE. 1.33 + */ 1.34 + 1.35 +#if defined(LIBC_SCCS) && !defined(lint) 1.36 +static char sccsid[] = "@(#)mktemp.c 8.1 (Berkeley) 6/4/93"; 1.37 +#endif /* LIBC_SCCS and not lint */ 1.38 + 1.39 +#ifdef macintosh 1.40 +#include <unix.h> 1.41 +#else 1.42 +#include <sys/types.h> 1.43 +#include <sys/stat.h> 1.44 +#endif 1.45 +#include <fcntl.h> 1.46 +#include <errno.h> 1.47 +#include <stdio.h> 1.48 +#include <ctype.h> 1.49 +#include "mcom_db.h" 1.50 + 1.51 +#ifndef _WINDOWS 1.52 +#include <unistd.h> 1.53 +#endif 1.54 + 1.55 +#ifdef _WINDOWS 1.56 +#include <process.h> 1.57 +#include "winfile.h" 1.58 +#endif 1.59 + 1.60 +static int _gettemp(char *path, register int *doopen, int extraFlags); 1.61 + 1.62 +int 1.63 +mkstemp(char *path) 1.64 +{ 1.65 +#ifdef XP_OS2 1.66 + FILE *temp = tmpfile(); 1.67 + 1.68 + return (temp ? fileno(temp) : -1); 1.69 +#else 1.70 + int fd; 1.71 + 1.72 + return (_gettemp(path, &fd, 0) ? fd : -1); 1.73 +#endif 1.74 +} 1.75 + 1.76 +int 1.77 +mkstempflags(char *path, int extraFlags) 1.78 +{ 1.79 + int fd; 1.80 + 1.81 + return (_gettemp(path, &fd, extraFlags) ? fd : -1); 1.82 +} 1.83 + 1.84 +/* NB: This routine modifies its input string, and does not always restore it. 1.85 +** returns 1 on success, 0 on failure. 1.86 +*/ 1.87 +static int 1.88 +_gettemp(char *path, register int *doopen, int extraFlags) 1.89 +{ 1.90 + register char *start, *trv; 1.91 + struct stat sbuf; 1.92 + unsigned int pid; 1.93 + 1.94 + pid = getpid(); 1.95 + for (trv = path; *trv; ++trv); /* extra X's get set to 0's */ 1.96 + while (*--trv == 'X') { 1.97 + *trv = (pid % 10) + '0'; 1.98 + pid /= 10; 1.99 + } 1.100 + 1.101 + /* 1.102 + * check the target directory; if you have six X's and it 1.103 + * doesn't exist this runs for a *very* long time. 1.104 + */ 1.105 + for (start = trv + 1;; --trv) { 1.106 + char saved; 1.107 + if (trv <= path) 1.108 + break; 1.109 + saved = *trv; 1.110 + if (saved == '/' || saved == '\\') { 1.111 + int rv; 1.112 + *trv = '\0'; 1.113 + rv = stat(path, &sbuf); 1.114 + *trv = saved; 1.115 + if (rv) 1.116 + return(0); 1.117 + if (!S_ISDIR(sbuf.st_mode)) { 1.118 + errno = ENOTDIR; 1.119 + return(0); 1.120 + } 1.121 + break; 1.122 + } 1.123 + } 1.124 + 1.125 + for (;;) { 1.126 + if (doopen) { 1.127 + if ((*doopen = 1.128 + open(path, O_CREAT|O_EXCL|O_RDWR|extraFlags, 0600)) >= 0) 1.129 + return(1); 1.130 + if (errno != EEXIST) 1.131 + return(0); 1.132 + } 1.133 + else if (stat(path, &sbuf)) 1.134 + return(errno == ENOENT ? 1 : 0); 1.135 + 1.136 + /* tricky little algorithm for backward compatibility */ 1.137 + for (trv = start;;) { 1.138 + if (!*trv) 1.139 + return(0); 1.140 + if (*trv == 'z') 1.141 + *trv++ = 'a'; 1.142 + else { 1.143 + if (isdigit(*trv)) 1.144 + *trv = 'a'; 1.145 + else 1.146 + ++*trv; 1.147 + break; 1.148 + } 1.149 + } 1.150 + } 1.151 + /*NOTREACHED*/ 1.152 +}