blob: 8631e649a75bd173a3c252fa574d46f459cab082 [file] [log] [blame]
Guido van Rossumf70e43a1991-02-19 12:39:46 +00001/***********************************************************
Guido van Rossum524b5881995-01-04 19:10:35 +00002Copyright 1991-1995 by Stichting Mathematisch Centrum, Amsterdam,
3The Netherlands.
Guido van Rossumf70e43a1991-02-19 12:39:46 +00004
5 All Rights Reserved
6
7Permission to use, copy, modify, and distribute this software and its
8documentation for any purpose and without fee is hereby granted,
9provided that the above copyright notice appear in all copies and that
10both that copyright notice and this permission notice appear in
11supporting documentation, and that the names of Stichting Mathematisch
12Centrum or CWI not be used in advertising or publicity pertaining to
13distribution of the software without specific, written prior permission.
14
15STICHTING MATHEMATISCH CENTRUM DISCLAIMS ALL WARRANTIES WITH REGARD TO
16THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND
17FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH CENTRUM BE LIABLE
18FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
19WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
20ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
21OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
22
23******************************************************************/
24
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000025/* POSIX module implementation */
26
Guido van Rossum3f5da241990-12-20 15:06:42 +000027#include "allobjects.h"
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000028#include "modsupport.h"
Guido van Rossumff4949e1992-08-05 19:58:53 +000029#include "ceval.h"
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000030
Guido van Rossumb6775db1994-08-01 11:34:53 +000031#include <string.h>
32#include <errno.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +000033#include <sys/types.h>
34#include <sys/stat.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +000035
36#include "mytime.h" /* For clock_t on some systems */
37
38#ifdef HAVE_FCNTL_H
39#include <fcntl.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000040#endif /* HAVE_FCNTL_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000041
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000042#ifndef NT
Guido van Rossumb6775db1994-08-01 11:34:53 +000043#ifdef HAVE_UNISTD_H
Guido van Rossum0b0db8e1993-01-21 16:07:51 +000044#include <unistd.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +000045#else /* !HAVE_UNISTD_H */
Guido van Rossuma2b7f401993-01-04 09:09:59 +000046extern int mkdir PROTO((const char *, mode_t));
47extern int chdir PROTO((const char *));
Guido van Rossume22e6441993-07-09 10:51:31 +000048extern int rmdir PROTO((const char *));
49extern int chmod PROTO((const char *, mode_t));
Guido van Rossumb6775db1994-08-01 11:34:53 +000050extern int chown PROTO((const char *, uid_t, gid_t));
51extern char *getcwd PROTO((char *, int));
Guido van Rossume22e6441993-07-09 10:51:31 +000052extern char *strerror PROTO((int));
Guido van Rossuma2b7f401993-01-04 09:09:59 +000053extern int link PROTO((const char *, const char *));
54extern int rename PROTO((const char *, const char *));
Guido van Rossuma2b7f401993-01-04 09:09:59 +000055extern int stat PROTO((const char *, struct stat *));
56extern int unlink PROTO((const char *));
57extern int pclose PROTO((FILE *));
Guido van Rossumb6775db1994-08-01 11:34:53 +000058#ifdef HAVE_SYMLINK
Guido van Rossuma2b7f401993-01-04 09:09:59 +000059extern int symlink PROTO((const char *, const char *));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000060#endif /_ HAVE_SYMLINK */
Guido van Rossumb6775db1994-08-01 11:34:53 +000061#ifdef HAVE_LSTAT
62extern int lstat PROTO((const char *, struct stat *));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000063#endif /* HAVE_LSTAT */
Guido van Rossumb6775db1994-08-01 11:34:53 +000064#endif /* !HAVE_UNISTD_H */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000065#endif /* !NT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000066
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000067#ifndef NT
Guido van Rossumb6775db1994-08-01 11:34:53 +000068/* XXX These are for SunOS4.1.3 but shouldn't hurt elsewhere */
69extern int rename();
70extern int pclose();
71extern int lstat();
72extern int symlink();
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000073#endif /* !NT */
Guido van Rossumb6775db1994-08-01 11:34:53 +000074
75#ifdef HAVE_UTIME_H
76#include <utime.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000077#endif /* HAVE_UTIME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000078
Guido van Rossum14ed0b21994-09-29 09:50:09 +000079#ifdef HAVE_SYS_UTIME_H
80#include <sys/utime.h>
81#define HAVE_UTIME_H /* pretend we do for the rest of this file */
82#endif /* HAVE_SYS_UTIME_H */
83
Guido van Rossumb6775db1994-08-01 11:34:53 +000084#ifdef HAVE_SYS_TIMES_H
85#include <sys/times.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000086#endif /* HAVE_SYS_TIMES_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000087
88#ifdef HAVE_SYS_PARAM_H
89#include <sys/param.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000090#endif /* HAVE_SYS_PARAM_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000091
92#ifdef HAVE_SYS_UTSNAME_H
93#include <sys/utsname.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000094#endif /* HAVE_SYS_UTSNAME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000095
96#ifndef MAXPATHLEN
97#define MAXPATHLEN 1024
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000098#endif /* MAXPATHLEN */
Guido van Rossumb6775db1994-08-01 11:34:53 +000099
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000100#ifdef HAVE_DIRENT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000101#include <dirent.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000102#define NAMLEN(dirent) strlen((dirent)->d_name)
103#else
Guido van Rossumb6775db1994-08-01 11:34:53 +0000104#define dirent direct
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000105#define NAMLEN(dirent) (dirent)->d_namlen
106#ifdef HAVE_SYS_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000107#include <sys/ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000108#endif
109#ifdef HAVE_SYS_DIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000110#include <sys/dir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000111#endif
112#ifdef HAVE_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000113#include <ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000114#endif
115#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +0000116
117#ifdef NT
118#include <direct.h>
119#include <io.h>
120#include <process.h>
121#include <windows.h>
122#define popen _popen
Guido van Rossum794d8131994-08-23 13:48:48 +0000123#define pclose _pclose
Guido van Rossumb6775db1994-08-01 11:34:53 +0000124#endif /* NT */
125
126#ifdef OS2
127#include <io.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000128#endif /* OS2 */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000129
130/* Return a dictionary corresponding to the POSIX environment table */
131
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000132#ifndef NT
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000133extern char **environ;
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000134#endif /* !NT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000135
136static object *
137convertenviron()
138{
139 object *d;
140 char **e;
141 d = newdictobject();
142 if (d == NULL)
143 return NULL;
144 if (environ == NULL)
145 return d;
146 /* XXX This part ignores errors */
147 for (e = environ; *e != NULL; e++) {
148 object *v;
149 char *p = strchr(*e, '=');
150 if (p == NULL)
151 continue;
152 v = newstringobject(p+1);
153 if (v == NULL)
154 continue;
155 *p = '\0';
156 (void) dictinsert(d, *e, v);
157 *p = '=';
158 DECREF(v);
159 }
160 return d;
161}
162
163
164static object *PosixError; /* Exception posix.error */
165
166/* Set a POSIX-specific error from errno, and return NULL */
167
Guido van Rossum687dd131993-05-17 08:34:16 +0000168static object * posix_error() { return err_errno(PosixError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000169}
170
171
172/* POSIX generic methods */
173
174static object *
175posix_1str(args, func)
176 object *args;
177 int (*func) FPROTO((const char *));
178{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000179 char *path1;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000180 int res;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000181 if (!getargs(args, "s", &path1))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000182 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000183 BGN_SAVE
184 res = (*func)(path1);
185 END_SAVE
186 if (res < 0)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000187 return posix_error();
188 INCREF(None);
189 return None;
190}
191
192static object *
193posix_2str(args, func)
194 object *args;
195 int (*func) FPROTO((const char *, const char *));
196{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000197 char *path1, *path2;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000198 int res;
Guido van Rossum234f9421993-06-17 12:35:49 +0000199 if (!getargs(args, "(ss)", &path1, &path2))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000200 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000201 BGN_SAVE
202 res = (*func)(path1, path2);
203 END_SAVE
204 if (res < 0)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000205 return posix_error();
206 INCREF(None);
207 return None;
208}
209
210static object *
211posix_strint(args, func)
212 object *args;
213 int (*func) FPROTO((const char *, int));
214{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000215 char *path;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000216 int i;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000217 int res;
Guido van Rossum234f9421993-06-17 12:35:49 +0000218 if (!getargs(args, "(si)", &path, &i))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000219 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000220 BGN_SAVE
221 res = (*func)(path, i);
222 END_SAVE
223 if (res < 0)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000224 return posix_error();
225 INCREF(None);
226 return None;
227}
228
229static object *
Guido van Rossumb6775db1994-08-01 11:34:53 +0000230posix_strintint(args, func)
231 object *args;
232 int (*func) FPROTO((const char *, int, int));
233{
234 char *path;
235 int i,i2;
236 int res;
237 if (!getargs(args, "(sii)", &path, &i, &i2))
238 return NULL;
239 BGN_SAVE
240 res = (*func)(path, i, i2);
241 END_SAVE
242 if (res < 0)
243 return posix_error();
244 INCREF(None);
245 return None;
246}
247
248static object *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000249posix_do_stat(self, args, statfunc)
250 object *self;
251 object *args;
252 int (*statfunc) FPROTO((const char *, struct stat *));
253{
254 struct stat st;
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000255 char *path;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000256 int res;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000257 if (!getargs(args, "s", &path))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000258 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000259 BGN_SAVE
260 res = (*statfunc)(path, &st);
261 END_SAVE
262 if (res != 0)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000263 return posix_error();
Guido van Rossum687dd131993-05-17 08:34:16 +0000264 return mkvalue("(llllllllll)",
Guido van Rossume5372401993-03-16 12:15:04 +0000265 (long)st.st_mode,
266 (long)st.st_ino,
267 (long)st.st_dev,
268 (long)st.st_nlink,
269 (long)st.st_uid,
270 (long)st.st_gid,
271 (long)st.st_size,
272 (long)st.st_atime,
273 (long)st.st_mtime,
274 (long)st.st_ctime);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000275}
276
277
278/* POSIX methods */
279
280static object *
281posix_chdir(self, args)
282 object *self;
283 object *args;
284{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000285 return posix_1str(args, chdir);
286}
287
288static object *
289posix_chmod(self, args)
290 object *self;
291 object *args;
292{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000293 return posix_strint(args, chmod);
294}
295
Guido van Rossumb6775db1994-08-01 11:34:53 +0000296#ifdef HAVE_CHOWN
297static object *
298posix_chown(self, args)
299 object *self;
300 object *args;
301{
302 return posix_strintint(args, chown);
303}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000304#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000305
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000306static object *
307posix_getcwd(self, args)
308 object *self;
309 object *args;
310{
311 char buf[1026];
Guido van Rossumff4949e1992-08-05 19:58:53 +0000312 char *res;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000313 if (!getnoarg(args))
314 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000315 BGN_SAVE
316 res = getcwd(buf, sizeof buf);
317 END_SAVE
318 if (res == NULL)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000319 return posix_error();
320 return newstringobject(buf);
321}
322
Guido van Rossumb6775db1994-08-01 11:34:53 +0000323#ifdef HAVE_LINK
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000324static object *
325posix_link(self, args)
326 object *self;
327 object *args;
328{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000329 return posix_2str(args, link);
330}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000331#endif /* HAVE_LINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000332
Guido van Rossumb6775db1994-08-01 11:34:53 +0000333static object *
334posix_listdir(self, args)
335 object *self;
336 object *args;
337{
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000338#ifdef NT
339
Guido van Rossumb6775db1994-08-01 11:34:53 +0000340 char *name;
341 int len;
342 object *d, *v;
343 HANDLE hFindFile;
344 WIN32_FIND_DATA FileData;
345 char namebuf[MAX_PATH+5];
346
347 if (!getargs(args, "s#", &name, &len))
348 return NULL;
349 if (len >= MAX_PATH) {
350 err_setstr(ValueError, "path too long");
351 return NULL;
352 }
353 strcpy(namebuf, name);
354 if (namebuf[len-1] != '/' && namebuf[len-1] != '\\')
355 namebuf[len++] = '/';
356 strcpy(namebuf + len, "*.*");
357
358 if ((d = newlistobject(0)) == NULL)
359 return NULL;
360
361 hFindFile = FindFirstFile(namebuf, &FileData);
362 if (hFindFile == INVALID_HANDLE_VALUE) {
363 errno = GetLastError();
364 return posix_error();
365 }
366 do {
367 v = newstringobject(FileData.cFileName);
368 if (v == NULL) {
369 DECREF(d);
370 d = NULL;
371 break;
372 }
373 if (addlistitem(d, v) != 0) {
374 DECREF(v);
375 DECREF(d);
376 d = NULL;
377 break;
378 }
379 DECREF(v);
380 } while (FindNextFile(hFindFile, &FileData) == TRUE);
381
382 if (FindClose(hFindFile) == FALSE) {
383 errno = GetLastError();
384 return posix_error();
385 }
386
387 return d;
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000388
389#else /* !NT */
390
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000391 char *name;
392 object *d, *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000393 DIR *dirp;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000394 struct dirent *ep;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000395 if (!getargs(args, "s", &name))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000396 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000397 BGN_SAVE
398 if ((dirp = opendir(name)) == NULL) {
399 RET_SAVE
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000400 return posix_error();
Guido van Rossumff4949e1992-08-05 19:58:53 +0000401 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000402 if ((d = newlistobject(0)) == NULL) {
403 closedir(dirp);
Guido van Rossumff4949e1992-08-05 19:58:53 +0000404 RET_SAVE
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000405 return NULL;
406 }
407 while ((ep = readdir(dirp)) != NULL) {
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000408 v = newsizedstringobject(ep->d_name, NAMLEN(ep));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000409 if (v == NULL) {
410 DECREF(d);
411 d = NULL;
412 break;
413 }
414 if (addlistitem(d, v) != 0) {
415 DECREF(v);
416 DECREF(d);
417 d = NULL;
418 break;
419 }
420 DECREF(v);
421 }
422 closedir(dirp);
Guido van Rossumff4949e1992-08-05 19:58:53 +0000423 END_SAVE
Guido van Rossum0ee42cd1991-04-08 21:01:03 +0000424
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000425 return d;
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000426
427#endif /* !NT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000428}
429
430static object *
431posix_mkdir(self, args)
432 object *self;
433 object *args;
434{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000435 return posix_strint(args, mkdir);
436}
437
Guido van Rossumb6775db1994-08-01 11:34:53 +0000438#ifdef HAVE_NICE
Guido van Rossum775f4da1993-01-09 17:18:52 +0000439static object *
440posix_nice(self, args)
441 object *self;
442 object *args;
443{
444 int increment, value;
445
446 if (!getargs(args, "i", &increment))
447 return NULL;
448 value = nice(increment);
449 if (value == -1)
450 return posix_error();
451 return newintobject((long) value);
452}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000453#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000454
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000455static object *
456posix_rename(self, args)
457 object *self;
458 object *args;
459{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000460 return posix_2str(args, rename);
461}
462
463static object *
464posix_rmdir(self, args)
465 object *self;
466 object *args;
467{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000468 return posix_1str(args, rmdir);
469}
470
471static object *
472posix_stat(self, args)
473 object *self;
474 object *args;
475{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000476 return posix_do_stat(self, args, stat);
477}
478
479static object *
480posix_system(self, args)
481 object *self;
482 object *args;
483{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000484 char *command;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000485 long sts;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000486 if (!getargs(args, "s", &command))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000487 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000488 BGN_SAVE
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000489 sts = system(command);
Guido van Rossumff4949e1992-08-05 19:58:53 +0000490 END_SAVE
491 return newintobject(sts);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000492}
493
494static object *
495posix_umask(self, args)
496 object *self;
497 object *args;
498{
499 int i;
500 if (!getintarg(args, &i))
501 return NULL;
502 i = umask(i);
503 if (i < 0)
504 return posix_error();
505 return newintobject((long)i);
506}
507
508static object *
509posix_unlink(self, args)
510 object *self;
511 object *args;
512{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000513 return posix_1str(args, unlink);
514}
515
Guido van Rossumb6775db1994-08-01 11:34:53 +0000516#ifdef HAVE_UNAME
Guido van Rossumc39de5f1992-02-05 11:15:54 +0000517static object *
518posix_uname(self, args)
519 object *self;
520 object *args;
521{
Guido van Rossumc39de5f1992-02-05 11:15:54 +0000522 struct utsname u;
523 object *v;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000524 int res;
Guido van Rossum50e61dc1992-03-27 17:22:31 +0000525 if (!getnoarg(args))
526 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000527 BGN_SAVE
528 res = uname(&u);
529 END_SAVE
530 if (res < 0)
Guido van Rossumc39de5f1992-02-05 11:15:54 +0000531 return posix_error();
Guido van Rossume5372401993-03-16 12:15:04 +0000532 return mkvalue("(sssss)",
533 u.sysname,
534 u.nodename,
535 u.release,
536 u.version,
537 u.machine);
Guido van Rossumc39de5f1992-02-05 11:15:54 +0000538}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000539#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000540
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000541static object *
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000542posix_utime(self, args)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000543 object *self;
544 object *args;
545{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000546 char *path;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000547 int res;
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000548
Guido van Rossumb6775db1994-08-01 11:34:53 +0000549#ifdef HAVE_UTIME_H
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000550 struct utimbuf buf;
551#define ATIME buf.actime
552#define MTIME buf.modtime
553#define UTIME_ARG &buf
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000554#else /* HAVE_UTIME_H */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000555 time_t buf[2];
556#define ATIME buf[0]
557#define MTIME buf[1]
558#define UTIME_ARG buf
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000559#endif /* HAVE_UTIME_H */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000560
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000561 if (!getargs(args, "(s(ll))", &path, &ATIME, &MTIME))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000562 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000563 BGN_SAVE
564 res = utime(path, UTIME_ARG);
565 END_SAVE
566 if (res < 0)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000567 return posix_error();
568 INCREF(None);
569 return None;
Guido van Rossum1ff6cb41991-04-08 20:59:13 +0000570#undef UTIME_ARG
571#undef ATIME
572#undef MTIME
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000573}
574
Guido van Rossum85e3b011991-06-03 12:42:10 +0000575
Guido van Rossum3b066191991-06-04 19:40:25 +0000576/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +0000577
578static object *
579posix__exit(self, args)
580 object *self;
581 object *args;
582{
583 int sts;
584 if (!getintarg(args, &sts))
585 return NULL;
586 _exit(sts);
587 /* NOTREACHED */
588}
589
Guido van Rossum85e3b011991-06-03 12:42:10 +0000590static object *
Guido van Rossum89b33251993-10-22 14:26:06 +0000591posix_execv(self, args)
Guido van Rossum85e3b011991-06-03 12:42:10 +0000592 object *self;
593 object *args;
594{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000595 char *path;
596 object *argv;
Guido van Rossum85e3b011991-06-03 12:42:10 +0000597 char **argvlist;
598 int i, argc;
599 object *(*getitem) PROTO((object *, int));
600
Guido van Rossum89b33251993-10-22 14:26:06 +0000601 /* execv has two arguments: (path, argv), where
Guido van Rossum85e3b011991-06-03 12:42:10 +0000602 argv is a list or tuple of strings. */
603
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000604 if (!getargs(args, "(sO)", &path, &argv))
Guido van Rossum85e3b011991-06-03 12:42:10 +0000605 return NULL;
Guido van Rossum85e3b011991-06-03 12:42:10 +0000606 if (is_listobject(argv)) {
607 argc = getlistsize(argv);
608 getitem = getlistitem;
609 }
610 else if (is_tupleobject(argv)) {
611 argc = gettuplesize(argv);
612 getitem = gettupleitem;
613 }
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000614 else {
615 badarg:
616 err_badarg();
617 return NULL;
618 }
Guido van Rossum85e3b011991-06-03 12:42:10 +0000619
620 argvlist = NEW(char *, argc+1);
621 if (argvlist == NULL)
622 return NULL;
623 for (i = 0; i < argc; i++) {
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000624 if (!getargs((*getitem)(argv, i), "s", &argvlist[i])) {
Guido van Rossum85e3b011991-06-03 12:42:10 +0000625 DEL(argvlist);
626 goto badarg;
627 }
Guido van Rossum85e3b011991-06-03 12:42:10 +0000628 }
629 argvlist[argc] = NULL;
630
Guido van Rossumb6775db1994-08-01 11:34:53 +0000631#ifdef BAD_EXEC_PROTOTYPES
632 execv(path, (const char **) argvlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000633#else /* BAD_EXEC_PROTOTYPES */
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000634 execv(path, argvlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000635#endif /* BAD_EXEC_PROTOTYPES */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000636
Guido van Rossum85e3b011991-06-03 12:42:10 +0000637 /* If we get here it's definitely an error */
638
639 DEL(argvlist);
640 return posix_error();
641}
642
643static object *
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000644posix_execve(self, args)
645 object *self;
646 object *args;
647{
648 char *path;
649 object *argv, *env;
650 char **argvlist;
651 char **envlist;
652 object *key, *val;
653 int i, pos, argc, envc;
654 object *(*getitem) PROTO((object *, int));
655
656 /* execve has three arguments: (path, argv, env), where
657 argv is a list or tuple of strings and env is a dictionary
658 like posix.environ. */
659
660 if (!getargs(args, "(sOO)", &path, &argv, &env))
661 return NULL;
662 if (is_listobject(argv)) {
663 argc = getlistsize(argv);
664 getitem = getlistitem;
665 }
666 else if (is_tupleobject(argv)) {
667 argc = gettuplesize(argv);
668 getitem = gettupleitem;
669 }
670 else {
671 err_setstr(TypeError, "argv must be tuple or list");
672 return NULL;
673 }
674 if (!is_dictobject(env)) {
675 err_setstr(TypeError, "env must be dictionary");
676 return NULL;
677 }
678
679 argvlist = NEW(char *, argc+1);
680 if (argvlist == NULL) {
681 err_nomem();
682 return NULL;
683 }
684 for (i = 0; i < argc; i++) {
685 if (!getargs((*getitem)(argv, i),
686 "s;argv must be list of strings",
687 &argvlist[i])) {
688 goto fail_1;
689 }
690 }
691 argvlist[argc] = NULL;
692
693 i = getmappingsize(env);
694 envlist = NEW(char *, i + 1);
695 if (envlist == NULL) {
696 err_nomem();
697 goto fail_1;
698 }
699 pos = 0;
700 envc = 0;
701 while (mappinggetnext(env, &pos, &key, &val)) {
702 char *p, *k, *v;
703 if (!getargs(key, "s;non-string key in env", &k) ||
704 !getargs(val, "s;non-string value in env", &v)) {
705 goto fail_2;
706 }
707 p = NEW(char, getstringsize(key) + getstringsize(val) + 2);
708 if (p == NULL) {
709 err_nomem();
710 goto fail_2;
711 }
712 sprintf(p, "%s=%s", k, v);
713 envlist[envc++] = p;
714 }
715 envlist[envc] = 0;
716
Guido van Rossumb6775db1994-08-01 11:34:53 +0000717
718#ifdef BAD_EXEC_PROTOTYPES
719 execve(path, (const char **)argvlist, envlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000720#else /* BAD_EXEC_PROTOTYPES */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000721 execve(path, argvlist, envlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000722#endif /* BAD_EXEC_PROTOTYPES */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000723
724 /* If we get here it's definitely an error */
725
726 (void) posix_error();
727
728 fail_2:
729 while (--envc >= 0)
730 DEL(envlist[envc]);
731 DEL(envlist);
732 fail_1:
733 DEL(argvlist);
734
735 return NULL;
736}
737
Guido van Rossum794d8131994-08-23 13:48:48 +0000738#ifndef NT
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000739static object *
Guido van Rossum85e3b011991-06-03 12:42:10 +0000740posix_fork(self, args)
741 object *self;
742 object *args;
743{
744 int pid;
Guido van Rossum50e61dc1992-03-27 17:22:31 +0000745 if (!getnoarg(args))
746 return NULL;
Guido van Rossum85e3b011991-06-03 12:42:10 +0000747 pid = fork();
748 if (pid == -1)
749 return posix_error();
750 return newintobject((long)pid);
751}
752
753static object *
Guido van Rossum46003ff1992-05-15 11:05:24 +0000754posix_getegid(self, args)
755 object *self;
756 object *args;
757{
758 if (!getnoarg(args))
759 return NULL;
760 return newintobject((long)getegid());
761}
762
763static object *
764posix_geteuid(self, args)
765 object *self;
766 object *args;
767{
768 if (!getnoarg(args))
769 return NULL;
770 return newintobject((long)geteuid());
771}
772
773static object *
774posix_getgid(self, args)
775 object *self;
776 object *args;
777{
778 if (!getnoarg(args))
779 return NULL;
780 return newintobject((long)getgid());
781}
Guido van Rossumb078ce11994-08-29 14:01:43 +0000782#endif /* !NT */
Guido van Rossum46003ff1992-05-15 11:05:24 +0000783
784static object *
Guido van Rossum85e3b011991-06-03 12:42:10 +0000785posix_getpid(self, args)
786 object *self;
787 object *args;
788{
Guido van Rossum04814471991-06-04 20:23:49 +0000789 if (!getnoarg(args))
Guido van Rossum85e3b011991-06-03 12:42:10 +0000790 return NULL;
791 return newintobject((long)getpid());
792}
793
Guido van Rossumb6775db1994-08-01 11:34:53 +0000794#ifdef HAVE_GETPGRP
Guido van Rossum85e3b011991-06-03 12:42:10 +0000795static object *
Guido van Rossum04814471991-06-04 20:23:49 +0000796posix_getpgrp(self, args)
797 object *self;
798 object *args;
799{
800 if (!getnoarg(args))
801 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000802#ifdef GETPGRP_HAVE_ARG
Guido van Rossum971443b1991-06-07 13:59:29 +0000803 return newintobject((long)getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000804#else /* GETPGRP_HAVE_ARG */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000805 return newintobject((long)getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000806#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +0000807}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000808#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +0000809
Guido van Rossumb6775db1994-08-01 11:34:53 +0000810#ifdef HAVE_SETPGRP
Guido van Rossum04814471991-06-04 20:23:49 +0000811static object *
Guido van Rossumc2670a01992-09-13 20:07:29 +0000812posix_setpgrp(self, args)
813 object *self;
814 object *args;
815{
816 if (!getnoarg(args))
817 return NULL;
Guido van Rossum64933891994-10-20 21:56:42 +0000818#ifdef SETPGRP_HAVE_ARG
Guido van Rossumc2670a01992-09-13 20:07:29 +0000819 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +0000820#else /* SETPGRP_HAVE_ARG */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000821 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +0000822#endif /* SETPGRP_HAVE_ARG */
Guido van Rossum687dd131993-05-17 08:34:16 +0000823 return posix_error();
Guido van Rossumc2670a01992-09-13 20:07:29 +0000824 INCREF(None);
825 return None;
826}
827
Guido van Rossumb6775db1994-08-01 11:34:53 +0000828#endif /* HAVE_SETPGRP */
829
Guido van Rossum794d8131994-08-23 13:48:48 +0000830#ifndef NT
Guido van Rossumc2670a01992-09-13 20:07:29 +0000831static object *
Guido van Rossum85e3b011991-06-03 12:42:10 +0000832posix_getppid(self, args)
833 object *self;
834 object *args;
835{
Guido van Rossum04814471991-06-04 20:23:49 +0000836 if (!getnoarg(args))
Guido van Rossum85e3b011991-06-03 12:42:10 +0000837 return NULL;
838 return newintobject((long)getppid());
839}
840
841static object *
Guido van Rossum46003ff1992-05-15 11:05:24 +0000842posix_getuid(self, args)
843 object *self;
844 object *args;
845{
846 if (!getnoarg(args))
847 return NULL;
848 return newintobject((long)getuid());
849}
850
851static object *
Guido van Rossum85e3b011991-06-03 12:42:10 +0000852posix_kill(self, args)
853 object *self;
854 object *args;
855{
856 int pid, sig;
Guido van Rossum234f9421993-06-17 12:35:49 +0000857 if (!getargs(args, "(ii)", &pid, &sig))
Guido van Rossum85e3b011991-06-03 12:42:10 +0000858 return NULL;
859 if (kill(pid, sig) == -1)
860 return posix_error();
861 INCREF(None);
862 return None;
863}
Guido van Rossum794d8131994-08-23 13:48:48 +0000864#endif /* !NT */
Guido van Rossum85e3b011991-06-03 12:42:10 +0000865
866static object *
Guido van Rossum3b066191991-06-04 19:40:25 +0000867posix_popen(self, args)
868 object *self;
869 object *args;
870{
Guido van Rossuma6a1e531995-01-10 15:36:38 +0000871 char *name;
872 char *mode = "r";
873 int bufsize = -1;
Guido van Rossum3b066191991-06-04 19:40:25 +0000874 FILE *fp;
Guido van Rossuma6a1e531995-01-10 15:36:38 +0000875 object *f;
876 if (!newgetargs(args, "s|si", &name, &mode, &bufsize))
Guido van Rossum3b066191991-06-04 19:40:25 +0000877 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000878 BGN_SAVE
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000879 fp = popen(name, mode);
Guido van Rossumff4949e1992-08-05 19:58:53 +0000880 END_SAVE
Guido van Rossum3b066191991-06-04 19:40:25 +0000881 if (fp == NULL)
882 return posix_error();
Guido van Rossuma6a1e531995-01-10 15:36:38 +0000883 f = newopenfileobject(fp, name, mode, pclose);
884 if (f != NULL)
885 setfilebufsize(f, bufsize);
886 return f;
Guido van Rossum3b066191991-06-04 19:40:25 +0000887}
888
Guido van Rossumb6775db1994-08-01 11:34:53 +0000889#ifdef HAVE_SETUID
Guido van Rossum3b066191991-06-04 19:40:25 +0000890static object *
Guido van Rossuma3d78fb1993-11-10 09:23:53 +0000891posix_setuid(self, args)
892 object *self;
893 object *args;
894{
895 int uid;
896 if (!getargs(args, "i", &uid))
897 return NULL;
898 if (setuid(uid) < 0)
899 return posix_error();
900 INCREF(None);
901 return None;
902}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000903#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +0000904
Guido van Rossumb6775db1994-08-01 11:34:53 +0000905#ifdef HAVE_SETGID
Guido van Rossuma3d78fb1993-11-10 09:23:53 +0000906static object *
907posix_setgid(self, args)
908 object *self;
909 object *args;
910{
911 int gid;
912 if (!getargs(args, "i", &gid))
913 return NULL;
914 if (setgid(gid) < 0)
915 return posix_error();
916 INCREF(None);
917 return None;
918}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000919#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +0000920
Guido van Rossumb6775db1994-08-01 11:34:53 +0000921#ifdef HAVE_WAITPID
Guido van Rossuma3d78fb1993-11-10 09:23:53 +0000922static object *
Guido van Rossum21803b81992-08-09 12:55:27 +0000923posix_waitpid(self, args)
Guido van Rossum85e3b011991-06-03 12:42:10 +0000924 object *self;
925 object *args;
926{
Guido van Rossum21803b81992-08-09 12:55:27 +0000927 int pid, options, sts;
928 if (!getargs(args, "(ii)", &pid, &options))
929 return NULL;
930 BGN_SAVE
931 pid = waitpid(pid, &sts, options);
932 END_SAVE
Guido van Rossum85e3b011991-06-03 12:42:10 +0000933 if (pid == -1)
934 return posix_error();
Guido van Rossum21803b81992-08-09 12:55:27 +0000935 else
936 return mkvalue("ii", pid, sts);
Guido van Rossum21803b81992-08-09 12:55:27 +0000937}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000938#endif /* HAVE_WAITPID */
Guido van Rossum21803b81992-08-09 12:55:27 +0000939
Guido van Rossum794d8131994-08-23 13:48:48 +0000940#ifndef NT
Guido van Rossum21803b81992-08-09 12:55:27 +0000941static object *
942posix_wait(self, args)
943 object *self;
944 object *args;
945{
946 int pid, sts;
Guido van Rossum21803b81992-08-09 12:55:27 +0000947 BGN_SAVE
948 pid = wait(&sts);
949 END_SAVE
950 if (pid == -1)
951 return posix_error();
952 else
953 return mkvalue("ii", pid, sts);
Guido van Rossum85e3b011991-06-03 12:42:10 +0000954}
Guido van Rossum794d8131994-08-23 13:48:48 +0000955#endif /* !NT */
Guido van Rossum85e3b011991-06-03 12:42:10 +0000956
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000957static object *
958posix_lstat(self, args)
959 object *self;
960 object *args;
961{
Guido van Rossumb6775db1994-08-01 11:34:53 +0000962#ifdef HAVE_LSTAT
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000963 return posix_do_stat(self, args, lstat);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000964#else /* !HAVE_LSTAT */
965 return posix_do_stat(self, args, stat);
966#endif /* !HAVE_LSTAT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000967}
968
Guido van Rossumb6775db1994-08-01 11:34:53 +0000969#ifdef HAVE_READLINK
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000970static object *
971posix_readlink(self, args)
972 object *self;
973 object *args;
974{
Guido van Rossumb6775db1994-08-01 11:34:53 +0000975 char buf[MAXPATHLEN];
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000976 char *path;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000977 int n;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +0000978 if (!getargs(args, "s", &path))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000979 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000980 BGN_SAVE
Guido van Rossum50e61dc1992-03-27 17:22:31 +0000981 n = readlink(path, buf, (int) sizeof buf);
Guido van Rossumff4949e1992-08-05 19:58:53 +0000982 END_SAVE
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000983 if (n < 0)
984 return posix_error();
985 return newsizedstringobject(buf, n);
986}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000987#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000988
Guido van Rossumb6775db1994-08-01 11:34:53 +0000989#ifdef HAVE_SYMLINK
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000990static object *
991posix_symlink(self, args)
992 object *self;
993 object *args;
994{
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000995 return posix_2str(args, symlink);
996}
Guido van Rossumb6775db1994-08-01 11:34:53 +0000997#endif /* HAVE_SYMLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000998
Guido van Rossumb6775db1994-08-01 11:34:53 +0000999#ifdef HAVE_TIMES
1000#ifndef HZ
1001#define HZ 60 /* Universal constant :-) */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001002#endif /* HZ */
Guido van Rossum22db57e1992-04-05 14:25:30 +00001003static object *
1004posix_times(self, args)
1005 object *self;
1006 object *args;
1007{
1008 struct tms t;
1009 clock_t c;
Guido van Rossum22db57e1992-04-05 14:25:30 +00001010 if (!getnoarg(args))
1011 return NULL;
1012 errno = 0;
1013 c = times(&t);
Guido van Rossum687dd131993-05-17 08:34:16 +00001014 if (c == (clock_t) -1)
1015 return posix_error();
Guido van Rossum0b0db8e1993-01-21 16:07:51 +00001016 return mkvalue("dddd",
1017 (double)t.tms_utime / HZ,
1018 (double)t.tms_stime / HZ,
1019 (double)t.tms_cutime / HZ,
1020 (double)t.tms_cstime / HZ);
Guido van Rossum22db57e1992-04-05 14:25:30 +00001021}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001022#endif /* HAVE_TIMES */
Guido van Rossum14ed0b21994-09-29 09:50:09 +00001023#ifdef NT
1024#define HAVE_TIMES /* so the method table will pick it up */
1025static object *
1026posix_times(self, args)
1027 object *self;
1028 object *args;
1029{
1030 FILETIME create, exit, kernel, user;
1031 HANDLE hProc;
1032 if (!getnoarg(args))
1033 return NULL;
1034 hProc = GetCurrentProcess();
1035 GetProcessTimes(hProc,&create, &exit, &kernel, &user);
1036 return mkvalue("dddd",
1037 (double)(kernel.dwHighDateTime*2E32+kernel.dwLowDateTime) / 2E6,
1038 (double)(user.dwHighDateTime*2E32+user.dwLowDateTime) / 2E6,
1039 (double)0,
1040 (double)0);
1041}
1042#endif /* NT */
Guido van Rossum22db57e1992-04-05 14:25:30 +00001043
Guido van Rossumb6775db1994-08-01 11:34:53 +00001044#ifdef HAVE_SETSID
Guido van Rossumc2670a01992-09-13 20:07:29 +00001045static object *
1046posix_setsid(self, args)
1047 object *self;
1048 object *args;
1049{
1050 if (!getnoarg(args))
1051 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00001052 if (setsid() < 0)
1053 return posix_error();
Guido van Rossumc2670a01992-09-13 20:07:29 +00001054 INCREF(None);
1055 return None;
1056}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001057#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00001058
Guido van Rossumb6775db1994-08-01 11:34:53 +00001059#ifdef HAVE_SETPGID
Guido van Rossumc2670a01992-09-13 20:07:29 +00001060static object *
1061posix_setpgid(self, args)
1062 object *self;
1063 object *args;
1064{
1065 int pid, pgrp;
1066 if (!getargs(args, "(ii)", &pid, &pgrp))
1067 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00001068 if (setpgid(pid, pgrp) < 0)
1069 return posix_error();
Guido van Rossumc2670a01992-09-13 20:07:29 +00001070 INCREF(None);
1071 return None;
1072}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001073#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00001074
Guido van Rossumb6775db1994-08-01 11:34:53 +00001075#ifdef HAVE_TCGETPGRP
Guido van Rossum7066dd71992-09-17 17:54:56 +00001076static object *
1077posix_tcgetpgrp(self, args)
1078 object *self;
1079 object *args;
1080{
1081 int fd, pgid;
1082 if (!getargs(args, "i", &fd))
1083 return NULL;
1084 pgid = tcgetpgrp(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00001085 if (pgid < 0)
1086 return posix_error();
Guido van Rossum7066dd71992-09-17 17:54:56 +00001087 return newintobject((long)pgid);
1088}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001089#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +00001090
Guido van Rossumb6775db1994-08-01 11:34:53 +00001091#ifdef HAVE_TCSETPGRP
Guido van Rossum7066dd71992-09-17 17:54:56 +00001092static object *
1093posix_tcsetpgrp(self, args)
1094 object *self;
1095 object *args;
1096{
1097 int fd, pgid;
1098 if (!getargs(args, "(ii)", &fd, &pgid))
1099 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00001100 if (tcsetpgrp(fd, pgid) < 0)
1101 return posix_error();
Guido van Rossum7066dd71992-09-17 17:54:56 +00001102 INCREF(None);
1103 return None;
1104}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001105#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +00001106
Guido van Rossum687dd131993-05-17 08:34:16 +00001107/* Functions acting on file descriptors */
1108
Guido van Rossum234f9421993-06-17 12:35:49 +00001109static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001110posix_open(self, args)
1111 object *self;
1112 object *args;
1113{
1114 char *file;
1115 int flag;
1116 int mode = 0777;
1117 int fd;
1118 if (!getargs(args, "(si)", &file, &flag)) {
1119 err_clear();
1120 if (!getargs(args, "(sii)", &file, &flag, &mode))
1121 return NULL;
1122 }
1123 BGN_SAVE
1124 fd = open(file, flag, mode);
1125 END_SAVE
1126 if (fd < 0)
1127 return posix_error();
1128 return newintobject((long)fd);
1129}
1130
Guido van Rossum234f9421993-06-17 12:35:49 +00001131static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001132posix_close(self, args)
1133 object *self;
1134 object *args;
1135{
1136 int fd, res;
1137 if (!getargs(args, "i", &fd))
1138 return NULL;
1139 BGN_SAVE
1140 res = close(fd);
1141 END_SAVE
1142 if (res < 0)
1143 return posix_error();
1144 INCREF(None);
1145 return None;
1146}
1147
Guido van Rossum234f9421993-06-17 12:35:49 +00001148static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001149posix_dup(self, args)
1150 object *self;
1151 object *args;
1152{
1153 int fd;
1154 if (!getargs(args, "i", &fd))
1155 return NULL;
1156 BGN_SAVE
1157 fd = dup(fd);
1158 END_SAVE
1159 if (fd < 0)
1160 return posix_error();
1161 return newintobject((long)fd);
1162}
1163
Guido van Rossum234f9421993-06-17 12:35:49 +00001164static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001165posix_dup2(self, args)
1166 object *self;
1167 object *args;
1168{
1169 int fd, fd2, res;
1170 if (!getargs(args, "(ii)", &fd, &fd2))
1171 return NULL;
1172 BGN_SAVE
1173 res = dup2(fd, fd2);
1174 END_SAVE
1175 if (res < 0)
1176 return posix_error();
1177 INCREF(None);
1178 return None;
1179}
1180
Guido van Rossum234f9421993-06-17 12:35:49 +00001181static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001182posix_lseek(self, args)
1183 object *self;
1184 object *args;
1185{
1186 int fd, how;
1187 long pos, res;
1188 if (!getargs(args, "(ili)", &fd, &pos, &how))
1189 return NULL;
1190#ifdef SEEK_SET
1191 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
1192 switch (how) {
1193 case 0: how = SEEK_SET; break;
1194 case 1: how = SEEK_CUR; break;
1195 case 2: how = SEEK_END; break;
1196 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001197#endif /* SEEK_END */
Guido van Rossum687dd131993-05-17 08:34:16 +00001198 BGN_SAVE
1199 res = lseek(fd, pos, how);
1200 END_SAVE
1201 if (res < 0)
1202 return posix_error();
1203 return newintobject(res);
1204}
1205
Guido van Rossum234f9421993-06-17 12:35:49 +00001206static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001207posix_read(self, args)
1208 object *self;
1209 object *args;
1210{
1211 int fd, size;
1212 object *buffer;
1213 if (!getargs(args, "(ii)", &fd, &size))
1214 return NULL;
1215 buffer = newsizedstringobject((char *)NULL, size);
1216 if (buffer == NULL)
1217 return NULL;
1218 BGN_SAVE
1219 size = read(fd, getstringvalue(buffer), size);
1220 END_SAVE
1221 if (size < 0) {
1222 DECREF(buffer);
1223 return posix_error();
1224 }
1225 resizestring(&buffer, size);
1226 return buffer;
1227}
1228
Guido van Rossum234f9421993-06-17 12:35:49 +00001229static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001230posix_write(self, args)
1231 object *self;
1232 object *args;
1233{
1234 int fd, size;
1235 char *buffer;
1236 if (!getargs(args, "(is#)", &fd, &buffer, &size))
1237 return NULL;
1238 BGN_SAVE
1239 size = write(fd, buffer, size);
1240 END_SAVE
1241 if (size < 0)
1242 return posix_error();
1243 return newintobject((long)size);
1244}
1245
Guido van Rossum234f9421993-06-17 12:35:49 +00001246static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001247posix_fstat(self, args)
1248 object *self;
1249 object *args;
1250{
1251 int fd;
1252 struct stat st;
1253 int res;
1254 if (!getargs(args, "i", &fd))
1255 return NULL;
1256 BGN_SAVE
1257 res = fstat(fd, &st);
1258 END_SAVE
1259 if (res != 0)
1260 return posix_error();
1261 return mkvalue("(llllllllll)",
1262 (long)st.st_mode,
1263 (long)st.st_ino,
1264 (long)st.st_dev,
1265 (long)st.st_nlink,
1266 (long)st.st_uid,
1267 (long)st.st_gid,
1268 (long)st.st_size,
1269 (long)st.st_atime,
1270 (long)st.st_mtime,
1271 (long)st.st_ctime);
1272}
1273
1274static object *
1275posix_fdopen(self, args)
1276 object *self;
1277 object *args;
1278{
1279 extern int fclose PROTO((FILE *));
1280 int fd;
Guido van Rossuma6a1e531995-01-10 15:36:38 +00001281 char *mode = "r";
1282 int bufsize = -1;
Guido van Rossum687dd131993-05-17 08:34:16 +00001283 FILE *fp;
Guido van Rossuma6a1e531995-01-10 15:36:38 +00001284 object *f;
1285 if (!newgetargs(args, "i|si", &fd, &mode, &bufsize))
Guido van Rossum687dd131993-05-17 08:34:16 +00001286 return NULL;
1287 BGN_SAVE
1288 fp = fdopen(fd, mode);
1289 END_SAVE
1290 if (fp == NULL)
1291 return posix_error();
Guido van Rossuma6a1e531995-01-10 15:36:38 +00001292 f = newopenfileobject(fp, "(fdopen)", mode, fclose);
1293 if (f != NULL)
1294 setfilebufsize(f, bufsize);
1295 return f;
Guido van Rossum687dd131993-05-17 08:34:16 +00001296}
1297
Guido van Rossum234f9421993-06-17 12:35:49 +00001298static object *
Guido van Rossum687dd131993-05-17 08:34:16 +00001299posix_pipe(self, args)
1300 object *self;
1301 object *args;
1302{
Guido van Rossum794d8131994-08-23 13:48:48 +00001303#ifndef NT
Guido van Rossum687dd131993-05-17 08:34:16 +00001304 int fds[2];
1305 int res;
1306 if (!getargs(args, ""))
1307 return NULL;
1308 BGN_SAVE
1309 res = pipe(fds);
1310 END_SAVE
1311 if (res != 0)
1312 return posix_error();
1313 return mkvalue("(ii)", fds[0], fds[1]);
Guido van Rossum794d8131994-08-23 13:48:48 +00001314#else /* NT */
1315 HANDLE read, write;
1316 BOOL ok;
1317 if (!getargs(args, ""))
1318 return NULL;
1319 BGN_SAVE
1320 ok = CreatePipe( &read, &write, NULL, 0);
1321 END_SAVE
1322 if (!ok)
1323 return posix_error();
1324 return mkvalue("(ii)", read, write);
1325#endif /* NT */
Guido van Rossum687dd131993-05-17 08:34:16 +00001326}
Guido van Rossum22db57e1992-04-05 14:25:30 +00001327
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001328static struct methodlist posix_methods[] = {
1329 {"chdir", posix_chdir},
1330 {"chmod", posix_chmod},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001331#ifdef HAVE_CHOWN
1332 {"chown", posix_chown},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001333#endif /* HAVE_CHOWN */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001334 {"getcwd", posix_getcwd},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001335#ifdef HAVE_LINK
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001336 {"link", posix_link},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001337#endif /* HAVE_LINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001338 {"listdir", posix_listdir},
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001339 {"lstat", posix_lstat},
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001340 {"mkdir", posix_mkdir},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001341#ifdef HAVE_NICE
Guido van Rossum775f4da1993-01-09 17:18:52 +00001342 {"nice", posix_nice},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001343#endif /* HAVE_NICE */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001344#ifdef HAVE_READLINK
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001345 {"readlink", posix_readlink},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001346#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001347 {"rename", posix_rename},
1348 {"rmdir", posix_rmdir},
1349 {"stat", posix_stat},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001350#ifdef HAVE_SYMLINK
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001351 {"symlink", posix_symlink},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001352#endif /* HAVE_SYMLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001353 {"system", posix_system},
1354 {"umask", posix_umask},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001355#ifdef HAVE_UNAME
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001356 {"uname", posix_uname},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001357#endif /* HAVE_UNAME */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001358 {"unlink", posix_unlink},
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001359 {"utime", posix_utime},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001360#ifdef HAVE_TIMES
Guido van Rossum22db57e1992-04-05 14:25:30 +00001361 {"times", posix_times},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001362#endif /* HAVE_TIMES */
Guido van Rossum85e3b011991-06-03 12:42:10 +00001363 {"_exit", posix__exit},
Guido van Rossum89b33251993-10-22 14:26:06 +00001364 {"execv", posix_execv},
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001365 {"execve", posix_execve},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001366#ifndef NT
Guido van Rossum85e3b011991-06-03 12:42:10 +00001367 {"fork", posix_fork},
Guido van Rossum46003ff1992-05-15 11:05:24 +00001368 {"getegid", posix_getegid},
1369 {"geteuid", posix_geteuid},
1370 {"getgid", posix_getgid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001371#endif /* !NT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00001372 {"getpid", posix_getpid},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001373#ifdef HAVE_GETPGRP
Guido van Rossum04814471991-06-04 20:23:49 +00001374 {"getpgrp", posix_getpgrp},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001375#endif /* HAVE_GETPGRP */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001376#ifndef NT
Guido van Rossum85e3b011991-06-03 12:42:10 +00001377 {"getppid", posix_getppid},
Guido van Rossum46003ff1992-05-15 11:05:24 +00001378 {"getuid", posix_getuid},
Guido van Rossum85e3b011991-06-03 12:42:10 +00001379 {"kill", posix_kill},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001380#endif /* !NT */
Guido van Rossuma6a1e531995-01-10 15:36:38 +00001381 {"popen", posix_popen, 1},
Guido van Rossumb6775db1994-08-01 11:34:53 +00001382#ifdef HAVE_SETUID
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00001383 {"setuid", posix_setuid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001384#endif /* HAVE_SETUID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001385#ifdef HAVE_SETGID
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00001386 {"setgid", posix_setgid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001387#endif /* HAVE_SETGID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001388#ifdef HAVE_SETPGRP
Guido van Rossumc2670a01992-09-13 20:07:29 +00001389 {"setpgrp", posix_setpgrp},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001390#endif /* HAVE_SETPGRP */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001391#ifndef NT
Guido van Rossum85e3b011991-06-03 12:42:10 +00001392 {"wait", posix_wait},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001393#endif /* !NT */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001394#ifdef HAVE_WAITPID
Guido van Rossum21803b81992-08-09 12:55:27 +00001395 {"waitpid", posix_waitpid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001396#endif /* HAVE_WAITPID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001397#ifdef HAVE_SETSID
Guido van Rossumc2670a01992-09-13 20:07:29 +00001398 {"setsid", posix_setsid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001399#endif /* HAVE_SETSID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001400#ifdef HAVE_SETPGID
Guido van Rossumc2670a01992-09-13 20:07:29 +00001401 {"setpgid", posix_setpgid},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001402#endif /* HAVE_SETPGID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001403#ifdef HAVE_TCGETPGRP
Guido van Rossum7066dd71992-09-17 17:54:56 +00001404 {"tcgetpgrp", posix_tcgetpgrp},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001405#endif /* HAVE_TCGETPGRP */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001406#ifdef HAVE_TCSETPGRP
Guido van Rossum7066dd71992-09-17 17:54:56 +00001407 {"tcsetpgrp", posix_tcsetpgrp},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001408#endif /* HAVE_TCSETPGRP */
Guido van Rossum687dd131993-05-17 08:34:16 +00001409 {"open", posix_open},
1410 {"close", posix_close},
1411 {"dup", posix_dup},
1412 {"dup2", posix_dup2},
1413 {"lseek", posix_lseek},
1414 {"read", posix_read},
1415 {"write", posix_write},
1416 {"fstat", posix_fstat},
Guido van Rossuma6a1e531995-01-10 15:36:38 +00001417 {"fdopen", posix_fdopen, 1},
Guido van Rossum687dd131993-05-17 08:34:16 +00001418 {"pipe", posix_pipe},
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001419 {NULL, NULL} /* Sentinel */
1420};
1421
1422
Guido van Rossumb6775db1994-08-01 11:34:53 +00001423#ifdef NT
1424void
1425initnt()
1426{
1427 object *m, *d, *v;
1428
1429 m = initmodule("nt", posix_methods);
1430 d = getmoduledict(m);
1431
1432 /* Initialize nt.environ dictionary */
1433 v = convertenviron();
1434 if (v == NULL || dictinsert(d, "environ", v) != 0)
1435 fatal("can't define nt.environ");
1436 DECREF(v);
1437
1438 /* Initialize nt.error exception */
1439 PosixError = newstringobject("nt.error");
1440 if (PosixError == NULL || dictinsert(d, "error", PosixError) != 0)
1441 fatal("can't define nt.error");
1442}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001443#else /* !NT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001444void
1445initposix()
1446{
1447 object *m, *d, *v;
1448
1449 m = initmodule("posix", posix_methods);
1450 d = getmoduledict(m);
1451
1452 /* Initialize posix.environ dictionary */
1453 v = convertenviron();
1454 if (v == NULL || dictinsert(d, "environ", v) != 0)
1455 fatal("can't define posix.environ");
1456 DECREF(v);
1457
1458 /* Initialize posix.error exception */
1459 PosixError = newstringobject("posix.error");
1460 if (PosixError == NULL || dictinsert(d, "error", PosixError) != 0)
1461 fatal("can't define posix.error");
1462}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001463#endif /* !NT */