xref: /plan9/sys/src/ape/cmd/pax/port.c (revision 9a747e4fd48b9f4522c70c07e8f882a15030f964)
1 /* $Source: /u/mark/src/pax/RCS/port.c,v $
2  *
3  * $Revision: 1.2 $
4  *
5  * port.c - These are routines not available in all environments.
6  *
7  * DESCRIPTION
8  *
9  *	The routines contained in this file are provided for portability to
10  *	other versions of UNIX or other operating systems (e.g. MSDOS).
11  *	Not all systems have the same functions or the same semantics,
12  *	these routines attempt to bridge the gap as much as possible.
13  *
14  * AUTHOR
15  *
16  *	Mark H. Colburn, NAPS International (mark@jhereg.mn.org)
17  *	John Gilmore (gnu@hoptoad)
18  *
19  * Sponsored by The USENIX Association for public distribution.
20  *
21  * Copyright (c) 1989 Mark H. Colburn.
22  * All rights reserved.
23  *
24  * Redistribution and use in source and binary forms are permitted
25  * provided that the above copyright notice is duplicated in all such
26  * forms and that any documentation, advertising materials, and other
27  * materials related to such distribution and use acknowledge that the
28  * software was developed * by Mark H. Colburn and sponsored by The
29  * USENIX Association.
30  *
31  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
32  * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
33  * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
34  *
35  * $Log:	port.c,v $
36  * Revision 1.2  89/02/12  10:05:35  mark
37  * 1.2 release fixes
38  *
39  * Revision 1.1  88/12/23  18:02:29  mark
40  * Initial revision
41  *
42  */
43 
44 #ifndef lint
45 static char *ident = "$Id: port.c,v 1.2 89/02/12 10:05:35 mark Exp $";
46 static char *copyright = "Copyright (c) 1989 Mark H. Colburn.\nAll rights reserved.\n";
47 #endif /* ! lint */
48 
49 
50 /* Headers */
51 
52 #include "pax.h"
53 
54 
55 /*
56  * Some computers are not so crass as to align themselves into the BSD or USG
57  * camps.  If a system supplies all of the routines we fake here, add it to
58  * the list in the #if !defined()'s below and it'll all be skipped.
59  */
60 
61 #if !defined(mc300) && !defined(mc500) && !defined(mc700) && !defined(BSD) && !defined(_POSIX_SOURCE)
62 
63 /* mkdir - make a directory
64  *
65  * DESCRIPTION
66  *
67  * 	Mkdir will make a directory of the name "dpath" with a mode of
68  *	"dmode".  This is consistent with the BSD mkdir() function and the
69  *	P1003.1 definitions of MKDIR.
70  *
71  * PARAMETERS
72  *
73  *	dpath		- name of directory to create
74  *	dmode		- mode of the directory
75  *
76  * RETURNS
77  *
78  *	Returns 0 if the directory was successfully created, otherwise a
79  *	non-zero return value will be passed back to the calling function
80  *	and the value of errno should reflect the error.
81  */
82 
83 #ifdef __STDC__
84 
mkdir(char * dpath,int dmode)85 int mkdir(char *dpath, int dmode)
86 
87 #else
88 
89 int mkdir(dpath, dmode)
90 char           *dpath;
91 int             dmode;
92 
93 #endif
94 {
95     int             cpid, status;
96     Stat            statbuf;
97     extern int      errno;
98 
99     if (STAT(dpath, &statbuf) == 0) {
100 	errno = EEXIST;		/* Stat worked, so it already exists */
101 	return (-1);
102     }
103     /* If stat fails for a reason other than non-existence, return error */
104     if (errno != ENOENT)
105 	return (-1);
106 
107     switch (cpid = fork()) {
108 
109     case -1:			/* Error in fork() */
110 	return (-1);		/* Errno is set already */
111 
112     case 0:			/* Child process */
113 
114 	status = umask(0);	/* Get current umask */
115 	status = umask(status | (0777 & ~dmode));	/* Set for mkdir */
116 	execl("/bin/mkdir", "mkdir", dpath, (char *) 0);
117 	_exit(-1);		/* Can't exec /bin/mkdir */
118 
119     default:			/* Parent process */
120 	while (cpid != wait(&status)) {
121 	    /* Wait for child to finish */
122 	}
123     }
124 
125     if (TERM_SIGNAL(status) != 0 || TERM_VALUE(status) != 0) {
126 	errno = EIO;		/* We don't know why, but */
127 	return (-1);		/* /bin/mkdir failed */
128     }
129     return (0);
130 }
131 
132 
133 /* rmdir - remove a directory
134  *
135  * DESCRIPTION
136  *
137  *	Rmdir will remove the directory specified by "dpath".  It is
138  *	consistent with the BSD and POSIX rmdir functions.
139  *
140  * PARAMETERS
141  *
142  *	dpath		- name of directory to remove
143  *
144  * RETURNS
145  *
146  *	Returns 0 if the directory was successfully deleted, otherwise a
147  *	non-zero return value will be passed back to the calling function
148  *	and the value of errno should reflect the error.
149  */
150 
151 #ifdef __STDC__
152 
rmdir(char * dpath)153 int rmdir(char *dpath)
154 
155 #else
156 
157 int rmdir(dpath)
158 char           *dpath;
159 
160 #endif
161 {
162     int             cpid, status;
163     Stat            statbuf;
164     extern int      errno;
165 
166     /* check to see if it exists */
167     if (STAT(dpath, &statbuf) == -1) {
168 	return (-1);
169     }
170     switch (cpid = fork()) {
171 
172     case -1:			/* Error in fork() */
173 	return (-1);		/* Errno is set already */
174 
175     case 0:			/* Child process */
176 	execl("/bin/rmdir", "rmdir", dpath, (char *) 0);
177 	_exit(-1);		/* Can't exec /bin/rmdir */
178 
179     default:			/* Parent process */
180 	while (cpid != wait(&status)) {
181 	    /* Wait for child to finish */
182 	}
183     }
184 
185     if (TERM_SIGNAL(status) != 0 || TERM_VALUE(status) != 0) {
186 	errno = EIO;		/* We don't know why, but */
187 	return (-1);		/* /bin/rmdir failed */
188     }
189     return (0);
190 }
191 
192 #endif /* MASSCOMP, BSD */
193