blob: f897d0a6d86f10b1343899a665741c48232a4d50 [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
Guido van Rossumd266eb41996-10-25 14:44:06 +00007Permission to use, copy, modify, and distribute this software and its
8documentation for any purpose and without fee is hereby granted,
Guido van Rossumf70e43a1991-02-19 12:39:46 +00009provided that the above copyright notice appear in all copies and that
Guido van Rossumd266eb41996-10-25 14:44:06 +000010both that copyright notice and this permission notice appear in
Guido van Rossumf70e43a1991-02-19 12:39:46 +000011supporting documentation, and that the names of Stichting Mathematisch
Guido van Rossumd266eb41996-10-25 14:44:06 +000012Centrum or CWI or Corporation for National Research Initiatives or
13CNRI not be used in advertising or publicity pertaining to
14distribution of the software without specific, written prior
15permission.
Guido van Rossumf70e43a1991-02-19 12:39:46 +000016
Guido van Rossumd266eb41996-10-25 14:44:06 +000017While CWI is the initial source for this software, a modified version
18is made available by the Corporation for National Research Initiatives
19(CNRI) at the Internet address ftp://ftp.python.org.
20
21STICHTING MATHEMATISCH CENTRUM AND CNRI DISCLAIM ALL WARRANTIES WITH
22REGARD TO THIS SOFTWARE, INCLUDING ALL IMPLIED WARRANTIES OF
23MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL STICHTING MATHEMATISCH
24CENTRUM OR CNRI BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL
25DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR
26PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER
27TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
28PERFORMANCE OF THIS SOFTWARE.
Guido van Rossumf70e43a1991-02-19 12:39:46 +000029
30******************************************************************/
31
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000032/* POSIX module implementation */
33
Guido van Rossuma4916fa1996-05-23 22:58:55 +000034/* This file is also used for Windows NT and MS-Win. In that case the module
Guido van Rossumad0ee831995-03-01 10:34:45 +000035 actually calls itself 'nt', not 'posix', and a few functions are
36 either unimplemented or implemented differently. The source
Guido van Rossum8d665e61996-06-26 18:22:49 +000037 assumes that for Windows NT, the macro 'MS_WIN32' is defined independent
Guido van Rossumad0ee831995-03-01 10:34:45 +000038 of the compiler used. Different compilers define their own feature
Guido van Rossuma4916fa1996-05-23 22:58:55 +000039 test macro, e.g. '__BORLANDC__' or '_MSC_VER'. */
Guido van Rossumad0ee831995-03-01 10:34:45 +000040
Guido van Rossuma4916fa1996-05-23 22:58:55 +000041/* See also ../Dos/dosmodule.c */
Guido van Rossumad0ee831995-03-01 10:34:45 +000042
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000043static char posix__doc__ [] =
44"This module provides access to operating system functionality that is\n\
45standardized by the C Standard and the POSIX standard (a thinly\n\
46disguised Unix interface). Refer to the library manual and\n\
47corresponding Unix manual entries for more information on calls.";
48
Barry Warsaw53699e91996-12-10 23:23:01 +000049#include "Python.h"
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000050
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000051#if defined(PYOS_OS2)
52#define INCL_DOS
53#define INCL_DOSERRORS
54#define INCL_DOSPROCESS
55#define INCL_NOPMAPI
56#include <os2.h>
57#endif
58
Guido van Rossumb6775db1994-08-01 11:34:53 +000059#include <sys/types.h>
60#include <sys/stat.h>
Guido van Rossum36bc6801995-06-14 22:54:23 +000061#ifdef HAVE_SYS_WAIT_H
62#include <sys/wait.h> /* For WNOHANG */
63#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +000064
Guido van Rossuma376cc51996-12-05 23:43:35 +000065#ifdef HAVE_SIGNAL_H
66#include <signal.h>
67#endif
68
Guido van Rossumb6775db1994-08-01 11:34:53 +000069#include "mytime.h" /* For clock_t on some systems */
70
71#ifdef HAVE_FCNTL_H
72#include <fcntl.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000073#endif /* HAVE_FCNTL_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000074
Guido van Rossuma4916fa1996-05-23 22:58:55 +000075/* Various compilers have only certain posix functions */
Guido van Rossum6d8841c1997-08-14 19:57:39 +000076/* XXX Gosh I wish these were all moved into config.h */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000077#if defined(PYCC_VACPP) && defined(PYOS_OS2)
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000078#include <process.h>
79#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +000080#if defined(__WATCOMC__) && !defined(__QNX__) /* Watcom compiler */
Guido van Rossuma4916fa1996-05-23 22:58:55 +000081#define HAVE_GETCWD 1
82#define HAVE_OPENDIR 1
83#define HAVE_SYSTEM 1
84#if defined(__OS2__)
85#define HAVE_EXECV 1
86#define HAVE_WAIT 1
Guido van Rossumad0ee831995-03-01 10:34:45 +000087#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +000088#include <process.h>
89#else
90#ifdef __BORLANDC__ /* Borland compiler */
91#define HAVE_EXECV 1
92#define HAVE_GETCWD 1
93#define HAVE_GETEGID 1
94#define HAVE_GETEUID 1
95#define HAVE_GETGID 1
96#define HAVE_GETPPID 1
97#define HAVE_GETUID 1
98#define HAVE_KILL 1
99#define HAVE_OPENDIR 1
100#define HAVE_PIPE 1
101#define HAVE_POPEN 1
102#define HAVE_SYSTEM 1
103#define HAVE_WAIT 1
104#else
105#ifdef _MSC_VER /* Microsoft compiler */
Guido van Rossum8d665e61996-06-26 18:22:49 +0000106#define HAVE_GETCWD 1
107#ifdef MS_WIN32
Guido van Rossuma1065681999-01-25 23:20:23 +0000108#define HAVE_SPAWNV 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000109#define HAVE_EXECV 1
110#define HAVE_PIPE 1
111#define HAVE_POPEN 1
112#define HAVE_SYSTEM 1
113#else /* 16-bit Windows */
Guido van Rossum8d665e61996-06-26 18:22:49 +0000114#endif /* !MS_WIN32 */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000115#else /* all other compilers */
116/* Unix functions that the configure script doesn't check for */
117#define HAVE_EXECV 1
118#define HAVE_FORK 1
119#define HAVE_GETCWD 1
120#define HAVE_GETEGID 1
121#define HAVE_GETEUID 1
122#define HAVE_GETGID 1
123#define HAVE_GETPPID 1
124#define HAVE_GETUID 1
125#define HAVE_KILL 1
126#define HAVE_OPENDIR 1
127#define HAVE_PIPE 1
128#define HAVE_POPEN 1
129#define HAVE_SYSTEM 1
130#define HAVE_WAIT 1
Guido van Rossumd371ff11999-01-25 16:12:23 +0000131#define HAVE_TTYNAME 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000132#endif /* _MSC_VER */
133#endif /* __BORLANDC__ */
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000134#endif /* ! __WATCOMC__ || __QNX__ */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000135#endif /* ! __IBMC__ */
Guido van Rossumad0ee831995-03-01 10:34:45 +0000136
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000137#ifndef _MSC_VER
Guido van Rossum36bc6801995-06-14 22:54:23 +0000138
Guido van Rossumb6775db1994-08-01 11:34:53 +0000139#ifdef HAVE_UNISTD_H
Guido van Rossum0b0db8e1993-01-21 16:07:51 +0000140#include <unistd.h>
Guido van Rossum36bc6801995-06-14 22:54:23 +0000141#endif
142
143#ifdef NeXT
144/* NeXT's <unistd.h> and <utime.h> aren't worth much */
145#undef HAVE_UNISTD_H
146#undef HAVE_UTIME_H
Guido van Rossumb9f866c1997-05-22 15:12:39 +0000147#define HAVE_WAITPID
Guido van Rossum36bc6801995-06-14 22:54:23 +0000148/* #undef HAVE_GETCWD */
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000149#define UNION_WAIT /* This should really be checked for by autoconf */
Guido van Rossum36bc6801995-06-14 22:54:23 +0000150#endif
151
152#ifdef HAVE_UNISTD_H
Guido van Rossumad0ee831995-03-01 10:34:45 +0000153/* XXX These are for SunOS4.1.3 but shouldn't hurt elsewhere */
154extern int rename();
155extern int pclose();
156extern int lstat();
157extern int symlink();
Guido van Rossum8c67e4e1999-04-07 15:49:41 +0000158extern int fsync();
Guido van Rossumb6775db1994-08-01 11:34:53 +0000159#else /* !HAVE_UNISTD_H */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000160#if defined(PYCC_VACPP)
161extern int mkdir Py_PROTO((char *));
162#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000163#if ( defined(__WATCOMC__) || defined(_MSC_VER) ) && !defined(__QNX__)
Barry Warsaw53699e91996-12-10 23:23:01 +0000164extern int mkdir Py_PROTO((const char *));
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000165#else
Barry Warsaw53699e91996-12-10 23:23:01 +0000166extern int mkdir Py_PROTO((const char *, mode_t));
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000167#endif
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000168#endif
169#if defined(__IBMC__) || defined(__IBMCPP__)
170extern int chdir Py_PROTO((char *));
171extern int rmdir Py_PROTO((char *));
172#else
Barry Warsaw53699e91996-12-10 23:23:01 +0000173extern int chdir Py_PROTO((const char *));
174extern int rmdir Py_PROTO((const char *));
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000175#endif
Barry Warsaw53699e91996-12-10 23:23:01 +0000176extern int chmod Py_PROTO((const char *, mode_t));
177extern int chown Py_PROTO((const char *, uid_t, gid_t));
178extern char *getcwd Py_PROTO((char *, int));
179extern char *strerror Py_PROTO((int));
180extern int link Py_PROTO((const char *, const char *));
181extern int rename Py_PROTO((const char *, const char *));
182extern int stat Py_PROTO((const char *, struct stat *));
183extern int unlink Py_PROTO((const char *));
184extern int pclose Py_PROTO((FILE *));
Guido van Rossumb6775db1994-08-01 11:34:53 +0000185#ifdef HAVE_SYMLINK
Barry Warsaw53699e91996-12-10 23:23:01 +0000186extern int symlink Py_PROTO((const char *, const char *));
Guido van Rossuma38a5031995-02-17 15:11:36 +0000187#endif /* HAVE_SYMLINK */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000188#ifdef HAVE_LSTAT
Barry Warsaw53699e91996-12-10 23:23:01 +0000189extern int lstat Py_PROTO((const char *, struct stat *));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000190#endif /* HAVE_LSTAT */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000191#endif /* !HAVE_UNISTD_H */
Guido van Rossum36bc6801995-06-14 22:54:23 +0000192
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000193#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000194
Guido van Rossumb6775db1994-08-01 11:34:53 +0000195#ifdef HAVE_UTIME_H
196#include <utime.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000197#endif /* HAVE_UTIME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000198
Guido van Rossum14ed0b21994-09-29 09:50:09 +0000199#ifdef HAVE_SYS_UTIME_H
200#include <sys/utime.h>
201#define HAVE_UTIME_H /* pretend we do for the rest of this file */
202#endif /* HAVE_SYS_UTIME_H */
203
Guido van Rossumb6775db1994-08-01 11:34:53 +0000204#ifdef HAVE_SYS_TIMES_H
205#include <sys/times.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000206#endif /* HAVE_SYS_TIMES_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000207
208#ifdef HAVE_SYS_PARAM_H
209#include <sys/param.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000210#endif /* HAVE_SYS_PARAM_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000211
212#ifdef HAVE_SYS_UTSNAME_H
213#include <sys/utsname.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000214#endif /* HAVE_SYS_UTSNAME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000215
216#ifndef MAXPATHLEN
217#define MAXPATHLEN 1024
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000218#endif /* MAXPATHLEN */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000219
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000220#ifdef HAVE_DIRENT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000221#include <dirent.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000222#define NAMLEN(dirent) strlen((dirent)->d_name)
223#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000224#if defined(__WATCOMC__) && !defined(__QNX__)
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000225#include <direct.h>
226#define NAMLEN(dirent) strlen((dirent)->d_name)
227#else
Guido van Rossumb6775db1994-08-01 11:34:53 +0000228#define dirent direct
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000229#define NAMLEN(dirent) (dirent)->d_namlen
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000230#endif
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000231#ifdef HAVE_SYS_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000232#include <sys/ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000233#endif
234#ifdef HAVE_SYS_DIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000235#include <sys/dir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000236#endif
237#ifdef HAVE_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000238#include <ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000239#endif
240#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +0000241
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000242#ifdef _MSC_VER
Guido van Rossumb6775db1994-08-01 11:34:53 +0000243#include <direct.h>
244#include <io.h>
245#include <process.h>
246#include <windows.h>
Guido van Rossum8d665e61996-06-26 18:22:49 +0000247#ifdef MS_WIN32
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000248#define popen _popen
Guido van Rossum794d8131994-08-23 13:48:48 +0000249#define pclose _pclose
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000250#else /* 16-bit Windows */
251#include <dos.h>
252#include <ctype.h>
Guido van Rossum8d665e61996-06-26 18:22:49 +0000253#endif /* MS_WIN32 */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000254#endif /* _MSC_VER */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000255
Guido van Rossumd48f2521997-12-05 22:19:34 +0000256#if defined(PYCC_VACPP) && defined(PYOS_OS2)
Guido van Rossumb6775db1994-08-01 11:34:53 +0000257#include <io.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000258#endif /* OS2 */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000259
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000260#ifdef UNION_WAIT
261/* Emulate some macros on systems that have a union instead of macros */
262
263#ifndef WIFEXITED
264#define WIFEXITED(u_wait) (!(u_wait).w_termsig && !(u_wait).w_coredump)
265#endif
266
267#ifndef WEXITSTATUS
268#define WEXITSTATUS(u_wait) (WIFEXITED(u_wait)?((u_wait).w_retcode):-1)
269#endif
270
271#ifndef WTERMSIG
272#define WTERMSIG(u_wait) ((u_wait).w_termsig)
273#endif
274
275#endif /* UNION_WAIT */
276
Greg Wardb48bc172000-03-01 21:51:56 +0000277/* Don't use the "_r" form if we don't need it (also, won't have a
278 prototype for it, at least on Solaris -- maybe others as well?). */
279#if defined(HAVE_CTERMID_R) && defined(WITH_THREAD)
280#define USE_CTERMID_R
281#endif
282
283#if defined(HAVE_TMPNAM_R) && defined(WITH_THREAD)
284#define USE_TMPNAM_R
285#endif
286
Fred Drake699f3522000-06-29 21:12:41 +0000287/* choose the appropriate stat and fstat functions and return structs */
288#ifdef MS_WIN64
289# define STAT _stati64
290# define FSTAT _fstati64
291# define STRUCT_STAT struct _stati64
292#else
293# define STAT stat
294# define FSTAT fstat
295# define STRUCT_STAT struct stat
296#endif
297
298
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000299/* Return a dictionary corresponding to the POSIX environment table */
300
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000301#if !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000302extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000303#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000304
Barry Warsaw53699e91996-12-10 23:23:01 +0000305static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000306convertenviron()
307{
Barry Warsaw53699e91996-12-10 23:23:01 +0000308 PyObject *d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000309 char **e;
Barry Warsaw53699e91996-12-10 23:23:01 +0000310 d = PyDict_New();
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000311 if (d == NULL)
312 return NULL;
313 if (environ == NULL)
314 return d;
Guido van Rossum6a619f41999-08-03 19:41:10 +0000315 /* This part ignores errors */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000316 for (e = environ; *e != NULL; e++) {
Guido van Rossum6a619f41999-08-03 19:41:10 +0000317 PyObject *k;
Barry Warsaw53699e91996-12-10 23:23:01 +0000318 PyObject *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000319 char *p = strchr(*e, '=');
320 if (p == NULL)
321 continue;
Guido van Rossum6a619f41999-08-03 19:41:10 +0000322 k = PyString_FromStringAndSize(*e, (int)(p-*e));
323 if (k == NULL) {
324 PyErr_Clear();
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000325 continue;
Guido van Rossum6a619f41999-08-03 19:41:10 +0000326 }
327 v = PyString_FromString(p+1);
328 if (v == NULL) {
329 PyErr_Clear();
330 Py_DECREF(k);
331 continue;
332 }
333 if (PyDict_GetItem(d, k) == NULL) {
334 if (PyDict_SetItem(d, k, v) != 0)
335 PyErr_Clear();
336 }
337 Py_DECREF(k);
Barry Warsaw53699e91996-12-10 23:23:01 +0000338 Py_DECREF(v);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000339 }
Guido van Rossumd48f2521997-12-05 22:19:34 +0000340#if defined(PYOS_OS2)
341 {
342 APIRET rc;
343 char buffer[1024]; /* OS/2 Provides a Documented Max of 1024 Chars */
344
345 rc = DosQueryExtLIBPATH(buffer, BEGIN_LIBPATH);
346 if (rc == NO_ERROR) { /* (not a type, envname is NOT 'BEGIN_LIBPATH') */
347 PyObject *v = PyString_FromString(buffer);
348 PyDict_SetItemString(d, "BEGINLIBPATH", v);
349 Py_DECREF(v);
350 }
351 rc = DosQueryExtLIBPATH(buffer, END_LIBPATH);
352 if (rc == NO_ERROR) { /* (not a typo, envname is NOT 'END_LIBPATH') */
353 PyObject *v = PyString_FromString(buffer);
354 PyDict_SetItemString(d, "ENDLIBPATH", v);
355 Py_DECREF(v);
356 }
357 }
358#endif
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000359 return d;
360}
361
362
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000363/* Set a POSIX-specific error from errno, and return NULL */
364
Barry Warsawd58d7641998-07-23 16:14:40 +0000365static PyObject *
366posix_error()
Guido van Rossumad0ee831995-03-01 10:34:45 +0000367{
Barry Warsawca74da41999-02-09 19:31:45 +0000368 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000369}
Barry Warsawd58d7641998-07-23 16:14:40 +0000370static PyObject *
371posix_error_with_filename(name)
372 char* name;
373{
Barry Warsawca74da41999-02-09 19:31:45 +0000374 return PyErr_SetFromErrnoWithFilename(PyExc_OSError, name);
Barry Warsawd58d7641998-07-23 16:14:40 +0000375}
376
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000377
Guido van Rossumd48f2521997-12-05 22:19:34 +0000378#if defined(PYOS_OS2)
379/**********************************************************************
380 * Helper Function to Trim and Format OS/2 Messages
381 **********************************************************************/
382 static void
383os2_formatmsg(char *msgbuf, int msglen, char *reason)
384{
385 msgbuf[msglen] = '\0'; /* OS/2 Doesn't Guarantee a Terminator */
386
387 if (strlen(msgbuf) > 0) { /* If Non-Empty Msg, Trim CRLF */
388 char *lastc = &msgbuf[ strlen(msgbuf)-1 ];
389
390 while (lastc > msgbuf && isspace(*lastc))
391 *lastc-- = '\0'; /* Trim Trailing Whitespace (CRLF) */
392 }
393
394 /* Add Optional Reason Text */
395 if (reason) {
396 strcat(msgbuf, " : ");
397 strcat(msgbuf, reason);
398 }
399}
400
401/**********************************************************************
402 * Decode an OS/2 Operating System Error Code
403 *
404 * A convenience function to lookup an OS/2 error code and return a
405 * text message we can use to raise a Python exception.
406 *
407 * Notes:
408 * The messages for errors returned from the OS/2 kernel reside in
409 * the file OSO001.MSG in the \OS2 directory hierarchy.
410 *
411 **********************************************************************/
412 static char *
413os2_strerror(char *msgbuf, int msgbuflen, int errorcode, char *reason)
414{
415 APIRET rc;
416 ULONG msglen;
417
418 /* Retrieve Kernel-Related Error Message from OSO001.MSG File */
419 Py_BEGIN_ALLOW_THREADS
420 rc = DosGetMessage(NULL, 0, msgbuf, msgbuflen,
421 errorcode, "oso001.msg", &msglen);
422 Py_END_ALLOW_THREADS
423
424 if (rc == NO_ERROR)
425 os2_formatmsg(msgbuf, msglen, reason);
426 else
427 sprintf(msgbuf, "unknown OS error #%d", errorcode);
428
429 return msgbuf;
430}
431
432/* Set an OS/2-specific error and return NULL. OS/2 kernel
433 errors are not in a global variable e.g. 'errno' nor are
434 they congruent with posix error numbers. */
435
436static PyObject * os2_error(int code)
437{
438 char text[1024];
439 PyObject *v;
440
441 os2_strerror(text, sizeof(text), code, "");
442
443 v = Py_BuildValue("(is)", code, text);
444 if (v != NULL) {
Barry Warsawca74da41999-02-09 19:31:45 +0000445 PyErr_SetObject(PyExc_OSError, v);
Guido van Rossumd48f2521997-12-05 22:19:34 +0000446 Py_DECREF(v);
447 }
448 return NULL; /* Signal to Python that an Exception is Pending */
449}
450
451#endif /* OS2 */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000452
453/* POSIX generic methods */
454
Barry Warsaw53699e91996-12-10 23:23:01 +0000455static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000456posix_int(args, format, func)
Guido van Rossum21142a01999-01-08 21:05:37 +0000457 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000458 char *format;
Guido van Rossum21142a01999-01-08 21:05:37 +0000459 int (*func) Py_FPROTO((int));
460{
461 int fd;
462 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000463 if (!PyArg_ParseTuple(args, format, &fd))
Guido van Rossum21142a01999-01-08 21:05:37 +0000464 return NULL;
465 Py_BEGIN_ALLOW_THREADS
466 res = (*func)(fd);
467 Py_END_ALLOW_THREADS
468 if (res < 0)
469 return posix_error();
470 Py_INCREF(Py_None);
471 return Py_None;
472}
473
474
475static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000476posix_1str(args, format, func)
Barry Warsaw53699e91996-12-10 23:23:01 +0000477 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000478 char *format;
Barry Warsaw53699e91996-12-10 23:23:01 +0000479 int (*func) Py_FPROTO((const char *));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000480{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000481 char *path1;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000482 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000483 if (!PyArg_ParseTuple(args, format, &path1))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000484 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +0000485 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000486 res = (*func)(path1);
Barry Warsaw53699e91996-12-10 23:23:01 +0000487 Py_END_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000488 if (res < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +0000489 return posix_error_with_filename(path1);
Barry Warsaw53699e91996-12-10 23:23:01 +0000490 Py_INCREF(Py_None);
491 return Py_None;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000492}
493
Barry Warsaw53699e91996-12-10 23:23:01 +0000494static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000495posix_2str(args, format, func)
Barry Warsaw53699e91996-12-10 23:23:01 +0000496 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000497 char *format;
Barry Warsaw53699e91996-12-10 23:23:01 +0000498 int (*func) Py_FPROTO((const char *, const char *));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000499{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000500 char *path1, *path2;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000501 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000502 if (!PyArg_ParseTuple(args, format, &path1, &path2))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000503 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +0000504 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000505 res = (*func)(path1, path2);
Barry Warsaw53699e91996-12-10 23:23:01 +0000506 Py_END_ALLOW_THREADS
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000507 if (res != 0)
Barry Warsawd58d7641998-07-23 16:14:40 +0000508 /* XXX how to report both path1 and path2??? */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000509 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +0000510 Py_INCREF(Py_None);
511 return Py_None;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000512}
513
Barry Warsaw53699e91996-12-10 23:23:01 +0000514static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000515posix_strint(args, format, func)
Barry Warsaw53699e91996-12-10 23:23:01 +0000516 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000517 char *format;
Barry Warsaw53699e91996-12-10 23:23:01 +0000518 int (*func) Py_FPROTO((const char *, int));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000519{
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000520 char *path;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000521 int i;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000522 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000523 if (!PyArg_ParseTuple(args, format, &path, &i))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000524 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +0000525 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000526 res = (*func)(path, i);
Barry Warsaw53699e91996-12-10 23:23:01 +0000527 Py_END_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000528 if (res < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +0000529 return posix_error_with_filename(path);
Barry Warsaw53699e91996-12-10 23:23:01 +0000530 Py_INCREF(Py_None);
531 return Py_None;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000532}
533
Barry Warsaw53699e91996-12-10 23:23:01 +0000534static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000535posix_strintint(args, format, func)
Barry Warsaw53699e91996-12-10 23:23:01 +0000536 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000537 char *format;
Barry Warsaw53699e91996-12-10 23:23:01 +0000538 int (*func) Py_FPROTO((const char *, int, int));
Guido van Rossumb6775db1994-08-01 11:34:53 +0000539{
540 char *path;
541 int i,i2;
542 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000543 if (!PyArg_ParseTuple(args, format, &path, &i, &i2))
Guido van Rossumb6775db1994-08-01 11:34:53 +0000544 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +0000545 Py_BEGIN_ALLOW_THREADS
Guido van Rossumb6775db1994-08-01 11:34:53 +0000546 res = (*func)(path, i, i2);
Barry Warsaw53699e91996-12-10 23:23:01 +0000547 Py_END_ALLOW_THREADS
Guido van Rossumb6775db1994-08-01 11:34:53 +0000548 if (res < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +0000549 return posix_error_with_filename(path);
Barry Warsaw53699e91996-12-10 23:23:01 +0000550 Py_INCREF(Py_None);
551 return Py_None;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000552}
553
Fred Drake699f3522000-06-29 21:12:41 +0000554
555
556/* pack a system stat C structure into the Python stat tuple
557 (used by posix_stat() and posix_fstat()) */
558static PyObject*
559_pystat_fromstructstat(st)
560 STRUCT_STAT st;
561{
562 PyObject *v = PyTuple_New(10);
563 if (v == NULL)
564 return NULL;
565
566 PyTuple_SetItem(v, 0, PyInt_FromLong((long)st.st_mode));
567#ifdef HAVE_LARGEFILE_SUPPORT
568 PyTuple_SetItem(v, 1, PyLong_FromLongLong((LONG_LONG)st.st_ino));
569#else
570 PyTuple_SetItem(v, 1, PyInt_FromLong((long)st.st_ino));
571#endif
572#if defined(HAVE_LONG_LONG) && !defined(MS_WINDOWS)
573 PyTuple_SetItem(v, 2, PyLong_FromLongLong((LONG_LONG)st.st_dev));
574#else
575 PyTuple_SetItem(v, 2, PyInt_FromLong((long)st.st_dev));
576#endif
577 PyTuple_SetItem(v, 3, PyInt_FromLong((long)st.st_nlink));
578 PyTuple_SetItem(v, 4, PyInt_FromLong((long)st.st_uid));
579 PyTuple_SetItem(v, 5, PyInt_FromLong((long)st.st_gid));
580#ifdef HAVE_LARGEFILE_SUPPORT
581 PyTuple_SetItem(v, 6, PyLong_FromLongLong((LONG_LONG)st.st_size));
582#else
583 PyTuple_SetItem(v, 6, PyInt_FromLong(st.st_size));
584#endif
585#if SIZEOF_TIME_T > SIZEOF_LONG
586 PyTuple_SetItem(v, 7, PyLong_FromLongLong((LONG_LONG)st.st_atime));
587 PyTuple_SetItem(v, 8, PyLong_FromLongLong((LONG_LONG)st.st_mtime));
588 PyTuple_SetItem(v, 9, PyLong_FromLongLong((LONG_LONG)st.st_ctime));
589#else
590 PyTuple_SetItem(v, 7, PyInt_FromLong((long)st.st_atime));
591 PyTuple_SetItem(v, 8, PyInt_FromLong((long)st.st_mtime));
592 PyTuple_SetItem(v, 9, PyInt_FromLong((long)st.st_ctime));
593#endif
594
595 if (PyErr_Occurred()) {
596 Py_DECREF(v);
597 return NULL;
598 }
599
600 return v;
601}
602
603
Barry Warsaw53699e91996-12-10 23:23:01 +0000604static PyObject *
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000605posix_do_stat(self, args, format, statfunc)
Barry Warsaw53699e91996-12-10 23:23:01 +0000606 PyObject *self;
607 PyObject *args;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000608 char *format;
Fred Drake699f3522000-06-29 21:12:41 +0000609 int (*statfunc) Py_FPROTO((const char *, STRUCT_STAT *));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000610{
Fred Drake699f3522000-06-29 21:12:41 +0000611 STRUCT_STAT st;
Guido van Rossumef0a00e1992-01-27 16:51:30 +0000612 char *path;
Guido van Rossumff4949e1992-08-05 19:58:53 +0000613 int res;
Guido van Rossumace88ae2000-04-21 18:54:45 +0000614
615#ifdef MS_WIN32
616 int pathlen;
617 char pathcopy[MAX_PATH];
618#endif /* MS_WIN32 */
619
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000620 if (!PyArg_ParseTuple(args, format, &path))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000621 return NULL;
Guido van Rossumace88ae2000-04-21 18:54:45 +0000622
623#ifdef MS_WIN32
624 pathlen = strlen(path);
625 /* the library call can blow up if the file name is too long! */
626 if (pathlen > MAX_PATH) {
627 errno = ENAMETOOLONG;
628 return posix_error();
629 }
630
631 if ((pathlen > 0) && (path[pathlen-1] == '\\' || path[pathlen-1] == '/')) {
Guido van Rossum19dde102000-05-03 02:44:55 +0000632 /* exception for specific or current drive root */
633 if (!((pathlen == 1) ||
634 ((pathlen == 3) &&
Guido van Rossumace88ae2000-04-21 18:54:45 +0000635 (path[1] == ':') &&
Guido van Rossum19dde102000-05-03 02:44:55 +0000636 (path[2] == '\\' || path[2] == '/'))))
Guido van Rossumace88ae2000-04-21 18:54:45 +0000637 {
638 strncpy(pathcopy, path, pathlen);
639 pathcopy[pathlen-1] = '\0'; /* nuke the trailing backslash */
640 path = pathcopy;
641 }
642 }
643#endif /* MS_WIN32 */
644
Barry Warsaw53699e91996-12-10 23:23:01 +0000645 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000646 res = (*statfunc)(path, &st);
Barry Warsaw53699e91996-12-10 23:23:01 +0000647 Py_END_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000648 if (res != 0)
Barry Warsawd58d7641998-07-23 16:14:40 +0000649 return posix_error_with_filename(path);
Fred Drake699f3522000-06-29 21:12:41 +0000650
651 return _pystat_fromstructstat(st);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000652}
653
654
655/* POSIX methods */
656
Guido van Rossum94f6f721999-01-06 18:42:14 +0000657static char posix_access__doc__[] =
Guido van Rossum015f22a1999-01-06 22:52:38 +0000658"access(path, mode) -> 1 if granted, 0 otherwise\n\
Guido van Rossum94f6f721999-01-06 18:42:14 +0000659Test for access to a file.";
660
661static PyObject *
662posix_access(self, args)
663 PyObject *self;
664 PyObject *args;
665{
Guido van Rossum015f22a1999-01-06 22:52:38 +0000666 char *path;
667 int mode;
668 int res;
669
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000670 if (!PyArg_ParseTuple(args, "si:access", &path, &mode))
Guido van Rossum015f22a1999-01-06 22:52:38 +0000671 return NULL;
672 Py_BEGIN_ALLOW_THREADS
673 res = access(path, mode);
674 Py_END_ALLOW_THREADS
675 return(PyInt_FromLong(res == 0 ? 1L : 0L));
Guido van Rossum94f6f721999-01-06 18:42:14 +0000676}
677
Guido van Rossumd371ff11999-01-25 16:12:23 +0000678#ifndef F_OK
679#define F_OK 0
680#endif
681#ifndef R_OK
682#define R_OK 4
683#endif
684#ifndef W_OK
685#define W_OK 2
686#endif
687#ifndef X_OK
688#define X_OK 1
689#endif
690
691#ifdef HAVE_TTYNAME
Guido van Rossum94f6f721999-01-06 18:42:14 +0000692static char posix_ttyname__doc__[] =
Guido van Rossum61eeb041999-02-22 15:29:15 +0000693"ttyname(fd) -> String\n\
Guido van Rossum94f6f721999-01-06 18:42:14 +0000694Return the name of the terminal device connected to 'fd'.";
695
696static PyObject *
697posix_ttyname(self, args)
698 PyObject *self;
699 PyObject *args;
700{
Guido van Rossum94f6f721999-01-06 18:42:14 +0000701 int id;
702 char *ret;
703
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000704 if (!PyArg_ParseTuple(args, "i:ttyname", &id))
Guido van Rossum94f6f721999-01-06 18:42:14 +0000705 return NULL;
706
Guido van Rossum94f6f721999-01-06 18:42:14 +0000707 ret = ttyname(id);
708 if (ret == NULL)
709 return(posix_error());
710 return(PyString_FromString(ret));
711}
Guido van Rossumd371ff11999-01-25 16:12:23 +0000712#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +0000713
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000714#ifdef HAVE_CTERMID
715static char posix_ctermid__doc__[] =
716"ctermid() -> String\n\
717Return the name of the controlling terminal for this process.";
718
719static PyObject *
720posix_ctermid(self, args)
721 PyObject *self;
722 PyObject *args;
723{
724 char *ret;
725 char buffer[L_ctermid];
726
727 if (!PyArg_ParseTuple(args, ":ctermid"))
728 return NULL;
729
Greg Wardb48bc172000-03-01 21:51:56 +0000730#ifdef USE_CTERMID_R
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000731 ret = ctermid_r(buffer);
732#else
733 ret = ctermid(buffer);
734#endif
735 if (ret == NULL)
736 return(posix_error());
737 return(PyString_FromString(buffer));
738}
739#endif
740
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000741static char posix_chdir__doc__[] =
742"chdir(path) -> None\n\
743Change the current working directory to the specified path.";
744
Barry Warsaw53699e91996-12-10 23:23:01 +0000745static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000746posix_chdir(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000747 PyObject *self;
748 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000749{
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000750 return posix_1str(args, "s:chdir", chdir);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000751}
752
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000753
754static char posix_chmod__doc__[] =
755"chmod(path, mode) -> None\n\
756Change the access permissions of a file.";
757
Barry Warsaw53699e91996-12-10 23:23:01 +0000758static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000759posix_chmod(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000760 PyObject *self;
761 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000762{
Guido van Rossumffd15f52000-03-31 00:47:28 +0000763 char *path;
764 int i;
765 int res;
Guido van Rossum49679b42000-03-31 00:48:21 +0000766 if (!PyArg_ParseTuple(args, "si", &path, &i))
Guido van Rossumffd15f52000-03-31 00:47:28 +0000767 return NULL;
768 Py_BEGIN_ALLOW_THREADS
Guido van Rossumef40e772000-03-31 01:26:23 +0000769 res = chmod(path, i);
Guido van Rossumffd15f52000-03-31 00:47:28 +0000770 Py_END_ALLOW_THREADS
771 if (res < 0)
772 return posix_error_with_filename(path);
773 Py_INCREF(Py_None);
774 return Py_None;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000775}
776
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000777
Guido van Rossum21142a01999-01-08 21:05:37 +0000778#ifdef HAVE_FSYNC
779static char posix_fsync__doc__[] =
780"fsync(fildes) -> None\n\
781force write of file with filedescriptor to disk.";
782
783static PyObject *
784posix_fsync(self, args)
785 PyObject *self;
786 PyObject *args;
787{
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000788 return posix_int(args, "i:fsync", fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +0000789}
790#endif /* HAVE_FSYNC */
791
792#ifdef HAVE_FDATASYNC
793static char posix_fdatasync__doc__[] =
794"fdatasync(fildes) -> None\n\
795force write of file with filedescriptor to disk.\n\
796 does not force update of metadata.";
797
Guido van Rossum5d00b6d1999-01-08 21:28:05 +0000798extern int fdatasync(int); /* Prototype just in case */
799
Guido van Rossum21142a01999-01-08 21:05:37 +0000800static PyObject *
801posix_fdatasync(self, args)
802 PyObject *self;
803 PyObject *args;
804{
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000805 return posix_int(args, "i:fdatasync", fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +0000806}
807#endif /* HAVE_FDATASYNC */
808
809
Guido van Rossumb6775db1994-08-01 11:34:53 +0000810#ifdef HAVE_CHOWN
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000811static char posix_chown__doc__[] =
812"chown(path, uid, gid) -> None\n\
813Change the owner and group id of path to the numeric uid and gid.";
814
Barry Warsaw53699e91996-12-10 23:23:01 +0000815static PyObject *
Guido van Rossumb6775db1994-08-01 11:34:53 +0000816posix_chown(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000817 PyObject *self;
818 PyObject *args;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000819{
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000820 return posix_strintint(args, "sii:chown", chown);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000821}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000822#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000823
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000824
Guido van Rossum36bc6801995-06-14 22:54:23 +0000825#ifdef HAVE_GETCWD
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000826static char posix_getcwd__doc__[] =
827"getcwd() -> path\n\
828Return a string representing the current working directory.";
829
Barry Warsaw53699e91996-12-10 23:23:01 +0000830static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000831posix_getcwd(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000832 PyObject *self;
833 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000834{
835 char buf[1026];
Guido van Rossumff4949e1992-08-05 19:58:53 +0000836 char *res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000837 if (!PyArg_ParseTuple(args, ":getcwd"))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000838 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +0000839 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000840 res = getcwd(buf, sizeof buf);
Barry Warsaw53699e91996-12-10 23:23:01 +0000841 Py_END_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +0000842 if (res == NULL)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000843 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +0000844 return PyString_FromString(buf);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000845}
Guido van Rossum36bc6801995-06-14 22:54:23 +0000846#endif
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000847
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000848
Guido van Rossumb6775db1994-08-01 11:34:53 +0000849#ifdef HAVE_LINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000850static char posix_link__doc__[] =
851"link(src, dst) -> None\n\
852Create a hard link to a file.";
853
Barry Warsaw53699e91996-12-10 23:23:01 +0000854static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000855posix_link(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000856 PyObject *self;
857 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000858{
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000859 return posix_2str(args, "ss:link", link);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000860}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000861#endif /* HAVE_LINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000862
Guido van Rossumec4f4ac1997-06-02 22:20:51 +0000863
864static char posix_listdir__doc__[] =
865"listdir(path) -> list_of_strings\n\
866Return a list containing the names of the entries in the directory.\n\
867\n\
868 path: path of directory to list\n\
869\n\
870The list is in arbitrary order. It does not include the special\n\
871entries '.' and '..' even if they are present in the directory.";
872
Barry Warsaw53699e91996-12-10 23:23:01 +0000873static PyObject *
Guido van Rossumb6775db1994-08-01 11:34:53 +0000874posix_listdir(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +0000875 PyObject *self;
876 PyObject *args;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000877{
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000878 /* XXX Should redo this putting the (now four) versions of opendir
Guido van Rossum6d8841c1997-08-14 19:57:39 +0000879 in separate files instead of having them all here... */
Guido van Rossum8d665e61996-06-26 18:22:49 +0000880#if defined(MS_WIN32) && !defined(HAVE_OPENDIR)
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000881
Guido van Rossumb6775db1994-08-01 11:34:53 +0000882 char *name;
883 int len;
Barry Warsaw53699e91996-12-10 23:23:01 +0000884 PyObject *d, *v;
Guido van Rossumb6775db1994-08-01 11:34:53 +0000885 HANDLE hFindFile;
886 WIN32_FIND_DATA FileData;
887 char namebuf[MAX_PATH+5];
888
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000889 if (!PyArg_ParseTuple(args, "t#:listdir", &name, &len))
Guido van Rossumb6775db1994-08-01 11:34:53 +0000890 return NULL;
891 if (len >= MAX_PATH) {
Barry Warsaw53699e91996-12-10 23:23:01 +0000892 PyErr_SetString(PyExc_ValueError, "path too long");
Guido van Rossumb6775db1994-08-01 11:34:53 +0000893 return NULL;
894 }
895 strcpy(namebuf, name);
896 if (namebuf[len-1] != '/' && namebuf[len-1] != '\\')
897 namebuf[len++] = '/';
898 strcpy(namebuf + len, "*.*");
899
Barry Warsaw53699e91996-12-10 23:23:01 +0000900 if ((d = PyList_New(0)) == NULL)
Guido van Rossumb6775db1994-08-01 11:34:53 +0000901 return NULL;
902
903 hFindFile = FindFirstFile(namebuf, &FileData);
904 if (hFindFile == INVALID_HANDLE_VALUE) {
905 errno = GetLastError();
Guido van Rossum617bc191998-08-06 03:23:32 +0000906 if (errno == ERROR_FILE_NOT_FOUND)
907 return PyList_New(0);
Barry Warsawf63b8cc1999-05-27 23:13:21 +0000908 return posix_error_with_filename(name);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000909 }
910 do {
Guido van Rossum24f42ac1995-07-18 18:16:52 +0000911 if (FileData.cFileName[0] == '.' &&
912 (FileData.cFileName[1] == '\0' ||
913 FileData.cFileName[1] == '.' &&
914 FileData.cFileName[2] == '\0'))
915 continue;
Barry Warsaw53699e91996-12-10 23:23:01 +0000916 v = PyString_FromString(FileData.cFileName);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000917 if (v == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +0000918 Py_DECREF(d);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000919 d = NULL;
920 break;
921 }
Barry Warsaw53699e91996-12-10 23:23:01 +0000922 if (PyList_Append(d, v) != 0) {
923 Py_DECREF(v);
924 Py_DECREF(d);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000925 d = NULL;
926 break;
927 }
Barry Warsaw53699e91996-12-10 23:23:01 +0000928 Py_DECREF(v);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000929 } while (FindNextFile(hFindFile, &FileData) == TRUE);
930
931 if (FindClose(hFindFile) == FALSE) {
932 errno = GetLastError();
Andrew M. Kuchling54c8dc22000-06-06 20:52:17 +0000933 return posix_error_with_filename(name);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000934 }
935
936 return d;
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000937
Guido van Rossum8d665e61996-06-26 18:22:49 +0000938#else /* !MS_WIN32 */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000939#ifdef _MSC_VER /* 16-bit Windows */
940
941#ifndef MAX_PATH
942#define MAX_PATH 250
943#endif
944 char *name, *pt;
945 int len;
Barry Warsaw53699e91996-12-10 23:23:01 +0000946 PyObject *d, *v;
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000947 char namebuf[MAX_PATH+5];
948 struct _find_t ep;
949
Fred Drake5ab8eaf1999-12-09 21:13:07 +0000950 if (!PyArg_ParseTuple(args, "t#:listdir", &name, &len))
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000951 return NULL;
952 if (len >= MAX_PATH) {
Barry Warsaw53699e91996-12-10 23:23:01 +0000953 PyErr_SetString(PyExc_ValueError, "path too long");
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000954 return NULL;
955 }
956 strcpy(namebuf, name);
957 for (pt = namebuf; *pt; pt++)
958 if (*pt == '/')
959 *pt = '\\';
960 if (namebuf[len-1] != '\\')
961 namebuf[len++] = '\\';
962 strcpy(namebuf + len, "*.*");
963
Barry Warsaw53699e91996-12-10 23:23:01 +0000964 if ((d = PyList_New(0)) == NULL)
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000965 return NULL;
966
967 if (_dos_findfirst(namebuf, _A_RDONLY |
Barry Warsaw43d68b81996-12-19 22:10:44 +0000968 _A_HIDDEN | _A_SYSTEM | _A_SUBDIR, &ep) != 0)
969 {
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000970 errno = ENOENT;
Barry Warsawf63b8cc1999-05-27 23:13:21 +0000971 return posix_error_with_filename(name);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000972 }
973 do {
974 if (ep.name[0] == '.' &&
975 (ep.name[1] == '\0' ||
976 ep.name[1] == '.' &&
977 ep.name[2] == '\0'))
978 continue;
979 strcpy(namebuf, ep.name);
980 for (pt = namebuf; *pt; pt++)
981 if (isupper(*pt))
982 *pt = tolower(*pt);
Barry Warsaw53699e91996-12-10 23:23:01 +0000983 v = PyString_FromString(namebuf);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000984 if (v == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +0000985 Py_DECREF(d);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000986 d = NULL;
987 break;
988 }
Barry Warsaw53699e91996-12-10 23:23:01 +0000989 if (PyList_Append(d, v) != 0) {
990 Py_DECREF(v);
991 Py_DECREF(d);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000992 d = NULL;
993 break;
994 }
Barry Warsaw53699e91996-12-10 23:23:01 +0000995 Py_DECREF(v);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000996 } while (_dos_findnext(&ep) == 0);
997
998 return d;
999
1000#else
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001001#if defined(PYOS_OS2)
1002
1003#ifndef MAX_PATH
1004#define MAX_PATH CCHMAXPATH
1005#endif
1006 char *name, *pt;
1007 int len;
1008 PyObject *d, *v;
1009 char namebuf[MAX_PATH+5];
1010 HDIR hdir = 1;
1011 ULONG srchcnt = 1;
1012 FILEFINDBUF3 ep;
1013 APIRET rc;
1014
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001015 if (!PyArg_ParseTuple(args, "t#:listdir", &name, &len))
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001016 return NULL;
1017 if (len >= MAX_PATH) {
1018 PyErr_SetString(PyExc_ValueError, "path too long");
1019 return NULL;
1020 }
1021 strcpy(namebuf, name);
1022 for (pt = namebuf; *pt; pt++)
1023 if (*pt == '/')
1024 *pt = '\\';
1025 if (namebuf[len-1] != '\\')
1026 namebuf[len++] = '\\';
1027 strcpy(namebuf + len, "*.*");
1028
1029 if ((d = PyList_New(0)) == NULL)
1030 return NULL;
1031
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001032 rc = DosFindFirst(namebuf, /* Wildcard Pattern to Match */
1033 &hdir, /* Handle to Use While Search Directory */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001034 FILE_READONLY | FILE_HIDDEN | FILE_SYSTEM | FILE_DIRECTORY,
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001035 &ep, sizeof(ep), /* Structure to Receive Directory Entry */
1036 &srchcnt, /* Max and Actual Count of Entries Per Iteration */
1037 FIL_STANDARD); /* Format of Entry (EAs or Not) */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001038
1039 if (rc != NO_ERROR) {
1040 errno = ENOENT;
Barry Warsawf63b8cc1999-05-27 23:13:21 +00001041 return posix_error_with_filename(name);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001042 }
1043
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001044 if (srchcnt > 0) { /* If Directory is NOT Totally Empty, */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001045 do {
1046 if (ep.achName[0] == '.'
1047 && (ep.achName[1] == '\0' || ep.achName[1] == '.' && ep.achName[2] == '\0'))
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001048 continue; /* Skip Over "." and ".." Names */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001049
1050 strcpy(namebuf, ep.achName);
1051
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001052 /* Leave Case of Name Alone -- In Native Form */
1053 /* (Removed Forced Lowercasing Code) */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001054
1055 v = PyString_FromString(namebuf);
1056 if (v == NULL) {
1057 Py_DECREF(d);
1058 d = NULL;
1059 break;
1060 }
1061 if (PyList_Append(d, v) != 0) {
1062 Py_DECREF(v);
1063 Py_DECREF(d);
1064 d = NULL;
1065 break;
1066 }
1067 Py_DECREF(v);
1068 } while (DosFindNext(hdir, &ep, sizeof(ep), &srchcnt) == NO_ERROR && srchcnt > 0);
1069 }
1070
1071 return d;
1072#else
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001073
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001074 char *name;
Barry Warsaw53699e91996-12-10 23:23:01 +00001075 PyObject *d, *v;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001076 DIR *dirp;
Guido van Rossumb6775db1994-08-01 11:34:53 +00001077 struct dirent *ep;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001078 if (!PyArg_ParseTuple(args, "s:listdir", &name))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001079 return NULL;
Guido van Rossumff4949e1992-08-05 19:58:53 +00001080 if ((dirp = opendir(name)) == NULL) {
Barry Warsawf63b8cc1999-05-27 23:13:21 +00001081 return posix_error_with_filename(name);
Guido van Rossumff4949e1992-08-05 19:58:53 +00001082 }
Barry Warsaw53699e91996-12-10 23:23:01 +00001083 if ((d = PyList_New(0)) == NULL) {
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001084 closedir(dirp);
1085 return NULL;
1086 }
1087 while ((ep = readdir(dirp)) != NULL) {
Guido van Rossum24f42ac1995-07-18 18:16:52 +00001088 if (ep->d_name[0] == '.' &&
1089 (NAMLEN(ep) == 1 ||
Guido van Rossuma376cc51996-12-05 23:43:35 +00001090 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
Guido van Rossum24f42ac1995-07-18 18:16:52 +00001091 continue;
Barry Warsaw53699e91996-12-10 23:23:01 +00001092 v = PyString_FromStringAndSize(ep->d_name, NAMLEN(ep));
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001093 if (v == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001094 Py_DECREF(d);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001095 d = NULL;
1096 break;
1097 }
Barry Warsaw53699e91996-12-10 23:23:01 +00001098 if (PyList_Append(d, v) != 0) {
1099 Py_DECREF(v);
1100 Py_DECREF(d);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001101 d = NULL;
1102 break;
1103 }
Barry Warsaw53699e91996-12-10 23:23:01 +00001104 Py_DECREF(v);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001105 }
1106 closedir(dirp);
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00001107
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001108 return d;
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001109
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00001110#endif /* !PYOS_OS2 */
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001111#endif /* !_MSC_VER */
Guido van Rossum8d665e61996-06-26 18:22:49 +00001112#endif /* !MS_WIN32 */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001113}
1114
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001115static char posix_mkdir__doc__[] =
1116"mkdir(path [, mode=0777]) -> None\n\
1117Create a directory.";
1118
Barry Warsaw53699e91996-12-10 23:23:01 +00001119static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001120posix_mkdir(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001121 PyObject *self;
1122 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001123{
Guido van Rossumb0824db1996-02-25 04:50:32 +00001124 int res;
1125 char *path;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001126 int mode = 0777;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001127 if (!PyArg_ParseTuple(args, "s|i:mkdir", &path, &mode))
Guido van Rossumb0824db1996-02-25 04:50:32 +00001128 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001129 Py_BEGIN_ALLOW_THREADS
Guido van Rossumc5a0f531997-12-02 20:36:02 +00001130#if ( defined(__WATCOMC__) || defined(_MSC_VER) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001131 res = mkdir(path);
1132#else
Guido van Rossumb0824db1996-02-25 04:50:32 +00001133 res = mkdir(path, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001134#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00001135 Py_END_ALLOW_THREADS
Guido van Rossumb0824db1996-02-25 04:50:32 +00001136 if (res < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +00001137 return posix_error_with_filename(path);
Barry Warsaw53699e91996-12-10 23:23:01 +00001138 Py_INCREF(Py_None);
1139 return Py_None;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001140}
1141
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001142
Guido van Rossumb6775db1994-08-01 11:34:53 +00001143#ifdef HAVE_NICE
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001144static char posix_nice__doc__[] =
1145"nice(inc) -> new_priority\n\
1146Decrease the priority of process and return new priority.";
1147
Barry Warsaw53699e91996-12-10 23:23:01 +00001148static PyObject *
Guido van Rossum775f4da1993-01-09 17:18:52 +00001149posix_nice(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001150 PyObject *self;
1151 PyObject *args;
Guido van Rossum775f4da1993-01-09 17:18:52 +00001152{
1153 int increment, value;
1154
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001155 if (!PyArg_ParseTuple(args, "i:nice", &increment))
Guido van Rossum775f4da1993-01-09 17:18:52 +00001156 return NULL;
1157 value = nice(increment);
1158 if (value == -1)
1159 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00001160 return PyInt_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00001161}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001162#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001163
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001164
1165static char posix_rename__doc__[] =
1166"rename(old, new) -> None\n\
1167Rename a file or directory.";
1168
Barry Warsaw53699e91996-12-10 23:23:01 +00001169static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001170posix_rename(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001171 PyObject *self;
1172 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001173{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001174 return posix_2str(args, "ss:rename", rename);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001175}
1176
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001177
1178static char posix_rmdir__doc__[] =
1179"rmdir(path) -> None\n\
1180Remove a directory.";
1181
Barry Warsaw53699e91996-12-10 23:23:01 +00001182static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001183posix_rmdir(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001184 PyObject *self;
1185 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001186{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001187 return posix_1str(args, "s:rmdir", rmdir);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001188}
1189
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001190
1191static char posix_stat__doc__[] =
1192"stat(path) -> (mode,ino,dev,nlink,uid,gid,size,atime,mtime,ctime)\n\
1193Perform a stat system call on the given path.";
1194
Barry Warsaw53699e91996-12-10 23:23:01 +00001195static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001196posix_stat(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001197 PyObject *self;
1198 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001199{
Fred Drake699f3522000-06-29 21:12:41 +00001200 return posix_do_stat(self, args, "s:stat", STAT);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001201}
1202
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001203
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001204#ifdef HAVE_SYSTEM
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001205static char posix_system__doc__[] =
1206"system(command) -> exit_status\n\
1207Execute the command (a string) in a subshell.";
1208
Barry Warsaw53699e91996-12-10 23:23:01 +00001209static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001210posix_system(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001211 PyObject *self;
1212 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001213{
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001214 char *command;
Guido van Rossumff4949e1992-08-05 19:58:53 +00001215 long sts;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001216 if (!PyArg_ParseTuple(args, "s:system", &command))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001217 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001218 Py_BEGIN_ALLOW_THREADS
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001219 sts = system(command);
Barry Warsaw53699e91996-12-10 23:23:01 +00001220 Py_END_ALLOW_THREADS
1221 return PyInt_FromLong(sts);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001222}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001223#endif
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001224
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001225
1226static char posix_umask__doc__[] =
1227"umask(new_mask) -> old_mask\n\
1228Set the current numeric umask and return the previous umask.";
1229
Barry Warsaw53699e91996-12-10 23:23:01 +00001230static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001231posix_umask(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001232 PyObject *self;
1233 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001234{
1235 int i;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001236 if (!PyArg_ParseTuple(args, "i:umask", &i))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001237 return NULL;
1238 i = umask(i);
1239 if (i < 0)
1240 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00001241 return PyInt_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001242}
1243
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001244
1245static char posix_unlink__doc__[] =
1246"unlink(path) -> None\n\
1247Remove a file (same as remove(path)).";
1248
1249static char posix_remove__doc__[] =
1250"remove(path) -> None\n\
1251Remove a file (same as unlink(path)).";
1252
Barry Warsaw53699e91996-12-10 23:23:01 +00001253static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001254posix_unlink(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001255 PyObject *self;
1256 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001257{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001258 return posix_1str(args, "s:remove", unlink);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001259}
1260
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001261
Guido van Rossumb6775db1994-08-01 11:34:53 +00001262#ifdef HAVE_UNAME
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001263static char posix_uname__doc__[] =
1264"uname() -> (sysname, nodename, release, version, machine)\n\
1265Return a tuple identifying the current operating system.";
1266
Barry Warsaw53699e91996-12-10 23:23:01 +00001267static PyObject *
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001268posix_uname(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001269 PyObject *self;
1270 PyObject *args;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001271{
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001272 struct utsname u;
Guido van Rossumff4949e1992-08-05 19:58:53 +00001273 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001274 if (!PyArg_ParseTuple(args, ":uname"))
Guido van Rossum50e61dc1992-03-27 17:22:31 +00001275 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001276 Py_BEGIN_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +00001277 res = uname(&u);
Barry Warsaw53699e91996-12-10 23:23:01 +00001278 Py_END_ALLOW_THREADS
Guido van Rossumff4949e1992-08-05 19:58:53 +00001279 if (res < 0)
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001280 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00001281 return Py_BuildValue("(sssss)",
Barry Warsaw43d68b81996-12-19 22:10:44 +00001282 u.sysname,
1283 u.nodename,
1284 u.release,
1285 u.version,
1286 u.machine);
Guido van Rossumc39de5f1992-02-05 11:15:54 +00001287}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001288#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001289
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001290
1291static char posix_utime__doc__[] =
1292"utime(path, (atime, utime)) -> None\n\
Barry Warsaw3cef8562000-05-01 16:17:24 +00001293utime(path, None) -> None\n\
1294Set the access and modified time of the file to the given values. If the\n\
1295second form is used, set the access and modified times to the current time.";
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001296
Barry Warsaw53699e91996-12-10 23:23:01 +00001297static PyObject *
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001298posix_utime(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001299 PyObject *self;
1300 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001301{
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001302 char *path;
Guido van Rossumf8803dd1995-01-26 00:37:45 +00001303 long atime, mtime;
Guido van Rossumff4949e1992-08-05 19:58:53 +00001304 int res;
Barry Warsaw3cef8562000-05-01 16:17:24 +00001305 PyObject* arg;
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001306
Guido van Rossum6d8841c1997-08-14 19:57:39 +00001307/* XXX should define struct utimbuf instead, above */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001308#ifdef HAVE_UTIME_H
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001309 struct utimbuf buf;
1310#define ATIME buf.actime
1311#define MTIME buf.modtime
1312#define UTIME_ARG &buf
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001313#else /* HAVE_UTIME_H */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001314 time_t buf[2];
1315#define ATIME buf[0]
1316#define MTIME buf[1]
1317#define UTIME_ARG buf
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001318#endif /* HAVE_UTIME_H */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001319
Barry Warsaw3cef8562000-05-01 16:17:24 +00001320 if (!PyArg_ParseTuple(args, "sO:utime", &path, &arg))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001321 return NULL;
Barry Warsaw3cef8562000-05-01 16:17:24 +00001322 if (arg == Py_None) {
1323 /* optional time values not given */
1324 Py_BEGIN_ALLOW_THREADS
1325 res = utime(path, NULL);
1326 Py_END_ALLOW_THREADS
1327 }
1328 else if (!PyArg_Parse(arg, "(ll)", &atime, &mtime)) {
1329 PyErr_SetString(PyExc_TypeError,
1330 "Second argument must be a 2-tuple of numbers.");
1331 return NULL;
1332 }
1333 else {
1334 ATIME = atime;
1335 MTIME = mtime;
1336 Py_BEGIN_ALLOW_THREADS
1337 res = utime(path, UTIME_ARG);
1338 Py_END_ALLOW_THREADS
1339 }
Guido van Rossumff4949e1992-08-05 19:58:53 +00001340 if (res < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +00001341 return posix_error_with_filename(path);
Barry Warsaw53699e91996-12-10 23:23:01 +00001342 Py_INCREF(Py_None);
1343 return Py_None;
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00001344#undef UTIME_ARG
1345#undef ATIME
1346#undef MTIME
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001347}
1348
Guido van Rossum85e3b011991-06-03 12:42:10 +00001349
Guido van Rossum3b066191991-06-04 19:40:25 +00001350/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00001351
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001352static char posix__exit__doc__[] =
1353"_exit(status)\n\
1354Exit to the system with specified status, without normal exit processing.";
1355
Barry Warsaw53699e91996-12-10 23:23:01 +00001356static PyObject *
Guido van Rossum85e3b011991-06-03 12:42:10 +00001357posix__exit(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001358 PyObject *self;
1359 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001360{
1361 int sts;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001362 if (!PyArg_ParseTuple(args, "i:_exit", &sts))
Guido van Rossum85e3b011991-06-03 12:42:10 +00001363 return NULL;
1364 _exit(sts);
Guido van Rossuma376cc51996-12-05 23:43:35 +00001365 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00001366}
1367
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001368
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001369#ifdef HAVE_EXECV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001370static char posix_execv__doc__[] =
1371"execv(path, args)\n\
1372Execute an executable path with arguments, replacing current process.\n\
1373\n\
1374 path: path of executable file\n\
1375 args: tuple or list of strings";
1376
Barry Warsaw53699e91996-12-10 23:23:01 +00001377static PyObject *
Guido van Rossum89b33251993-10-22 14:26:06 +00001378posix_execv(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001379 PyObject *self;
1380 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001381{
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001382 char *path;
Barry Warsaw53699e91996-12-10 23:23:01 +00001383 PyObject *argv;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001384 char **argvlist;
1385 int i, argc;
Barry Warsaw53699e91996-12-10 23:23:01 +00001386 PyObject *(*getitem) Py_PROTO((PyObject *, int));
Guido van Rossum85e3b011991-06-03 12:42:10 +00001387
Guido van Rossum89b33251993-10-22 14:26:06 +00001388 /* execv has two arguments: (path, argv), where
Guido van Rossum85e3b011991-06-03 12:42:10 +00001389 argv is a list or tuple of strings. */
1390
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001391 if (!PyArg_ParseTuple(args, "sO:execv", &path, &argv))
Guido van Rossum85e3b011991-06-03 12:42:10 +00001392 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001393 if (PyList_Check(argv)) {
1394 argc = PyList_Size(argv);
1395 getitem = PyList_GetItem;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001396 }
Barry Warsaw53699e91996-12-10 23:23:01 +00001397 else if (PyTuple_Check(argv)) {
1398 argc = PyTuple_Size(argv);
1399 getitem = PyTuple_GetItem;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001400 }
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001401 else {
Guido van Rossum50422b42000-04-26 20:34:28 +00001402 PyErr_SetString(PyExc_TypeError, "argv must be tuple or list");
1403 return NULL;
1404 }
1405
1406 if (argc == 0) {
1407 PyErr_SetString(PyExc_ValueError, "empty argument list");
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001408 return NULL;
1409 }
Guido van Rossum85e3b011991-06-03 12:42:10 +00001410
Barry Warsaw53699e91996-12-10 23:23:01 +00001411 argvlist = PyMem_NEW(char *, argc+1);
Guido van Rossum85e3b011991-06-03 12:42:10 +00001412 if (argvlist == NULL)
1413 return NULL;
1414 for (i = 0; i < argc; i++) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001415 if (!PyArg_Parse((*getitem)(argv, i), "s", &argvlist[i])) {
1416 PyMem_DEL(argvlist);
Guido van Rossum50422b42000-04-26 20:34:28 +00001417 PyErr_SetString(PyExc_TypeError,
1418 "all arguments must be strings");
1419 return NULL;
1420
Guido van Rossum85e3b011991-06-03 12:42:10 +00001421 }
Guido van Rossum85e3b011991-06-03 12:42:10 +00001422 }
1423 argvlist[argc] = NULL;
1424
Guido van Rossumb6775db1994-08-01 11:34:53 +00001425#ifdef BAD_EXEC_PROTOTYPES
1426 execv(path, (const char **) argvlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001427#else /* BAD_EXEC_PROTOTYPES */
Guido van Rossumef0a00e1992-01-27 16:51:30 +00001428 execv(path, argvlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001429#endif /* BAD_EXEC_PROTOTYPES */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001430
Guido van Rossum85e3b011991-06-03 12:42:10 +00001431 /* If we get here it's definitely an error */
1432
Barry Warsaw53699e91996-12-10 23:23:01 +00001433 PyMem_DEL(argvlist);
Guido van Rossum85e3b011991-06-03 12:42:10 +00001434 return posix_error();
1435}
1436
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001437
1438static char posix_execve__doc__[] =
1439"execve(path, args, env)\n\
1440Execute a path with arguments and environment, replacing current process.\n\
1441\n\
1442 path: path of executable file\n\
1443 args: tuple or list of arguments\n\
1444 env: dictonary of strings mapping to strings";
1445
Barry Warsaw53699e91996-12-10 23:23:01 +00001446static PyObject *
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001447posix_execve(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001448 PyObject *self;
1449 PyObject *args;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001450{
1451 char *path;
Barry Warsaw53699e91996-12-10 23:23:01 +00001452 PyObject *argv, *env;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001453 char **argvlist;
1454 char **envlist;
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001455 PyObject *key, *val, *keys=NULL, *vals=NULL;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001456 int i, pos, argc, envc;
Barry Warsaw53699e91996-12-10 23:23:01 +00001457 PyObject *(*getitem) Py_PROTO((PyObject *, int));
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001458
1459 /* execve has three arguments: (path, argv, env), where
1460 argv is a list or tuple of strings and env is a dictionary
1461 like posix.environ. */
1462
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001463 if (!PyArg_ParseTuple(args, "sOO:execve", &path, &argv, &env))
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001464 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001465 if (PyList_Check(argv)) {
1466 argc = PyList_Size(argv);
1467 getitem = PyList_GetItem;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001468 }
Barry Warsaw53699e91996-12-10 23:23:01 +00001469 else if (PyTuple_Check(argv)) {
1470 argc = PyTuple_Size(argv);
1471 getitem = PyTuple_GetItem;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001472 }
1473 else {
Barry Warsaw53699e91996-12-10 23:23:01 +00001474 PyErr_SetString(PyExc_TypeError, "argv must be tuple or list");
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001475 return NULL;
1476 }
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001477 if (!PyMapping_Check(env)) {
1478 PyErr_SetString(PyExc_TypeError, "env must be mapping object");
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001479 return NULL;
1480 }
1481
Guido van Rossum50422b42000-04-26 20:34:28 +00001482 if (argc == 0) {
1483 PyErr_SetString(PyExc_ValueError,
1484 "empty argument list");
1485 return NULL;
1486 }
1487
Barry Warsaw53699e91996-12-10 23:23:01 +00001488 argvlist = PyMem_NEW(char *, argc+1);
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001489 if (argvlist == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001490 PyErr_NoMemory();
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001491 return NULL;
1492 }
1493 for (i = 0; i < argc; i++) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001494 if (!PyArg_Parse((*getitem)(argv, i),
Barry Warsaw43d68b81996-12-19 22:10:44 +00001495 "s;argv must be list of strings",
1496 &argvlist[i]))
1497 {
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001498 goto fail_1;
1499 }
1500 }
1501 argvlist[argc] = NULL;
1502
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001503 i = PyMapping_Length(env);
Barry Warsaw53699e91996-12-10 23:23:01 +00001504 envlist = PyMem_NEW(char *, i + 1);
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001505 if (envlist == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001506 PyErr_NoMemory();
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001507 goto fail_1;
1508 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001509 envc = 0;
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001510 keys = PyMapping_Keys(env);
1511 vals = PyMapping_Values(env);
1512 if (!keys || !vals)
1513 goto fail_2;
1514
1515 for (pos = 0; pos < i; pos++) {
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001516 char *p, *k, *v;
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001517
1518 key = PyList_GetItem(keys, pos);
1519 val = PyList_GetItem(vals, pos);
1520 if (!key || !val)
1521 goto fail_2;
1522
Barry Warsaw53699e91996-12-10 23:23:01 +00001523 if (!PyArg_Parse(key, "s;non-string key in env", &k) ||
Barry Warsaw43d68b81996-12-19 22:10:44 +00001524 !PyArg_Parse(val, "s;non-string value in env", &v))
1525 {
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001526 goto fail_2;
1527 }
Guido van Rossumd48f2521997-12-05 22:19:34 +00001528
1529#if defined(PYOS_OS2)
1530 /* Omit Pseudo-Env Vars that Would Confuse Programs if Passed On */
1531 if (stricmp(k, "BEGINLIBPATH") != 0 && stricmp(k, "ENDLIBPATH") != 0) {
1532#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00001533 p = PyMem_NEW(char, PyString_Size(key)+PyString_Size(val) + 2);
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001534 if (p == NULL) {
Barry Warsaw53699e91996-12-10 23:23:01 +00001535 PyErr_NoMemory();
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001536 goto fail_2;
1537 }
1538 sprintf(p, "%s=%s", k, v);
1539 envlist[envc++] = p;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001540#if defined(PYOS_OS2)
1541 }
1542#endif
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001543 }
1544 envlist[envc] = 0;
1545
Guido van Rossumb6775db1994-08-01 11:34:53 +00001546
1547#ifdef BAD_EXEC_PROTOTYPES
1548 execve(path, (const char **)argvlist, envlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001549#else /* BAD_EXEC_PROTOTYPES */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001550 execve(path, argvlist, envlist);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001551#endif /* BAD_EXEC_PROTOTYPES */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001552
1553 /* If we get here it's definitely an error */
1554
1555 (void) posix_error();
1556
1557 fail_2:
1558 while (--envc >= 0)
Barry Warsaw53699e91996-12-10 23:23:01 +00001559 PyMem_DEL(envlist[envc]);
1560 PyMem_DEL(envlist);
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001561 fail_1:
Barry Warsaw53699e91996-12-10 23:23:01 +00001562 PyMem_DEL(argvlist);
Barry Warsaw5ed19dc1997-01-29 15:08:24 +00001563 Py_XDECREF(vals);
1564 Py_XDECREF(keys);
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001565 return NULL;
1566}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001567#endif /* HAVE_EXECV */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00001568
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001569
Guido van Rossuma1065681999-01-25 23:20:23 +00001570#ifdef HAVE_SPAWNV
1571static char posix_spawnv__doc__[] =
Fred Drakea6dff3e1999-02-01 22:24:40 +00001572"spawnv(mode, path, args)\n\
Guido van Rossuma1065681999-01-25 23:20:23 +00001573Execute an executable path with arguments, replacing current process.\n\
1574\n\
Fred Drakea6dff3e1999-02-01 22:24:40 +00001575 mode: mode of process creation\n\
Guido van Rossuma1065681999-01-25 23:20:23 +00001576 path: path of executable file\n\
1577 args: tuple or list of strings";
1578
1579static PyObject *
1580posix_spawnv(self, args)
1581 PyObject *self;
1582 PyObject *args;
1583{
1584 char *path;
1585 PyObject *argv;
1586 char **argvlist;
1587 int mode, i, argc;
Fred Drake699f3522000-06-29 21:12:41 +00001588 intptr_t spawnval;
Guido van Rossuma1065681999-01-25 23:20:23 +00001589 PyObject *(*getitem) Py_PROTO((PyObject *, int));
1590
1591 /* spawnv has three arguments: (mode, path, argv), where
1592 argv is a list or tuple of strings. */
1593
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001594 if (!PyArg_ParseTuple(args, "isO:spawnv", &mode, &path, &argv))
Guido van Rossuma1065681999-01-25 23:20:23 +00001595 return NULL;
1596 if (PyList_Check(argv)) {
1597 argc = PyList_Size(argv);
1598 getitem = PyList_GetItem;
1599 }
1600 else if (PyTuple_Check(argv)) {
1601 argc = PyTuple_Size(argv);
1602 getitem = PyTuple_GetItem;
1603 }
1604 else {
Fred Drake137507e2000-06-01 02:02:46 +00001605 PyErr_SetString(PyExc_TypeError, "argv must be tuple or list");
Guido van Rossuma1065681999-01-25 23:20:23 +00001606 return NULL;
1607 }
1608
1609 argvlist = PyMem_NEW(char *, argc+1);
1610 if (argvlist == NULL)
1611 return NULL;
1612 for (i = 0; i < argc; i++) {
1613 if (!PyArg_Parse((*getitem)(argv, i), "s", &argvlist[i])) {
1614 PyMem_DEL(argvlist);
Fred Drake137507e2000-06-01 02:02:46 +00001615 PyErr_SetString(PyExc_TypeError,
1616 "all arguments must be strings");
1617 return NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00001618 }
1619 }
1620 argvlist[argc] = NULL;
1621
Guido van Rossum246bc171999-02-01 23:54:31 +00001622 if (mode == _OLD_P_OVERLAY)
1623 mode = _P_OVERLAY;
Fred Drake699f3522000-06-29 21:12:41 +00001624 spawnval = _spawnv(mode, path, argvlist);
Guido van Rossuma1065681999-01-25 23:20:23 +00001625
1626 PyMem_DEL(argvlist);
1627
Fred Drake699f3522000-06-29 21:12:41 +00001628 if (spawnval == -1)
Guido van Rossuma1065681999-01-25 23:20:23 +00001629 return posix_error();
1630 else
Fred Drake699f3522000-06-29 21:12:41 +00001631#if SIZEOF_LONG == SIZE_VOID_P
1632 return Py_BuildValue("l", spawnval);
1633#else
1634 return Py_BuildValue("L", spawnval);
1635#endif
Guido van Rossuma1065681999-01-25 23:20:23 +00001636}
1637
1638
1639static char posix_spawnve__doc__[] =
Fred Drakea6dff3e1999-02-01 22:24:40 +00001640"spawnve(mode, path, args, env)\n\
Guido van Rossuma1065681999-01-25 23:20:23 +00001641Execute a path with arguments and environment, replacing current process.\n\
1642\n\
Fred Drakea6dff3e1999-02-01 22:24:40 +00001643 mode: mode of process creation\n\
Guido van Rossuma1065681999-01-25 23:20:23 +00001644 path: path of executable file\n\
1645 args: tuple or list of arguments\n\
1646 env: dictonary of strings mapping to strings";
1647
1648static PyObject *
1649posix_spawnve(self, args)
1650 PyObject *self;
1651 PyObject *args;
1652{
1653 char *path;
1654 PyObject *argv, *env;
1655 char **argvlist;
1656 char **envlist;
1657 PyObject *key, *val, *keys=NULL, *vals=NULL, *res=NULL;
1658 int mode, i, pos, argc, envc;
Fred Drake699f3522000-06-29 21:12:41 +00001659 intptr_t spawnval;
Guido van Rossuma1065681999-01-25 23:20:23 +00001660 PyObject *(*getitem) Py_PROTO((PyObject *, int));
1661
1662 /* spawnve has four arguments: (mode, path, argv, env), where
1663 argv is a list or tuple of strings and env is a dictionary
1664 like posix.environ. */
1665
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001666 if (!PyArg_ParseTuple(args, "isOO:spawnve", &mode, &path, &argv, &env))
Guido van Rossuma1065681999-01-25 23:20:23 +00001667 return NULL;
1668 if (PyList_Check(argv)) {
1669 argc = PyList_Size(argv);
1670 getitem = PyList_GetItem;
1671 }
1672 else if (PyTuple_Check(argv)) {
1673 argc = PyTuple_Size(argv);
1674 getitem = PyTuple_GetItem;
1675 }
1676 else {
1677 PyErr_SetString(PyExc_TypeError, "argv must be tuple or list");
1678 return NULL;
1679 }
1680 if (!PyMapping_Check(env)) {
1681 PyErr_SetString(PyExc_TypeError, "env must be mapping object");
1682 return NULL;
1683 }
1684
1685 argvlist = PyMem_NEW(char *, argc+1);
1686 if (argvlist == NULL) {
1687 PyErr_NoMemory();
1688 return NULL;
1689 }
1690 for (i = 0; i < argc; i++) {
1691 if (!PyArg_Parse((*getitem)(argv, i),
1692 "s;argv must be list of strings",
1693 &argvlist[i]))
1694 {
1695 goto fail_1;
1696 }
1697 }
1698 argvlist[argc] = NULL;
1699
1700 i = PyMapping_Length(env);
1701 envlist = PyMem_NEW(char *, i + 1);
1702 if (envlist == NULL) {
1703 PyErr_NoMemory();
1704 goto fail_1;
1705 }
1706 envc = 0;
1707 keys = PyMapping_Keys(env);
1708 vals = PyMapping_Values(env);
1709 if (!keys || !vals)
1710 goto fail_2;
1711
1712 for (pos = 0; pos < i; pos++) {
1713 char *p, *k, *v;
1714
1715 key = PyList_GetItem(keys, pos);
1716 val = PyList_GetItem(vals, pos);
1717 if (!key || !val)
1718 goto fail_2;
1719
1720 if (!PyArg_Parse(key, "s;non-string key in env", &k) ||
1721 !PyArg_Parse(val, "s;non-string value in env", &v))
1722 {
1723 goto fail_2;
1724 }
1725 p = PyMem_NEW(char, PyString_Size(key)+PyString_Size(val) + 2);
1726 if (p == NULL) {
1727 PyErr_NoMemory();
1728 goto fail_2;
1729 }
1730 sprintf(p, "%s=%s", k, v);
1731 envlist[envc++] = p;
1732 }
1733 envlist[envc] = 0;
1734
Guido van Rossum246bc171999-02-01 23:54:31 +00001735 if (mode == _OLD_P_OVERLAY)
1736 mode = _P_OVERLAY;
Fred Drake699f3522000-06-29 21:12:41 +00001737 spawnval = _spawnve(mode, path, argvlist, envlist);
1738 if (spawnval == -1)
Guido van Rossuma1065681999-01-25 23:20:23 +00001739 (void) posix_error();
1740 else
Fred Drake699f3522000-06-29 21:12:41 +00001741#if SIZEOF_LONG == SIZE_VOID_P
1742 res = Py_BuildValue("l", spawnval);
1743#else
1744 res = Py_BuildValue("L", spawnval);
1745#endif
Guido van Rossuma1065681999-01-25 23:20:23 +00001746
1747 fail_2:
1748 while (--envc >= 0)
1749 PyMem_DEL(envlist[envc]);
1750 PyMem_DEL(envlist);
1751 fail_1:
1752 PyMem_DEL(argvlist);
1753 Py_XDECREF(vals);
1754 Py_XDECREF(keys);
1755 return res;
1756}
1757#endif /* HAVE_SPAWNV */
1758
1759
Guido van Rossumad0ee831995-03-01 10:34:45 +00001760#ifdef HAVE_FORK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001761static char posix_fork__doc__[] =
1762"fork() -> pid\n\
1763Fork a child process.\n\
1764\n\
1765Return 0 to child process and PID of child to parent process.";
1766
Barry Warsaw53699e91996-12-10 23:23:01 +00001767static PyObject *
Guido van Rossum85e3b011991-06-03 12:42:10 +00001768posix_fork(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001769 PyObject *self;
1770 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001771{
1772 int pid;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001773 if (!PyArg_ParseTuple(args, ":fork"))
Guido van Rossum50e61dc1992-03-27 17:22:31 +00001774 return NULL;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001775 pid = fork();
1776 if (pid == -1)
1777 return posix_error();
Guido van Rossum359bcaa1997-11-14 22:24:28 +00001778 PyOS_AfterFork();
Barry Warsaw53699e91996-12-10 23:23:01 +00001779 return PyInt_FromLong((long)pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00001780}
Guido van Rossumad0ee831995-03-01 10:34:45 +00001781#endif
Guido van Rossum85e3b011991-06-03 12:42:10 +00001782
Fred Drake8cef4cf2000-06-28 16:40:38 +00001783#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY)
1784#ifdef HAVE_PTY_H
1785#include <pty.h>
1786#else
1787#ifdef HAVE_LIBUTIL_H
1788#include <libutil.h>
1789#else
1790/* BSDI does not supply a prototype for the 'openpty' and 'forkpty'
1791 functions, eventhough they are included in libutil. */
1792#include <termios.h>
1793extern int openpty(int *, int *, char *, struct termios *, struct winsize *);
1794extern int forkpty(int *, char *, struct termios *, struct winsize *);
1795#endif /* HAVE_LIBUTIL_H */
1796#endif /* HAVE_PTY_H */
1797#endif /* defined(HAVE_OPENPTY) or defined(HAVE_FORKPTY) */
1798
1799#ifdef HAVE_OPENPTY
1800static char posix_openpty__doc__[] =
1801"openpty() -> (master_fd, slave_fd)\n\
1802Open a pseudo-terminal, returning open fd's for both master and slave end.\n";
1803
1804static PyObject *
1805posix_openpty(self, args)
1806 PyObject *self;
1807 PyObject *args;
1808{
1809 int master_fd, slave_fd;
1810 if (!PyArg_ParseTuple(args, ":openpty"))
1811 return NULL;
1812 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
1813 return posix_error();
1814 return Py_BuildValue("(ii)", master_fd, slave_fd);
1815}
1816#endif
1817
1818#ifdef HAVE_FORKPTY
1819static char posix_forkpty__doc__[] =
1820"forkpty() -> (pid, master_fd)\n\
1821Fork a new process with a new pseudo-terminal as controlling tty.\n\n\
1822Like fork(), return 0 as pid to child process, and PID of child to parent.\n\
1823To both, return fd of newly opened pseudo-terminal.\n";
1824
1825static PyObject *
1826posix_forkpty(self, args)
1827 PyObject *self;
1828 PyObject *args;
1829{
1830 int master_fd, pid;
1831
1832 if (!PyArg_ParseTuple(args, ":forkpty"))
1833 return NULL;
1834 pid = forkpty(&master_fd, NULL, NULL, NULL);
1835 if (pid == -1)
1836 return posix_error();
1837 PyOS_AfterFork();
1838 return Py_BuildValue("(ii)", pid, master_fd);
1839}
1840#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001841
Guido van Rossumad0ee831995-03-01 10:34:45 +00001842#ifdef HAVE_GETEGID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001843static char posix_getegid__doc__[] =
1844"getegid() -> egid\n\
1845Return the current process's effective group id.";
1846
Barry Warsaw53699e91996-12-10 23:23:01 +00001847static PyObject *
Guido van Rossum46003ff1992-05-15 11:05:24 +00001848posix_getegid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001849 PyObject *self;
1850 PyObject *args;
Guido van Rossum46003ff1992-05-15 11:05:24 +00001851{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001852 if (!PyArg_ParseTuple(args, ":getegid"))
Guido van Rossum46003ff1992-05-15 11:05:24 +00001853 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001854 return PyInt_FromLong((long)getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00001855}
Guido van Rossumad0ee831995-03-01 10:34:45 +00001856#endif
Guido van Rossum46003ff1992-05-15 11:05:24 +00001857
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001858
Guido van Rossumad0ee831995-03-01 10:34:45 +00001859#ifdef HAVE_GETEUID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001860static char posix_geteuid__doc__[] =
1861"geteuid() -> euid\n\
1862Return the current process's effective user id.";
1863
Barry Warsaw53699e91996-12-10 23:23:01 +00001864static PyObject *
Guido van Rossum46003ff1992-05-15 11:05:24 +00001865posix_geteuid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001866 PyObject *self;
1867 PyObject *args;
Guido van Rossum46003ff1992-05-15 11:05:24 +00001868{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001869 if (!PyArg_ParseTuple(args, ":geteuid"))
Guido van Rossum46003ff1992-05-15 11:05:24 +00001870 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001871 return PyInt_FromLong((long)geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00001872}
Guido van Rossumad0ee831995-03-01 10:34:45 +00001873#endif
Guido van Rossum46003ff1992-05-15 11:05:24 +00001874
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001875
Guido van Rossumad0ee831995-03-01 10:34:45 +00001876#ifdef HAVE_GETGID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001877static char posix_getgid__doc__[] =
1878"getgid() -> gid\n\
1879Return the current process's group id.";
1880
Barry Warsaw53699e91996-12-10 23:23:01 +00001881static PyObject *
Guido van Rossum46003ff1992-05-15 11:05:24 +00001882posix_getgid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001883 PyObject *self;
1884 PyObject *args;
Guido van Rossum46003ff1992-05-15 11:05:24 +00001885{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001886 if (!PyArg_ParseTuple(args, ":getgid"))
Guido van Rossum46003ff1992-05-15 11:05:24 +00001887 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001888 return PyInt_FromLong((long)getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00001889}
Guido van Rossumad0ee831995-03-01 10:34:45 +00001890#endif
Guido van Rossum46003ff1992-05-15 11:05:24 +00001891
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001892
1893static char posix_getpid__doc__[] =
1894"getpid() -> pid\n\
1895Return the current process id";
1896
Barry Warsaw53699e91996-12-10 23:23:01 +00001897static PyObject *
Guido van Rossum85e3b011991-06-03 12:42:10 +00001898posix_getpid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001899 PyObject *self;
1900 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00001901{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001902 if (!PyArg_ParseTuple(args, ":getpid"))
Guido van Rossum85e3b011991-06-03 12:42:10 +00001903 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00001904 return PyInt_FromLong((long)getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00001905}
1906
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001907
Fred Drakec9680921999-12-13 16:37:25 +00001908#ifdef HAVE_GETGROUPS
1909static char posix_getgroups__doc__[] = "\
1910getgroups() -> list of group IDs\n\
1911Return list of supplemental group IDs for the process.";
1912
1913static PyObject *
1914posix_getgroups(self, args)
1915 PyObject *self;
1916 PyObject *args;
1917{
1918 PyObject *result = NULL;
1919
1920 if (PyArg_ParseTuple(args, ":getgroups")) {
1921#ifdef NGROUPS_MAX
1922#define MAX_GROUPS NGROUPS_MAX
1923#else
1924 /* defined to be 16 on Solaris7, so this should be a small number */
1925#define MAX_GROUPS 64
1926#endif
1927 gid_t grouplist[MAX_GROUPS];
1928 int n;
1929
1930 n = getgroups(MAX_GROUPS, grouplist);
1931 if (n < 0)
1932 posix_error();
1933 else {
1934 result = PyList_New(n);
1935 if (result != NULL) {
1936 PyObject *o;
1937 int i;
1938 for (i = 0; i < n; ++i) {
1939 o = PyInt_FromLong((long)grouplist[i]);
1940 if (o == NULL) {
1941 Py_DECREF(result);
1942 result = NULL;
1943 break;
1944 }
1945 PyList_SET_ITEM(result, i, o);
1946 }
1947 }
1948 }
1949 }
1950 return result;
1951}
1952#endif
1953
Guido van Rossumb6775db1994-08-01 11:34:53 +00001954#ifdef HAVE_GETPGRP
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001955static char posix_getpgrp__doc__[] =
1956"getpgrp() -> pgrp\n\
1957Return the current process group id.";
1958
Barry Warsaw53699e91996-12-10 23:23:01 +00001959static PyObject *
Guido van Rossum04814471991-06-04 20:23:49 +00001960posix_getpgrp(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001961 PyObject *self;
1962 PyObject *args;
Guido van Rossum04814471991-06-04 20:23:49 +00001963{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001964 if (!PyArg_ParseTuple(args, ":getpgrp"))
Guido van Rossum04814471991-06-04 20:23:49 +00001965 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00001966#ifdef GETPGRP_HAVE_ARG
Barry Warsaw53699e91996-12-10 23:23:01 +00001967 return PyInt_FromLong((long)getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001968#else /* GETPGRP_HAVE_ARG */
Barry Warsaw53699e91996-12-10 23:23:01 +00001969 return PyInt_FromLong((long)getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00001970#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00001971}
Guido van Rossumb6775db1994-08-01 11:34:53 +00001972#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00001973
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001974
Guido van Rossumb6775db1994-08-01 11:34:53 +00001975#ifdef HAVE_SETPGRP
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00001976static char posix_setpgrp__doc__[] =
1977"setpgrp() -> None\n\
1978Make this process a session leader.";
1979
Barry Warsaw53699e91996-12-10 23:23:01 +00001980static PyObject *
Guido van Rossumc2670a01992-09-13 20:07:29 +00001981posix_setpgrp(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00001982 PyObject *self;
1983 PyObject *args;
Guido van Rossumc2670a01992-09-13 20:07:29 +00001984{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00001985 if (!PyArg_ParseTuple(args, ":setpgrp"))
Guido van Rossumc2670a01992-09-13 20:07:29 +00001986 return NULL;
Guido van Rossum64933891994-10-20 21:56:42 +00001987#ifdef SETPGRP_HAVE_ARG
Guido van Rossumc2670a01992-09-13 20:07:29 +00001988 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00001989#else /* SETPGRP_HAVE_ARG */
Guido van Rossumb6775db1994-08-01 11:34:53 +00001990 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00001991#endif /* SETPGRP_HAVE_ARG */
Guido van Rossum687dd131993-05-17 08:34:16 +00001992 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00001993 Py_INCREF(Py_None);
1994 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00001995}
1996
Guido van Rossumb6775db1994-08-01 11:34:53 +00001997#endif /* HAVE_SETPGRP */
1998
Guido van Rossumad0ee831995-03-01 10:34:45 +00001999#ifdef HAVE_GETPPID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002000static char posix_getppid__doc__[] =
2001"getppid() -> ppid\n\
2002Return the parent's process id.";
2003
Barry Warsaw53699e91996-12-10 23:23:01 +00002004static PyObject *
Guido van Rossum85e3b011991-06-03 12:42:10 +00002005posix_getppid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002006 PyObject *self;
2007 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00002008{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002009 if (!PyArg_ParseTuple(args, ":getppid"))
Guido van Rossum85e3b011991-06-03 12:42:10 +00002010 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002011 return PyInt_FromLong((long)getppid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00002012}
Guido van Rossumad0ee831995-03-01 10:34:45 +00002013#endif
Guido van Rossum85e3b011991-06-03 12:42:10 +00002014
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002015
Fred Drake12c6e2d1999-12-14 21:25:03 +00002016#ifdef HAVE_GETLOGIN
2017static char posix_getlogin__doc__[] = "\
2018getlogin() -> string\n\
2019Return the actual login name.";
2020
2021static PyObject *
2022posix_getlogin(self, args)
2023 PyObject *self;
2024 PyObject *args;
2025{
2026 PyObject *result = NULL;
2027
2028 if (PyArg_ParseTuple(args, ":getlogin")) {
2029 char *name = getlogin();
2030
2031 if (name == NULL)
2032 posix_error();
2033 else
2034 result = PyString_FromString(name);
2035 }
2036 return result;
2037}
2038#endif
2039
Guido van Rossumad0ee831995-03-01 10:34:45 +00002040#ifdef HAVE_GETUID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002041static char posix_getuid__doc__[] =
2042"getuid() -> uid\n\
2043Return the current process's user id.";
2044
Barry Warsaw53699e91996-12-10 23:23:01 +00002045static PyObject *
Guido van Rossum46003ff1992-05-15 11:05:24 +00002046posix_getuid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002047 PyObject *self;
2048 PyObject *args;
Guido van Rossum46003ff1992-05-15 11:05:24 +00002049{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002050 if (!PyArg_ParseTuple(args, ":getuid"))
Guido van Rossum46003ff1992-05-15 11:05:24 +00002051 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002052 return PyInt_FromLong((long)getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00002053}
Guido van Rossumad0ee831995-03-01 10:34:45 +00002054#endif
Guido van Rossum46003ff1992-05-15 11:05:24 +00002055
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002056
Guido van Rossumad0ee831995-03-01 10:34:45 +00002057#ifdef HAVE_KILL
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002058static char posix_kill__doc__[] =
2059"kill(pid, sig) -> None\n\
2060Kill a process with a signal.";
2061
Barry Warsaw53699e91996-12-10 23:23:01 +00002062static PyObject *
Guido van Rossum85e3b011991-06-03 12:42:10 +00002063posix_kill(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002064 PyObject *self;
2065 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00002066{
2067 int pid, sig;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002068 if (!PyArg_ParseTuple(args, "ii:kill", &pid, &sig))
Guido van Rossum85e3b011991-06-03 12:42:10 +00002069 return NULL;
Guido van Rossumd48f2521997-12-05 22:19:34 +00002070#if defined(PYOS_OS2)
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002071 if (sig == XCPT_SIGNAL_INTR || sig == XCPT_SIGNAL_BREAK) {
2072 APIRET rc;
2073 if ((rc = DosSendSignalException(pid, sig)) != NO_ERROR)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002074 return os2_error(rc);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002075
2076 } else if (sig == XCPT_SIGNAL_KILLPROC) {
2077 APIRET rc;
2078 if ((rc = DosKillProcess(DKP_PROCESS, pid)) != NO_ERROR)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002079 return os2_error(rc);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002080
2081 } else
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002082 return NULL; /* Unrecognized Signal Requested */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002083#else
Guido van Rossum85e3b011991-06-03 12:42:10 +00002084 if (kill(pid, sig) == -1)
2085 return posix_error();
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002086#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00002087 Py_INCREF(Py_None);
2088 return Py_None;
Guido van Rossum85e3b011991-06-03 12:42:10 +00002089}
Guido van Rossumad0ee831995-03-01 10:34:45 +00002090#endif
Guido van Rossum85e3b011991-06-03 12:42:10 +00002091
Guido van Rossumc0125471996-06-28 18:55:32 +00002092#ifdef HAVE_PLOCK
2093
2094#ifdef HAVE_SYS_LOCK_H
2095#include <sys/lock.h>
2096#endif
2097
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002098static char posix_plock__doc__[] =
2099"plock(op) -> None\n\
2100Lock program segments into memory.";
2101
Barry Warsaw53699e91996-12-10 23:23:01 +00002102static PyObject *
Guido van Rossumc0125471996-06-28 18:55:32 +00002103posix_plock(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002104 PyObject *self;
2105 PyObject *args;
Guido van Rossumc0125471996-06-28 18:55:32 +00002106{
2107 int op;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002108 if (!PyArg_ParseTuple(args, "i:plock", &op))
Guido van Rossumc0125471996-06-28 18:55:32 +00002109 return NULL;
2110 if (plock(op) == -1)
2111 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002112 Py_INCREF(Py_None);
2113 return Py_None;
Guido van Rossumc0125471996-06-28 18:55:32 +00002114}
2115#endif
2116
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002117
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002118#ifdef HAVE_POPEN
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002119static char posix_popen__doc__[] =
2120"popen(command [, mode='r' [, bufsize]]) -> pipe\n\
2121Open a pipe to/from a command returning a file object.";
2122
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002123#if defined(PYOS_OS2)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002124static int
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002125async_system(const char *command)
2126{
2127 char *p, errormsg[256], args[1024];
2128 RESULTCODES rcodes;
2129 APIRET rc;
2130 char *shell = getenv("COMSPEC");
2131 if (!shell)
2132 shell = "cmd";
2133
2134 strcpy(args, shell);
2135 p = &args[ strlen(args)+1 ];
2136 strcpy(p, "/c ");
2137 strcat(p, command);
2138 p += strlen(p) + 1;
2139 *p = '\0';
2140
2141 rc = DosExecPgm(errormsg, sizeof(errormsg),
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002142 EXEC_ASYNC, /* Execute Async w/o Wait for Results */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002143 args,
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002144 NULL, /* Inherit Parent's Environment */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002145 &rcodes, shell);
2146 return rc;
2147}
2148
Guido van Rossumd48f2521997-12-05 22:19:34 +00002149static FILE *
2150popen(const char *command, const char *mode, int pipesize, int *err)
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002151{
2152 HFILE rhan, whan;
2153 FILE *retfd = NULL;
2154 APIRET rc = DosCreatePipe(&rhan, &whan, pipesize);
2155
Guido van Rossumd48f2521997-12-05 22:19:34 +00002156 if (rc != NO_ERROR) {
2157 *err = rc;
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002158 return NULL; /* ERROR - Unable to Create Anon Pipe */
Guido van Rossumd48f2521997-12-05 22:19:34 +00002159 }
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002160
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002161 if (strchr(mode, 'r') != NULL) { /* Treat Command as a Data Source */
2162 int oldfd = dup(1); /* Save STDOUT Handle in Another Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002163
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002164 DosEnterCritSec(); /* Stop Other Threads While Changing Handles */
2165 close(1); /* Make STDOUT Available for Reallocation */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002166
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002167 if (dup2(whan, 1) == 0) { /* Connect STDOUT to Pipe Write Side */
2168 DosClose(whan); /* Close Now-Unused Pipe Write Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002169
2170 if (async_system(command) == NO_ERROR)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002171 retfd = fdopen(rhan, mode); /* And Return Pipe Read Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002172 }
2173
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002174 dup2(oldfd, 1); /* Reconnect STDOUT to Original Handle */
2175 DosExitCritSec(); /* Now Allow Other Threads to Run */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002176
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002177 close(oldfd); /* And Close Saved STDOUT Handle */
2178 return retfd; /* Return fd of Pipe or NULL if Error */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002179
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002180 } else if (strchr(mode, 'w')) { /* Treat Command as a Data Sink */
2181 int oldfd = dup(0); /* Save STDIN Handle in Another Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002182
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002183 DosEnterCritSec(); /* Stop Other Threads While Changing Handles */
2184 close(0); /* Make STDIN Available for Reallocation */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002185
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002186 if (dup2(rhan, 0) == 0) { /* Connect STDIN to Pipe Read Side */
2187 DosClose(rhan); /* Close Now-Unused Pipe Read Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002188
2189 if (async_system(command) == NO_ERROR)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002190 retfd = fdopen(whan, mode); /* And Return Pipe Write Handle */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002191 }
2192
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002193 dup2(oldfd, 0); /* Reconnect STDIN to Original Handle */
2194 DosExitCritSec(); /* Now Allow Other Threads to Run */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002195
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002196 close(oldfd); /* And Close Saved STDIN Handle */
2197 return retfd; /* Return fd of Pipe or NULL if Error */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002198
Guido van Rossumd48f2521997-12-05 22:19:34 +00002199 } else {
2200 *err = ERROR_INVALID_ACCESS;
Guido van Rossumc5a0f531997-12-02 20:36:02 +00002201 return NULL; /* ERROR - Invalid Mode (Neither Read nor Write) */
Guido van Rossumd48f2521997-12-05 22:19:34 +00002202 }
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002203}
2204
2205static PyObject *
2206posix_popen(self, args)
2207 PyObject *self;
2208 PyObject *args;
2209{
2210 char *name;
2211 char *mode = "r";
Guido van Rossumd48f2521997-12-05 22:19:34 +00002212 int err, bufsize = -1;
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002213 FILE *fp;
2214 PyObject *f;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002215 if (!PyArg_ParseTuple(args, "s|si:popen", &name, &mode, &bufsize))
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002216 return NULL;
2217 Py_BEGIN_ALLOW_THREADS
Guido van Rossumd48f2521997-12-05 22:19:34 +00002218 fp = popen(name, mode, (bufsize > 0) ? bufsize : 4096, &err);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002219 Py_END_ALLOW_THREADS
2220 if (fp == NULL)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002221 return os2_error(err);
2222
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002223 f = PyFile_FromFile(fp, name, mode, fclose);
2224 if (f != NULL)
2225 PyFile_SetBufSize(f, bufsize);
2226 return f;
2227}
2228
2229#else
Barry Warsaw53699e91996-12-10 23:23:01 +00002230static PyObject *
Guido van Rossum3b066191991-06-04 19:40:25 +00002231posix_popen(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002232 PyObject *self;
2233 PyObject *args;
Guido van Rossum3b066191991-06-04 19:40:25 +00002234{
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002235 char *name;
2236 char *mode = "r";
2237 int bufsize = -1;
Guido van Rossum3b066191991-06-04 19:40:25 +00002238 FILE *fp;
Barry Warsaw53699e91996-12-10 23:23:01 +00002239 PyObject *f;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002240 if (!PyArg_ParseTuple(args, "s|si:popen", &name, &mode, &bufsize))
Guido van Rossum3b066191991-06-04 19:40:25 +00002241 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002242 Py_BEGIN_ALLOW_THREADS
Guido van Rossumef0a00e1992-01-27 16:51:30 +00002243 fp = popen(name, mode);
Barry Warsaw53699e91996-12-10 23:23:01 +00002244 Py_END_ALLOW_THREADS
Guido van Rossum3b066191991-06-04 19:40:25 +00002245 if (fp == NULL)
2246 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002247 f = PyFile_FromFile(fp, name, mode, pclose);
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002248 if (f != NULL)
Barry Warsaw53699e91996-12-10 23:23:01 +00002249 PyFile_SetBufSize(f, bufsize);
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002250 return f;
Guido van Rossum3b066191991-06-04 19:40:25 +00002251}
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002252#endif
2253
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002254#endif /* HAVE_POPEN */
Guido van Rossum3b066191991-06-04 19:40:25 +00002255
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002256
Guido van Rossumb6775db1994-08-01 11:34:53 +00002257#ifdef HAVE_SETUID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002258static char posix_setuid__doc__[] =
2259"setuid(uid) -> None\n\
2260Set the current process's user id.";
Barry Warsaw53699e91996-12-10 23:23:01 +00002261static PyObject *
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002262posix_setuid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002263 PyObject *self;
2264 PyObject *args;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002265{
2266 int uid;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002267 if (!PyArg_ParseTuple(args, "i:setuid", &uid))
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002268 return NULL;
2269 if (setuid(uid) < 0)
2270 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002271 Py_INCREF(Py_None);
2272 return Py_None;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002273}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00002274#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002275
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002276
Guido van Rossumb6775db1994-08-01 11:34:53 +00002277#ifdef HAVE_SETGID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002278static char posix_setgid__doc__[] =
2279"setgid(gid) -> None\n\
2280Set the current process's group id.";
2281
Barry Warsaw53699e91996-12-10 23:23:01 +00002282static PyObject *
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002283posix_setgid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002284 PyObject *self;
2285 PyObject *args;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002286{
2287 int gid;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002288 if (!PyArg_ParseTuple(args, "i:setgid", &gid))
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002289 return NULL;
2290 if (setgid(gid) < 0)
2291 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002292 Py_INCREF(Py_None);
2293 return Py_None;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002294}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00002295#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00002296
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002297
Guido van Rossumb6775db1994-08-01 11:34:53 +00002298#ifdef HAVE_WAITPID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002299static char posix_waitpid__doc__[] =
2300"waitpid(pid, options) -> (pid, status)\n\
2301Wait for completion of a give child process.";
2302
Barry Warsaw53699e91996-12-10 23:23:01 +00002303static PyObject *
Guido van Rossum21803b81992-08-09 12:55:27 +00002304posix_waitpid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002305 PyObject *self;
2306 PyObject *args;
Guido van Rossum85e3b011991-06-03 12:42:10 +00002307{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002308 int pid, options;
2309#ifdef UNION_WAIT
2310 union wait status;
2311#define status_i (status.w_status)
2312#else
2313 int status;
2314#define status_i status
2315#endif
2316 status_i = 0;
2317
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002318 if (!PyArg_ParseTuple(args, "ii:waitpid", &pid, &options))
Guido van Rossum21803b81992-08-09 12:55:27 +00002319 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002320 Py_BEGIN_ALLOW_THREADS
Guido van Rossume6a3aa61999-02-01 16:15:30 +00002321#ifdef NeXT
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002322 pid = wait4(pid, &status, options, NULL);
Guido van Rossume6a3aa61999-02-01 16:15:30 +00002323#else
2324 pid = waitpid(pid, &status, options);
2325#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00002326 Py_END_ALLOW_THREADS
Guido van Rossum85e3b011991-06-03 12:42:10 +00002327 if (pid == -1)
2328 return posix_error();
Guido van Rossum21803b81992-08-09 12:55:27 +00002329 else
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002330 return Py_BuildValue("ii", pid, status_i);
Guido van Rossum21803b81992-08-09 12:55:27 +00002331}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002332#endif /* HAVE_WAITPID */
Guido van Rossum21803b81992-08-09 12:55:27 +00002333
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002334
Guido van Rossumad0ee831995-03-01 10:34:45 +00002335#ifdef HAVE_WAIT
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002336static char posix_wait__doc__[] =
2337"wait() -> (pid, status)\n\
2338Wait for completion of a child process.";
2339
Barry Warsaw53699e91996-12-10 23:23:01 +00002340static PyObject *
Guido van Rossum21803b81992-08-09 12:55:27 +00002341posix_wait(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002342 PyObject *self;
2343 PyObject *args;
Guido van Rossum21803b81992-08-09 12:55:27 +00002344{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002345 int pid;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002346#ifdef UNION_WAIT
2347 union wait status;
2348#define status_i (status.w_status)
Guido van Rossumb9f866c1997-05-22 15:12:39 +00002349#else
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002350 int status;
2351#define status_i status
Guido van Rossumb9f866c1997-05-22 15:12:39 +00002352#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002353 if (!PyArg_ParseTuple(args, ":wait"))
2354 return NULL;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002355 status_i = 0;
2356 Py_BEGIN_ALLOW_THREADS
2357 pid = wait(&status);
Barry Warsaw53699e91996-12-10 23:23:01 +00002358 Py_END_ALLOW_THREADS
Guido van Rossum21803b81992-08-09 12:55:27 +00002359 if (pid == -1)
2360 return posix_error();
2361 else
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00002362 return Py_BuildValue("ii", pid, status_i);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002363#undef status_i
Guido van Rossum85e3b011991-06-03 12:42:10 +00002364}
Guido van Rossumad0ee831995-03-01 10:34:45 +00002365#endif
Guido van Rossum85e3b011991-06-03 12:42:10 +00002366
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002367
2368static char posix_lstat__doc__[] =
2369"lstat(path) -> (mode,ino,dev,nlink,uid,gid,size,atime,mtime,ctime)\n\
2370Like stat(path), but do not follow symbolic links.";
2371
Barry Warsaw53699e91996-12-10 23:23:01 +00002372static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002373posix_lstat(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002374 PyObject *self;
2375 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002376{
Guido van Rossumb6775db1994-08-01 11:34:53 +00002377#ifdef HAVE_LSTAT
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002378 return posix_do_stat(self, args, "s:lstat", lstat);
Guido van Rossumb6775db1994-08-01 11:34:53 +00002379#else /* !HAVE_LSTAT */
Fred Drake699f3522000-06-29 21:12:41 +00002380 return posix_do_stat(self, args, "s:lstat", STAT);
Guido van Rossumb6775db1994-08-01 11:34:53 +00002381#endif /* !HAVE_LSTAT */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002382}
2383
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002384
Guido van Rossumb6775db1994-08-01 11:34:53 +00002385#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002386static char posix_readlink__doc__[] =
2387"readlink(path) -> path\n\
2388Return a string representing the path to which the symbolic link points.";
2389
Barry Warsaw53699e91996-12-10 23:23:01 +00002390static PyObject *
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002391posix_readlink(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002392 PyObject *self;
2393 PyObject *args;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002394{
Guido van Rossumb6775db1994-08-01 11:34:53 +00002395 char buf[MAXPATHLEN];
Guido van Rossumef0a00e1992-01-27 16:51:30 +00002396 char *path;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002397 int n;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002398 if (!PyArg_ParseTuple(args, "s:readlink", &path))
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002399 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002400 Py_BEGIN_ALLOW_THREADS
Guido van Rossum50e61dc1992-03-27 17:22:31 +00002401 n = readlink(path, buf, (int) sizeof buf);
Barry Warsaw53699e91996-12-10 23:23:01 +00002402 Py_END_ALLOW_THREADS
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002403 if (n < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +00002404 return posix_error_with_filename(path);
Barry Warsaw53699e91996-12-10 23:23:01 +00002405 return PyString_FromStringAndSize(buf, n);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002406}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002407#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002408
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002409
Guido van Rossumb6775db1994-08-01 11:34:53 +00002410#ifdef HAVE_SYMLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002411static char posix_symlink__doc__[] =
2412"symlink(src, dst) -> None\n\
2413Create a symbolic link.";
2414
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002415static PyObject *
2416posix_symlink(self, args)
2417 PyObject *self;
2418 PyObject *args;
2419{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002420 return posix_2str(args, "ss:symlink", symlink);
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002421}
2422#endif /* HAVE_SYMLINK */
2423
2424
2425#ifdef HAVE_TIMES
2426#ifndef HZ
2427#define HZ 60 /* Universal constant :-) */
2428#endif /* HZ */
2429
Guido van Rossumd48f2521997-12-05 22:19:34 +00002430#if defined(PYCC_VACPP) && defined(PYOS_OS2)
2431static long
2432system_uptime()
2433{
2434 ULONG value = 0;
2435
2436 Py_BEGIN_ALLOW_THREADS
2437 DosQuerySysInfo(QSV_MS_COUNT, QSV_MS_COUNT, &value, sizeof(value));
2438 Py_END_ALLOW_THREADS
2439
2440 return value;
2441}
2442
2443static PyObject *
2444posix_times(self, args)
2445 PyObject *self;
2446 PyObject *args;
2447{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002448 if (!PyArg_ParseTuple(args, ":times"))
Guido van Rossumd48f2521997-12-05 22:19:34 +00002449 return NULL;
2450
2451 /* Currently Only Uptime is Provided -- Others Later */
2452 return Py_BuildValue("ddddd",
2453 (double)0 /* t.tms_utime / HZ */,
2454 (double)0 /* t.tms_stime / HZ */,
2455 (double)0 /* t.tms_cutime / HZ */,
2456 (double)0 /* t.tms_cstime / HZ */,
2457 (double)system_uptime() / 1000);
2458}
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002459#else /* not OS2 */
Barry Warsaw53699e91996-12-10 23:23:01 +00002460static PyObject *
Guido van Rossum22db57e1992-04-05 14:25:30 +00002461posix_times(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002462 PyObject *self;
2463 PyObject *args;
Guido van Rossum22db57e1992-04-05 14:25:30 +00002464{
2465 struct tms t;
2466 clock_t c;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002467 if (!PyArg_ParseTuple(args, ":times"))
Guido van Rossum22db57e1992-04-05 14:25:30 +00002468 return NULL;
2469 errno = 0;
2470 c = times(&t);
Guido van Rossum687dd131993-05-17 08:34:16 +00002471 if (c == (clock_t) -1)
2472 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002473 return Py_BuildValue("ddddd",
Barry Warsaw43d68b81996-12-19 22:10:44 +00002474 (double)t.tms_utime / HZ,
2475 (double)t.tms_stime / HZ,
2476 (double)t.tms_cutime / HZ,
2477 (double)t.tms_cstime / HZ,
2478 (double)c / HZ);
Guido van Rossum22db57e1992-04-05 14:25:30 +00002479}
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002480#endif /* not OS2 */
Guido van Rossumb6775db1994-08-01 11:34:53 +00002481#endif /* HAVE_TIMES */
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002482
2483
Guido van Rossum87755a21996-09-07 00:59:43 +00002484#ifdef MS_WIN32
Guido van Rossum14ed0b21994-09-29 09:50:09 +00002485#define HAVE_TIMES /* so the method table will pick it up */
Barry Warsaw53699e91996-12-10 23:23:01 +00002486static PyObject *
Guido van Rossum14ed0b21994-09-29 09:50:09 +00002487posix_times(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002488 PyObject *self;
2489 PyObject *args;
Guido van Rossum14ed0b21994-09-29 09:50:09 +00002490{
2491 FILETIME create, exit, kernel, user;
2492 HANDLE hProc;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002493 if (!PyArg_ParseTuple(args, ":times"))
Guido van Rossum14ed0b21994-09-29 09:50:09 +00002494 return NULL;
2495 hProc = GetCurrentProcess();
Guido van Rossumb8c3cbd1999-02-16 14:37:28 +00002496 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
2497 /* The fields of a FILETIME structure are the hi and lo part
2498 of a 64-bit value expressed in 100 nanosecond units.
2499 1e7 is one second in such units; 1e-7 the inverse.
2500 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
2501 */
Barry Warsaw53699e91996-12-10 23:23:01 +00002502 return Py_BuildValue(
2503 "ddddd",
Guido van Rossumb8c3cbd1999-02-16 14:37:28 +00002504 (double)(kernel.dwHighDateTime*429.4967296 +
2505 kernel.dwLowDateTime*1e-7),
2506 (double)(user.dwHighDateTime*429.4967296 +
2507 user.dwLowDateTime*1e-7),
Barry Warsaw53699e91996-12-10 23:23:01 +00002508 (double)0,
2509 (double)0,
2510 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +00002511}
Guido van Rossum8d665e61996-06-26 18:22:49 +00002512#endif /* MS_WIN32 */
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002513
2514#ifdef HAVE_TIMES
Roger E. Masse0318fd61997-06-05 22:07:58 +00002515static char posix_times__doc__[] =
2516"times() -> (utime, stime, cutime, cstime, elapsed_time)\n\
2517Return a tuple of floating point numbers indicating process times.";
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00002518#endif
Guido van Rossum22db57e1992-04-05 14:25:30 +00002519
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002520
Guido van Rossumb6775db1994-08-01 11:34:53 +00002521#ifdef HAVE_SETSID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002522static char posix_setsid__doc__[] =
2523"setsid() -> None\n\
2524Call the system call setsid().";
2525
Barry Warsaw53699e91996-12-10 23:23:01 +00002526static PyObject *
Guido van Rossumc2670a01992-09-13 20:07:29 +00002527posix_setsid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002528 PyObject *self;
2529 PyObject *args;
Guido van Rossumc2670a01992-09-13 20:07:29 +00002530{
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002531 if (!PyArg_ParseTuple(args, ":setsid"))
Guido van Rossumc2670a01992-09-13 20:07:29 +00002532 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00002533 if (setsid() < 0)
2534 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002535 Py_INCREF(Py_None);
2536 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00002537}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002538#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00002539
Guido van Rossumb6775db1994-08-01 11:34:53 +00002540#ifdef HAVE_SETPGID
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002541static char posix_setpgid__doc__[] =
2542"setpgid(pid, pgrp) -> None\n\
2543Call the system call setpgid().";
2544
Barry Warsaw53699e91996-12-10 23:23:01 +00002545static PyObject *
Guido van Rossumc2670a01992-09-13 20:07:29 +00002546posix_setpgid(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002547 PyObject *self;
2548 PyObject *args;
Guido van Rossumc2670a01992-09-13 20:07:29 +00002549{
2550 int pid, pgrp;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002551 if (!PyArg_ParseTuple(args, "ii:setpgid", &pid, &pgrp))
Guido van Rossumc2670a01992-09-13 20:07:29 +00002552 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00002553 if (setpgid(pid, pgrp) < 0)
2554 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002555 Py_INCREF(Py_None);
2556 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00002557}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002558#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00002559
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002560
Guido van Rossumb6775db1994-08-01 11:34:53 +00002561#ifdef HAVE_TCGETPGRP
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002562static char posix_tcgetpgrp__doc__[] =
2563"tcgetpgrp(fd) -> pgid\n\
2564Return the process group associated with the terminal given by a fd.";
2565
Barry Warsaw53699e91996-12-10 23:23:01 +00002566static PyObject *
Guido van Rossum7066dd71992-09-17 17:54:56 +00002567posix_tcgetpgrp(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002568 PyObject *self;
2569 PyObject *args;
Guido van Rossum7066dd71992-09-17 17:54:56 +00002570{
2571 int fd, pgid;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002572 if (!PyArg_ParseTuple(args, "i:tcgetpgrp", &fd))
Guido van Rossum7066dd71992-09-17 17:54:56 +00002573 return NULL;
2574 pgid = tcgetpgrp(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00002575 if (pgid < 0)
2576 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002577 return PyInt_FromLong((long)pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +00002578}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002579#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +00002580
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002581
Guido van Rossumb6775db1994-08-01 11:34:53 +00002582#ifdef HAVE_TCSETPGRP
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002583static char posix_tcsetpgrp__doc__[] =
2584"tcsetpgrp(fd, pgid) -> None\n\
2585Set the process group associated with the terminal given by a fd.";
2586
Barry Warsaw53699e91996-12-10 23:23:01 +00002587static PyObject *
Guido van Rossum7066dd71992-09-17 17:54:56 +00002588posix_tcsetpgrp(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002589 PyObject *self;
2590 PyObject *args;
Guido van Rossum7066dd71992-09-17 17:54:56 +00002591{
2592 int fd, pgid;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002593 if (!PyArg_ParseTuple(args, "ii:tcsetpgrp", &fd, &pgid))
Guido van Rossum7066dd71992-09-17 17:54:56 +00002594 return NULL;
Guido van Rossum687dd131993-05-17 08:34:16 +00002595 if (tcsetpgrp(fd, pgid) < 0)
2596 return posix_error();
Barry Warsaw43d68b81996-12-19 22:10:44 +00002597 Py_INCREF(Py_None);
Barry Warsaw53699e91996-12-10 23:23:01 +00002598 return Py_None;
Guido van Rossum7066dd71992-09-17 17:54:56 +00002599}
Guido van Rossumb6775db1994-08-01 11:34:53 +00002600#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +00002601
Guido van Rossum687dd131993-05-17 08:34:16 +00002602/* Functions acting on file descriptors */
2603
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002604static char posix_open__doc__[] =
2605"open(filename, flag [, mode=0777]) -> fd\n\
2606Open a file (for low level IO).";
2607
Barry Warsaw53699e91996-12-10 23:23:01 +00002608static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002609posix_open(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002610 PyObject *self;
2611 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002612{
2613 char *file;
2614 int flag;
2615 int mode = 0777;
2616 int fd;
Barry Warsaw43d68b81996-12-19 22:10:44 +00002617 if (!PyArg_ParseTuple(args, "si|i", &file, &flag, &mode))
2618 return NULL;
2619
Barry Warsaw53699e91996-12-10 23:23:01 +00002620 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002621 fd = open(file, flag, mode);
Barry Warsaw53699e91996-12-10 23:23:01 +00002622 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002623 if (fd < 0)
Barry Warsawd58d7641998-07-23 16:14:40 +00002624 return posix_error_with_filename(file);
Barry Warsaw53699e91996-12-10 23:23:01 +00002625 return PyInt_FromLong((long)fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00002626}
2627
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002628
2629static char posix_close__doc__[] =
2630"close(fd) -> None\n\
2631Close a file descriptor (for low level IO).";
2632
Barry Warsaw53699e91996-12-10 23:23:01 +00002633static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002634posix_close(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002635 PyObject *self;
2636 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002637{
2638 int fd, res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002639 if (!PyArg_ParseTuple(args, "i:close", &fd))
Guido van Rossum687dd131993-05-17 08:34:16 +00002640 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002641 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002642 res = close(fd);
Barry Warsaw53699e91996-12-10 23:23:01 +00002643 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002644 if (res < 0)
2645 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002646 Py_INCREF(Py_None);
2647 return Py_None;
Guido van Rossum687dd131993-05-17 08:34:16 +00002648}
2649
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002650
2651static char posix_dup__doc__[] =
2652"dup(fd) -> fd2\n\
2653Return a duplicate of a file descriptor.";
2654
Barry Warsaw53699e91996-12-10 23:23:01 +00002655static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002656posix_dup(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002657 PyObject *self;
2658 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002659{
2660 int fd;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002661 if (!PyArg_ParseTuple(args, "i:dup", &fd))
Guido van Rossum687dd131993-05-17 08:34:16 +00002662 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002663 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002664 fd = dup(fd);
Barry Warsaw53699e91996-12-10 23:23:01 +00002665 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002666 if (fd < 0)
2667 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002668 return PyInt_FromLong((long)fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00002669}
2670
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002671
2672static char posix_dup2__doc__[] =
2673"dup2(fd, fd2) -> None\n\
2674Duplicate file descriptor.";
2675
Barry Warsaw53699e91996-12-10 23:23:01 +00002676static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002677posix_dup2(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002678 PyObject *self;
2679 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002680{
2681 int fd, fd2, res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002682 if (!PyArg_ParseTuple(args, "ii:dup2", &fd, &fd2))
Guido van Rossum687dd131993-05-17 08:34:16 +00002683 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002684 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002685 res = dup2(fd, fd2);
Barry Warsaw53699e91996-12-10 23:23:01 +00002686 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002687 if (res < 0)
2688 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002689 Py_INCREF(Py_None);
2690 return Py_None;
Guido van Rossum687dd131993-05-17 08:34:16 +00002691}
2692
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002693
2694static char posix_lseek__doc__[] =
2695"lseek(fd, pos, how) -> newpos\n\
2696Set the current position of a file descriptor.";
2697
Barry Warsaw53699e91996-12-10 23:23:01 +00002698static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002699posix_lseek(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002700 PyObject *self;
2701 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002702{
2703 int fd, how;
Fred Drake699f3522000-06-29 21:12:41 +00002704#ifdef MS_WIN64
2705 LONG_LONG pos, res;
2706#else
Guido van Rossum94f6f721999-01-06 18:42:14 +00002707 off_t pos, res;
Fred Drake699f3522000-06-29 21:12:41 +00002708#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00002709 PyObject *posobj;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002710 if (!PyArg_ParseTuple(args, "iOi:lseek", &fd, &posobj, &how))
Guido van Rossum687dd131993-05-17 08:34:16 +00002711 return NULL;
2712#ifdef SEEK_SET
2713 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
2714 switch (how) {
2715 case 0: how = SEEK_SET; break;
2716 case 1: how = SEEK_CUR; break;
2717 case 2: how = SEEK_END; break;
2718 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00002719#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +00002720
2721#if !defined(HAVE_LARGEFILE_SUPPORT)
2722 pos = PyInt_AsLong(posobj);
2723#else
2724 pos = PyLong_Check(posobj) ?
2725 PyLong_AsLongLong(posobj) : PyInt_AsLong(posobj);
2726#endif
2727 if (PyErr_Occurred())
2728 return NULL;
2729
Barry Warsaw53699e91996-12-10 23:23:01 +00002730 Py_BEGIN_ALLOW_THREADS
Fred Drake699f3522000-06-29 21:12:41 +00002731#ifdef MS_WIN64
2732 res = _lseeki64(fd, pos, how);
2733#else
Guido van Rossum687dd131993-05-17 08:34:16 +00002734 res = lseek(fd, pos, how);
Fred Drake699f3522000-06-29 21:12:41 +00002735#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00002736 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002737 if (res < 0)
2738 return posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +00002739
2740#if !defined(HAVE_LARGEFILE_SUPPORT)
Barry Warsaw53699e91996-12-10 23:23:01 +00002741 return PyInt_FromLong(res);
Guido van Rossum94f6f721999-01-06 18:42:14 +00002742#else
2743 return PyLong_FromLongLong(res);
2744#endif
Guido van Rossum687dd131993-05-17 08:34:16 +00002745}
2746
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002747
2748static char posix_read__doc__[] =
2749"read(fd, buffersize) -> string\n\
2750Read a file descriptor.";
2751
Barry Warsaw53699e91996-12-10 23:23:01 +00002752static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002753posix_read(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002754 PyObject *self;
2755 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002756{
Guido van Rossum8bac5461996-06-11 18:38:48 +00002757 int fd, size, n;
Barry Warsaw53699e91996-12-10 23:23:01 +00002758 PyObject *buffer;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002759 if (!PyArg_ParseTuple(args, "ii:read", &fd, &size))
Guido van Rossum687dd131993-05-17 08:34:16 +00002760 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002761 buffer = PyString_FromStringAndSize((char *)NULL, size);
Guido van Rossum687dd131993-05-17 08:34:16 +00002762 if (buffer == NULL)
2763 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002764 Py_BEGIN_ALLOW_THREADS
2765 n = read(fd, PyString_AsString(buffer), size);
2766 Py_END_ALLOW_THREADS
Guido van Rossum8bac5461996-06-11 18:38:48 +00002767 if (n < 0) {
Barry Warsaw53699e91996-12-10 23:23:01 +00002768 Py_DECREF(buffer);
Guido van Rossum687dd131993-05-17 08:34:16 +00002769 return posix_error();
2770 }
Guido van Rossum8bac5461996-06-11 18:38:48 +00002771 if (n != size)
Barry Warsaw53699e91996-12-10 23:23:01 +00002772 _PyString_Resize(&buffer, n);
Guido van Rossum687dd131993-05-17 08:34:16 +00002773 return buffer;
2774}
2775
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002776
2777static char posix_write__doc__[] =
2778"write(fd, string) -> byteswritten\n\
2779Write a string to a file descriptor.";
2780
Barry Warsaw53699e91996-12-10 23:23:01 +00002781static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002782posix_write(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002783 PyObject *self;
2784 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002785{
2786 int fd, size;
2787 char *buffer;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002788 if (!PyArg_ParseTuple(args, "is#:write", &fd, &buffer, &size))
Guido van Rossum687dd131993-05-17 08:34:16 +00002789 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002790 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002791 size = write(fd, buffer, size);
Barry Warsaw53699e91996-12-10 23:23:01 +00002792 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002793 if (size < 0)
2794 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002795 return PyInt_FromLong((long)size);
Guido van Rossum687dd131993-05-17 08:34:16 +00002796}
2797
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002798
2799static char posix_fstat__doc__[]=
2800"fstat(fd) -> (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
2801Like stat(), but for an open file descriptor.";
2802
Barry Warsaw53699e91996-12-10 23:23:01 +00002803static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002804posix_fstat(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002805 PyObject *self;
2806 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002807{
2808 int fd;
Fred Drake699f3522000-06-29 21:12:41 +00002809 STRUCT_STAT st;
Guido van Rossum687dd131993-05-17 08:34:16 +00002810 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002811 if (!PyArg_ParseTuple(args, "i:fstat", &fd))
Guido van Rossum687dd131993-05-17 08:34:16 +00002812 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002813 Py_BEGIN_ALLOW_THREADS
Fred Drake699f3522000-06-29 21:12:41 +00002814 res = FSTAT(fd, &st);
Barry Warsaw53699e91996-12-10 23:23:01 +00002815 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002816 if (res != 0)
2817 return posix_error();
Fred Drake699f3522000-06-29 21:12:41 +00002818
2819 return _pystat_fromstructstat(st);
Guido van Rossum687dd131993-05-17 08:34:16 +00002820}
2821
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002822
2823static char posix_fdopen__doc__[] =
2824"fdopen(fd, [, mode='r' [, bufsize]]) -> file_object\n\
2825Return an open file object connected to a file descriptor.";
2826
Barry Warsaw53699e91996-12-10 23:23:01 +00002827static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002828posix_fdopen(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002829 PyObject *self;
2830 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002831{
Barry Warsaw53699e91996-12-10 23:23:01 +00002832 extern int fclose Py_PROTO((FILE *));
Guido van Rossum687dd131993-05-17 08:34:16 +00002833 int fd;
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002834 char *mode = "r";
2835 int bufsize = -1;
Guido van Rossum687dd131993-05-17 08:34:16 +00002836 FILE *fp;
Barry Warsaw53699e91996-12-10 23:23:01 +00002837 PyObject *f;
2838 if (!PyArg_ParseTuple(args, "i|si", &fd, &mode, &bufsize))
Guido van Rossum687dd131993-05-17 08:34:16 +00002839 return NULL;
Barry Warsaw43d68b81996-12-19 22:10:44 +00002840
Barry Warsaw53699e91996-12-10 23:23:01 +00002841 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002842 fp = fdopen(fd, mode);
Barry Warsaw53699e91996-12-10 23:23:01 +00002843 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002844 if (fp == NULL)
2845 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002846 f = PyFile_FromFile(fp, "(fdopen)", mode, fclose);
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002847 if (f != NULL)
Barry Warsaw53699e91996-12-10 23:23:01 +00002848 PyFile_SetBufSize(f, bufsize);
Guido van Rossuma6a1e531995-01-10 15:36:38 +00002849 return f;
Guido van Rossum687dd131993-05-17 08:34:16 +00002850}
2851
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002852
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002853#ifdef HAVE_PIPE
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002854static char posix_pipe__doc__[] =
2855"pipe() -> (read_end, write_end)\n\
2856Create a pipe.";
2857
Barry Warsaw53699e91996-12-10 23:23:01 +00002858static PyObject *
Guido van Rossum687dd131993-05-17 08:34:16 +00002859posix_pipe(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002860 PyObject *self;
2861 PyObject *args;
Guido van Rossum687dd131993-05-17 08:34:16 +00002862{
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002863#if defined(PYOS_OS2)
2864 HFILE read, write;
2865 APIRET rc;
2866
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002867 if (!PyArg_ParseTuple(args, ":pipe"))
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002868 return NULL;
2869
2870 Py_BEGIN_ALLOW_THREADS
2871 rc = DosCreatePipe( &read, &write, 4096);
2872 Py_END_ALLOW_THREADS
2873 if (rc != NO_ERROR)
Guido van Rossumd48f2521997-12-05 22:19:34 +00002874 return os2_error(rc);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002875
2876 return Py_BuildValue("(ii)", read, write);
2877#else
Guido van Rossum8d665e61996-06-26 18:22:49 +00002878#if !defined(MS_WIN32)
Guido van Rossum687dd131993-05-17 08:34:16 +00002879 int fds[2];
2880 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002881 if (!PyArg_ParseTuple(args, ":pipe"))
Guido van Rossum687dd131993-05-17 08:34:16 +00002882 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002883 Py_BEGIN_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002884 res = pipe(fds);
Barry Warsaw53699e91996-12-10 23:23:01 +00002885 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +00002886 if (res != 0)
2887 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002888 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum8d665e61996-06-26 18:22:49 +00002889#else /* MS_WIN32 */
Guido van Rossum794d8131994-08-23 13:48:48 +00002890 HANDLE read, write;
Guido van Rossumb3f9f4b1998-06-12 15:05:15 +00002891 int read_fd, write_fd;
Guido van Rossum794d8131994-08-23 13:48:48 +00002892 BOOL ok;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002893 if (!PyArg_ParseTuple(args, ":pipe"))
Guido van Rossum794d8131994-08-23 13:48:48 +00002894 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002895 Py_BEGIN_ALLOW_THREADS
Guido van Rossumb3f9f4b1998-06-12 15:05:15 +00002896 ok = CreatePipe(&read, &write, NULL, 0);
Barry Warsaw53699e91996-12-10 23:23:01 +00002897 Py_END_ALLOW_THREADS
Guido van Rossum794d8131994-08-23 13:48:48 +00002898 if (!ok)
2899 return posix_error();
Fred Drake699f3522000-06-29 21:12:41 +00002900 read_fd = _open_osfhandle((intptr_t)read, 0);
2901 write_fd = _open_osfhandle((intptr_t)write, 1);
Guido van Rossumb3f9f4b1998-06-12 15:05:15 +00002902 return Py_BuildValue("(ii)", read_fd, write_fd);
Guido van Rossum8d665e61996-06-26 18:22:49 +00002903#endif /* MS_WIN32 */
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00002904#endif
Guido van Rossum687dd131993-05-17 08:34:16 +00002905}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002906#endif /* HAVE_PIPE */
2907
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002908
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002909#ifdef HAVE_MKFIFO
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002910static char posix_mkfifo__doc__[] =
2911"mkfifo(file, [, mode=0666]) -> None\n\
2912Create a FIFO (a POSIX named pipe).";
2913
Barry Warsaw53699e91996-12-10 23:23:01 +00002914static PyObject *
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002915posix_mkfifo(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002916 PyObject *self;
2917 PyObject *args;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002918{
2919 char *file;
2920 int mode = 0666;
2921 int res;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002922 if (!PyArg_ParseTuple(args, "s|i:mkfifo", &file, &mode))
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002923 return NULL;
Barry Warsaw53699e91996-12-10 23:23:01 +00002924 Py_BEGIN_ALLOW_THREADS
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002925 res = mkfifo(file, mode);
Barry Warsaw53699e91996-12-10 23:23:01 +00002926 Py_END_ALLOW_THREADS
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002927 if (res < 0)
2928 return posix_error();
Barry Warsaw53699e91996-12-10 23:23:01 +00002929 Py_INCREF(Py_None);
2930 return Py_None;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002931}
2932#endif
2933
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002934
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002935#ifdef HAVE_FTRUNCATE
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002936static char posix_ftruncate__doc__[] =
2937"ftruncate(fd, length) -> None\n\
2938Truncate a file to a specified length.";
2939
Barry Warsaw53699e91996-12-10 23:23:01 +00002940static PyObject *
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002941posix_ftruncate(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00002942 PyObject *self; /* Not used */
2943 PyObject *args;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002944{
2945 int fd;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002946 off_t length;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002947 int res;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002948 PyObject *lenobj;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002949
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002950 if (!PyArg_ParseTuple(args, "iO:ftruncate", &fd, &lenobj))
Guido van Rossum94f6f721999-01-06 18:42:14 +00002951 return NULL;
2952
2953#if !defined(HAVE_LARGEFILE_SUPPORT)
2954 length = PyInt_AsLong(lenobj);
2955#else
2956 length = PyLong_Check(lenobj) ?
2957 PyLong_AsLongLong(lenobj) : PyInt_AsLong(lenobj);
2958#endif
2959 if (PyErr_Occurred())
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002960 return NULL;
2961
Barry Warsaw53699e91996-12-10 23:23:01 +00002962 Py_BEGIN_ALLOW_THREADS
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002963 res = ftruncate(fd, length);
Barry Warsaw53699e91996-12-10 23:23:01 +00002964 Py_END_ALLOW_THREADS
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002965 if (res < 0) {
Barry Warsaw53699e91996-12-10 23:23:01 +00002966 PyErr_SetFromErrno(PyExc_IOError);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002967 return NULL;
2968 }
Barry Warsaw53699e91996-12-10 23:23:01 +00002969 Py_INCREF(Py_None);
2970 return Py_None;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00002971}
2972#endif
Guido van Rossum22db57e1992-04-05 14:25:30 +00002973
Guido van Rossumb9f866c1997-05-22 15:12:39 +00002974#ifdef NeXT
2975#define HAVE_PUTENV
2976/* Steve Spicklemire got this putenv from NeXTAnswers */
2977static int
2978putenv(char *newval)
2979{
2980 extern char **environ;
2981
2982 static int firstTime = 1;
2983 char **ep;
2984 char *cp;
2985 int esiz;
2986 char *np;
2987
2988 if (!(np = strchr(newval, '=')))
2989 return 1;
2990 *np = '\0';
2991
2992 /* look it up */
2993 for (ep=environ ; *ep ; ep++)
2994 {
2995 /* this should always be true... */
2996 if (cp = strchr(*ep, '='))
2997 {
2998 *cp = '\0';
2999 if (!strcmp(*ep, newval))
3000 {
3001 /* got it! */
3002 *cp = '=';
3003 break;
3004 }
3005 *cp = '=';
3006 }
3007 else
3008 {
3009 *np = '=';
3010 return 1;
3011 }
3012 }
3013
3014 *np = '=';
3015 if (*ep)
3016 {
3017 /* the string was already there:
3018 just replace it with the new one */
3019 *ep = newval;
3020 return 0;
3021 }
3022
3023 /* expand environ by one */
3024 for (esiz=2, ep=environ ; *ep ; ep++)
3025 esiz++;
3026 if (firstTime)
3027 {
3028 char **epp;
3029 char **newenv;
3030 if (!(newenv = malloc(esiz * sizeof(char *))))
3031 return 1;
3032
3033 for (ep=environ, epp=newenv ; *ep ;)
3034 *epp++ = *ep++;
3035 *epp++ = newval;
3036 *epp = (char *) 0;
3037 environ = newenv;
3038 }
3039 else
3040 {
3041 if (!(environ = realloc(environ, esiz * sizeof(char *))))
3042 return 1;
3043 environ[esiz - 2] = newval;
3044 environ[esiz - 1] = (char *) 0;
3045 firstTime = 0;
3046 }
3047
3048 return 0;
3049}
Guido van Rossumc6ef2041997-08-21 02:30:45 +00003050#endif /* NeXT */
Guido van Rossumb9f866c1997-05-22 15:12:39 +00003051
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003052
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003053#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003054static char posix_putenv__doc__[] =
3055"putenv(key, value) -> None\n\
3056Change or add an environment variable.";
3057
Guido van Rossumbcc20741998-08-04 22:53:56 +00003058#ifdef __BEOS__
3059/* We have putenv(), but not in the headers (as of PR2). - [cjh] */
3060int putenv( const char *str );
3061#endif
3062
Fred Drake762e2061999-08-26 17:23:54 +00003063/* Save putenv() parameters as values here, so we can collect them when they
3064 * get re-set with another call for the same key. */
3065static PyObject *posix_putenv_garbage;
3066
Barry Warsaw53699e91996-12-10 23:23:01 +00003067static PyObject *
Guido van Rossumb6a47161997-09-15 22:54:34 +00003068posix_putenv(self, args)
Barry Warsaw53699e91996-12-10 23:23:01 +00003069 PyObject *self;
3070 PyObject *args;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003071{
3072 char *s1, *s2;
3073 char *new;
Fred Drake762e2061999-08-26 17:23:54 +00003074 PyObject *newstr;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003075
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003076 if (!PyArg_ParseTuple(args, "ss:putenv", &s1, &s2))
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003077 return NULL;
Guido van Rossumd48f2521997-12-05 22:19:34 +00003078
3079#if defined(PYOS_OS2)
3080 if (stricmp(s1, "BEGINLIBPATH") == 0) {
3081 APIRET rc;
3082
3083 if (strlen(s2) == 0) /* If New Value is an Empty String */
3084 s2 = NULL; /* Then OS/2 API Wants a NULL to Undefine It */
3085
3086 rc = DosSetExtLIBPATH(s2, BEGIN_LIBPATH);
3087 if (rc != NO_ERROR)
3088 return os2_error(rc);
3089
3090 } else if (stricmp(s1, "ENDLIBPATH") == 0) {
3091 APIRET rc;
3092
3093 if (strlen(s2) == 0) /* If New Value is an Empty String */
3094 s2 = NULL; /* Then OS/2 API Wants a NULL to Undefine It */
3095
3096 rc = DosSetExtLIBPATH(s2, END_LIBPATH);
3097 if (rc != NO_ERROR)
3098 return os2_error(rc);
3099 } else {
3100#endif
3101
Fred Drake762e2061999-08-26 17:23:54 +00003102 /* XXX This can leak memory -- not easy to fix :-( */
3103 newstr = PyString_FromStringAndSize(NULL, strlen(s1) + strlen(s2) + 2);
3104 if (newstr == NULL)
3105 return PyErr_NoMemory();
3106 new = PyString_AS_STRING(newstr);
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003107 (void) sprintf(new, "%s=%s", s1, s2);
3108 if (putenv(new)) {
3109 posix_error();
3110 return NULL;
3111 }
Fred Drake762e2061999-08-26 17:23:54 +00003112 /* Install the first arg and newstr in posix_putenv_garbage;
3113 * this will cause previous value to be collected. This has to
3114 * happen after the real putenv() call because the old value
3115 * was still accessible until then. */
3116 if (PyDict_SetItem(posix_putenv_garbage,
3117 PyTuple_GET_ITEM(args, 0), newstr)) {
3118 /* really not much we can do; just leak */
3119 PyErr_Clear();
3120 }
3121 else {
3122 Py_DECREF(newstr);
3123 }
Guido van Rossumd48f2521997-12-05 22:19:34 +00003124
3125#if defined(PYOS_OS2)
3126 }
3127#endif
Barry Warsaw53699e91996-12-10 23:23:01 +00003128 Py_INCREF(Py_None);
3129 return Py_None;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003130}
Guido van Rossumb6a47161997-09-15 22:54:34 +00003131#endif /* putenv */
3132
3133#ifdef HAVE_STRERROR
3134static char posix_strerror__doc__[] =
3135"strerror(code) -> string\n\
3136Translate an error code to a message string.";
3137
3138PyObject *
3139posix_strerror(self, args)
3140 PyObject *self;
3141 PyObject *args;
3142{
3143 int code;
3144 char *message;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003145 if (!PyArg_ParseTuple(args, "i:strerror", &code))
Guido van Rossumb6a47161997-09-15 22:54:34 +00003146 return NULL;
3147 message = strerror(code);
3148 if (message == NULL) {
3149 PyErr_SetString(PyExc_ValueError,
3150 "strerror code out of range");
3151 return NULL;
3152 }
3153 return PyString_FromString(message);
3154}
3155#endif /* strerror */
3156
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00003157
Guido van Rossumc9641791998-08-04 15:26:23 +00003158#ifdef HAVE_SYS_WAIT_H
3159
3160#ifdef WIFSTOPPED
3161static char posix_WIFSTOPPED__doc__[] =
3162"WIFSTOPPED(status) -> Boolean\n\
Fred Drake7e3535c1999-02-02 16:37:11 +00003163Return true if the process returning 'status' was stopped.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003164
3165static PyObject *
3166posix_WIFSTOPPED(self, args)
3167 PyObject *self;
3168 PyObject *args;
3169{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003170#ifdef UNION_WAIT
3171 union wait status;
3172#define status_i (status.w_status)
3173#else
3174 int status;
3175#define status_i status
3176#endif
3177 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003178
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003179 if (!PyArg_ParseTuple(args, "i:WIFSTOPPED", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003180 {
3181 return NULL;
3182 }
3183
3184 return Py_BuildValue("i", WIFSTOPPED(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003185#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003186}
3187#endif /* WIFSTOPPED */
3188
3189#ifdef WIFSIGNALED
3190static char posix_WIFSIGNALED__doc__[] =
3191"WIFSIGNALED(status) -> Boolean\n\
Guido van Rossum3366d1c1999-02-23 18:34:43 +00003192Return true if the process returning 'status' was terminated by a signal.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003193
3194static PyObject *
3195posix_WIFSIGNALED(self, args)
3196 PyObject *self;
3197 PyObject *args;
3198{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003199#ifdef UNION_WAIT
3200 union wait status;
3201#define status_i (status.w_status)
3202#else
3203 int status;
3204#define status_i status
3205#endif
3206 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003207
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003208 if (!PyArg_ParseTuple(args, "i:WIFSIGNALED", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003209 {
3210 return NULL;
3211 }
3212
3213 return Py_BuildValue("i", WIFSIGNALED(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003214#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003215}
3216#endif /* WIFSIGNALED */
3217
3218#ifdef WIFEXITED
3219static char posix_WIFEXITED__doc__[] =
3220"WIFEXITED(status) -> Boolean\n\
Fred Drake7e3535c1999-02-02 16:37:11 +00003221Return true if the process returning 'status' exited using the exit()\n\
3222system call.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003223
3224static PyObject *
3225posix_WIFEXITED(self, args)
3226 PyObject *self;
3227 PyObject *args;
3228{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003229#ifdef UNION_WAIT
3230 union wait status;
3231#define status_i (status.w_status)
3232#else
3233 int status;
3234#define status_i status
3235#endif
3236 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003237
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003238 if (!PyArg_ParseTuple(args, "i:WIFEXITED", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003239 {
3240 return NULL;
3241 }
3242
3243 return Py_BuildValue("i", WIFEXITED(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003244#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003245}
3246#endif /* WIFEXITED */
3247
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003248#ifdef WEXITSTATUS
Guido van Rossumc9641791998-08-04 15:26:23 +00003249static char posix_WEXITSTATUS__doc__[] =
3250"WEXITSTATUS(status) -> integer\n\
Fred Drake7e3535c1999-02-02 16:37:11 +00003251Return the process return code from 'status'.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003252
3253static PyObject *
3254posix_WEXITSTATUS(self, args)
3255 PyObject *self;
3256 PyObject *args;
3257{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003258#ifdef UNION_WAIT
3259 union wait status;
3260#define status_i (status.w_status)
3261#else
3262 int status;
3263#define status_i status
3264#endif
3265 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003266
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003267 if (!PyArg_ParseTuple(args, "i:WEXITSTATUS", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003268 {
3269 return NULL;
3270 }
3271
3272 return Py_BuildValue("i", WEXITSTATUS(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003273#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003274}
3275#endif /* WEXITSTATUS */
3276
3277#ifdef WTERMSIG
3278static char posix_WTERMSIG__doc__[] =
3279"WTERMSIG(status) -> integer\n\
Fred Drake7e3535c1999-02-02 16:37:11 +00003280Return the signal that terminated the process that provided the 'status'\n\
3281value.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003282
3283static PyObject *
3284posix_WTERMSIG(self, args)
3285 PyObject *self;
3286 PyObject *args;
3287{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003288#ifdef UNION_WAIT
3289 union wait status;
3290#define status_i (status.w_status)
3291#else
3292 int status;
3293#define status_i status
3294#endif
3295 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003296
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003297 if (!PyArg_ParseTuple(args, "i:WTERMSIG", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003298 {
3299 return NULL;
3300 }
3301
3302 return Py_BuildValue("i", WTERMSIG(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003303#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003304}
3305#endif /* WTERMSIG */
3306
3307#ifdef WSTOPSIG
3308static char posix_WSTOPSIG__doc__[] =
3309"WSTOPSIG(status) -> integer\n\
Fred Drake7e3535c1999-02-02 16:37:11 +00003310Return the signal that stopped the process that provided the 'status' value.";
Guido van Rossumc9641791998-08-04 15:26:23 +00003311
3312static PyObject *
3313posix_WSTOPSIG(self, args)
3314 PyObject *self;
3315 PyObject *args;
3316{
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00003317#ifdef UNION_WAIT
3318 union wait status;
3319#define status_i (status.w_status)
3320#else
3321 int status;
3322#define status_i status
3323#endif
3324 status_i = 0;
Guido van Rossumc9641791998-08-04 15:26:23 +00003325
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003326 if (!PyArg_ParseTuple(args, "i:WSTOPSIG", &status_i))
Guido van Rossumc9641791998-08-04 15:26:23 +00003327 {
3328 return NULL;
3329 }
3330
3331 return Py_BuildValue("i", WSTOPSIG(status));
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003332#undef status_i
Guido van Rossumc9641791998-08-04 15:26:23 +00003333}
3334#endif /* WSTOPSIG */
3335
3336#endif /* HAVE_SYS_WAIT_H */
3337
3338
Guido van Rossum94f6f721999-01-06 18:42:14 +00003339#if defined(HAVE_FSTATVFS)
Guido van Rossumd5753e11999-10-19 13:29:23 +00003340#ifdef _SCO_DS
3341/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
3342 needed definitions in sys/statvfs.h */
3343#define _SVID3
3344#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00003345#include <sys/statvfs.h>
3346
3347static char posix_fstatvfs__doc__[] =
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003348"fstatvfs(fd) -> \n\
3349 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax)\n\
Guido van Rossum94f6f721999-01-06 18:42:14 +00003350Perform an fstatvfs system call on the given fd.";
3351
3352static PyObject *
3353posix_fstatvfs(self, args)
3354 PyObject *self;
3355 PyObject *args;
3356{
3357 int fd, res;
3358 struct statvfs st;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003359 if (!PyArg_ParseTuple(args, "i:fstatvfs", &fd))
Guido van Rossum94f6f721999-01-06 18:42:14 +00003360 return NULL;
3361 Py_BEGIN_ALLOW_THREADS
3362 res = fstatvfs(fd, &st);
3363 Py_END_ALLOW_THREADS
3364 if (res != 0)
3365 return posix_error();
3366#if !defined(HAVE_LARGEFILE_SUPPORT)
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003367 return Py_BuildValue("(llllllllll)",
Guido van Rossum94f6f721999-01-06 18:42:14 +00003368 (long) st.f_bsize,
3369 (long) st.f_frsize,
3370 (long) st.f_blocks,
3371 (long) st.f_bfree,
3372 (long) st.f_bavail,
3373 (long) st.f_files,
3374 (long) st.f_ffree,
3375 (long) st.f_favail,
Guido van Rossum94f6f721999-01-06 18:42:14 +00003376 (long) st.f_flag,
3377 (long) st.f_namemax);
3378#else
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003379 return Py_BuildValue("(llLLLLLLll)",
Guido van Rossum94f6f721999-01-06 18:42:14 +00003380 (long) st.f_bsize,
3381 (long) st.f_frsize,
3382 (LONG_LONG) st.f_blocks,
3383 (LONG_LONG) st.f_bfree,
3384 (LONG_LONG) st.f_bavail,
3385 (LONG_LONG) st.f_files,
3386 (LONG_LONG) st.f_ffree,
3387 (LONG_LONG) st.f_favail,
Guido van Rossum94f6f721999-01-06 18:42:14 +00003388 (long) st.f_flag,
3389 (long) st.f_namemax);
3390#endif
3391}
3392#endif /* HAVE_FSTATVFS */
3393
3394
3395#if defined(HAVE_STATVFS)
3396#include <sys/statvfs.h>
3397
3398static char posix_statvfs__doc__[] =
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003399"statvfs(path) -> \n\
3400 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax)\n\
Guido van Rossum94f6f721999-01-06 18:42:14 +00003401Perform a statvfs system call on the given path.";
3402
3403static PyObject *
3404posix_statvfs(self, args)
3405 PyObject *self;
3406 PyObject *args;
3407{
3408 char *path;
3409 int res;
3410 struct statvfs st;
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003411 if (!PyArg_ParseTuple(args, "s:statvfs", &path))
Guido van Rossum94f6f721999-01-06 18:42:14 +00003412 return NULL;
3413 Py_BEGIN_ALLOW_THREADS
3414 res = statvfs(path, &st);
3415 Py_END_ALLOW_THREADS
3416 if (res != 0)
3417 return posix_error_with_filename(path);
3418#if !defined(HAVE_LARGEFILE_SUPPORT)
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003419 return Py_BuildValue("(llllllllll)",
Guido van Rossum94f6f721999-01-06 18:42:14 +00003420 (long) st.f_bsize,
3421 (long) st.f_frsize,
3422 (long) st.f_blocks,
3423 (long) st.f_bfree,
3424 (long) st.f_bavail,
3425 (long) st.f_files,
3426 (long) st.f_ffree,
3427 (long) st.f_favail,
Guido van Rossum94f6f721999-01-06 18:42:14 +00003428 (long) st.f_flag,
3429 (long) st.f_namemax);
3430#else /* HAVE_LARGEFILE_SUPPORT */
Guido van Rossum0c9608c1999-02-03 16:32:37 +00003431 return Py_BuildValue("(llLLLLLLll)",
Guido van Rossum94f6f721999-01-06 18:42:14 +00003432 (long) st.f_bsize,
3433 (long) st.f_frsize,
3434 (LONG_LONG) st.f_blocks,
3435 (LONG_LONG) st.f_bfree,
3436 (LONG_LONG) st.f_bavail,
3437 (LONG_LONG) st.f_files,
3438 (LONG_LONG) st.f_ffree,
3439 (LONG_LONG) st.f_favail,
Guido van Rossum94f6f721999-01-06 18:42:14 +00003440 (long) st.f_flag,
3441 (long) st.f_namemax);
3442#endif
3443}
3444#endif /* HAVE_STATVFS */
3445
3446
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003447#ifdef HAVE_TEMPNAM
3448static char posix_tempnam__doc__[] = "\
3449tempnam([dir[, prefix]]) -> string\n\
3450Return a unique name for a temporary file.\n\
3451The directory and a short may be specified as strings; they may be omitted\n\
3452or None if not needed.";
3453
3454static PyObject *
3455posix_tempnam(self, args)
3456 PyObject *self;
3457 PyObject *args;
3458{
3459 PyObject *result = NULL;
3460 char *dir = NULL;
3461 char *pfx = NULL;
3462 char *name;
3463
3464 if (!PyArg_ParseTuple(args, "|zz:tempnam", &dir, &pfx))
3465 return NULL;
3466 name = tempnam(dir, pfx);
3467 if (name == NULL)
3468 return PyErr_NoMemory();
3469 result = PyString_FromString(name);
3470 free(name);
3471 return result;
3472}
Guido van Rossumd371ff11999-01-25 16:12:23 +00003473#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003474
3475
3476#ifdef HAVE_TMPFILE
3477static char posix_tmpfile__doc__[] = "\
3478tmpfile() -> file object\n\
3479Create a temporary file with no directory entries.";
3480
3481static PyObject *
3482posix_tmpfile(self, args)
3483 PyObject *self;
3484 PyObject *args;
3485{
3486 FILE *fp;
3487
3488 if (!PyArg_ParseTuple(args, ":tmpfile"))
3489 return NULL;
3490 fp = tmpfile();
3491 if (fp == NULL)
3492 return posix_error();
3493 return PyFile_FromFile(fp, "<tmpfile>", "w+", fclose);
3494}
3495#endif
3496
3497
3498#ifdef HAVE_TMPNAM
3499static char posix_tmpnam__doc__[] = "\
3500tmpnam() -> string\n\
3501Return a unique name for a temporary file.";
3502
3503static PyObject *
3504posix_tmpnam(self, args)
3505 PyObject *self;
3506 PyObject *args;
3507{
3508 char buffer[L_tmpnam];
3509 char *name;
3510
3511 if (!PyArg_ParseTuple(args, ":tmpnam"))
3512 return NULL;
Greg Wardb48bc172000-03-01 21:51:56 +00003513#ifdef USE_TMPNAM_R
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003514 name = tmpnam_r(buffer);
3515#else
3516 name = tmpnam(buffer);
3517#endif
3518 if (name == NULL) {
3519 PyErr_SetObject(PyExc_OSError,
3520 Py_BuildValue("is", 0,
Greg Wardb48bc172000-03-01 21:51:56 +00003521#ifdef USE_TMPNAM_R
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003522 "unexpected NULL from tmpnam_r"
3523#else
3524 "unexpected NULL from tmpnam"
3525#endif
3526 ));
3527 return NULL;
3528 }
3529 return PyString_FromString(buffer);
3530}
3531#endif
3532
3533
Fred Drakec9680921999-12-13 16:37:25 +00003534/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
3535 * It maps strings representing configuration variable names to
3536 * integer values, allowing those functions to be called with the
3537 * magic names instead of poluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +00003538 * rarely-used constants. There are three separate tables that use
3539 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +00003540 *
3541 * This code is always included, even if none of the interfaces that
3542 * need it are included. The #if hackery needed to avoid it would be
3543 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +00003544 */
3545struct constdef {
3546 char *name;
3547 long value;
3548};
3549
Fred Drake12c6e2d1999-12-14 21:25:03 +00003550static int
3551conv_confname(arg, valuep, table, tablesize)
3552 PyObject *arg;
3553 int *valuep;
3554 struct constdef *table;
3555 size_t tablesize;
3556{
3557 if (PyInt_Check(arg)) {
3558 *valuep = PyInt_AS_LONG(arg);
3559 return 1;
3560 }
3561 if (PyString_Check(arg)) {
3562 /* look up the value in the table using a binary search */
Fred Drake699f3522000-06-29 21:12:41 +00003563 size_t lo = 0;
3564 size_t mid;
3565 size_t hi = tablesize;
3566 int cmp;
Fred Drake12c6e2d1999-12-14 21:25:03 +00003567 char *confname = PyString_AS_STRING(arg);
3568 while (lo < hi) {
3569 mid = (lo + hi) / 2;
3570 cmp = strcmp(confname, table[mid].name);
3571 if (cmp < 0)
3572 hi = mid;
3573 else if (cmp > 0)
3574 lo = mid + 1;
3575 else {
3576 *valuep = table[mid].value;
3577 return 1;
3578 }
3579 }
3580 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
3581 }
3582 else
3583 PyErr_SetString(PyExc_TypeError,
3584 "configuration names must be strings or integers");
3585 return 0;
3586}
3587
3588
3589#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
3590static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +00003591#ifdef _PC_ABI_AIO_XFER_MAX
3592 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
3593#endif
3594#ifdef _PC_ABI_ASYNC_IO
3595 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
3596#endif
Fred Drakec9680921999-12-13 16:37:25 +00003597#ifdef _PC_ASYNC_IO
3598 {"PC_ASYNC_IO", _PC_ASYNC_IO},
3599#endif
3600#ifdef _PC_CHOWN_RESTRICTED
3601 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
3602#endif
3603#ifdef _PC_FILESIZEBITS
3604 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
3605#endif
3606#ifdef _PC_LAST
3607 {"PC_LAST", _PC_LAST},
3608#endif
3609#ifdef _PC_LINK_MAX
3610 {"PC_LINK_MAX", _PC_LINK_MAX},
3611#endif
3612#ifdef _PC_MAX_CANON
3613 {"PC_MAX_CANON", _PC_MAX_CANON},
3614#endif
3615#ifdef _PC_MAX_INPUT
3616 {"PC_MAX_INPUT", _PC_MAX_INPUT},
3617#endif
3618#ifdef _PC_NAME_MAX
3619 {"PC_NAME_MAX", _PC_NAME_MAX},
3620#endif
3621#ifdef _PC_NO_TRUNC
3622 {"PC_NO_TRUNC", _PC_NO_TRUNC},
3623#endif
3624#ifdef _PC_PATH_MAX
3625 {"PC_PATH_MAX", _PC_PATH_MAX},
3626#endif
3627#ifdef _PC_PIPE_BUF
3628 {"PC_PIPE_BUF", _PC_PIPE_BUF},
3629#endif
3630#ifdef _PC_PRIO_IO
3631 {"PC_PRIO_IO", _PC_PRIO_IO},
3632#endif
3633#ifdef _PC_SOCK_MAXBUF
3634 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
3635#endif
3636#ifdef _PC_SYNC_IO
3637 {"PC_SYNC_IO", _PC_SYNC_IO},
3638#endif
3639#ifdef _PC_VDISABLE
3640 {"PC_VDISABLE", _PC_VDISABLE},
3641#endif
3642};
3643
Fred Drakec9680921999-12-13 16:37:25 +00003644static int
3645conv_path_confname(arg, valuep)
3646 PyObject *arg;
3647 int *valuep;
3648{
3649 return conv_confname(arg, valuep, posix_constants_pathconf,
3650 sizeof(posix_constants_pathconf)
3651 / sizeof(struct constdef));
3652}
3653#endif
3654
3655#ifdef HAVE_FPATHCONF
3656static char posix_fpathconf__doc__[] = "\
3657fpathconf(fd, name) -> integer\n\
3658Return the configuration limit name for the file descriptor fd.\n\
3659If there is no limit, return -1.";
3660
3661static PyObject *
3662posix_fpathconf(self, args)
3663 PyObject *self;
3664 PyObject *args;
3665{
3666 PyObject *result = NULL;
3667 int name, fd;
3668
Fred Drake12c6e2d1999-12-14 21:25:03 +00003669 if (PyArg_ParseTuple(args, "iO&:fpathconf", &fd,
3670 conv_path_confname, &name)) {
Fred Drakec9680921999-12-13 16:37:25 +00003671 long limit;
3672
3673 errno = 0;
3674 limit = fpathconf(fd, name);
3675 if (limit == -1 && errno != 0)
3676 posix_error();
3677 else
3678 result = PyInt_FromLong(limit);
3679 }
3680 return result;
3681}
3682#endif
3683
3684
3685#ifdef HAVE_PATHCONF
3686static char posix_pathconf__doc__[] = "\
3687pathconf(path, name) -> integer\n\
3688Return the configuration limit name for the file or directory path.\n\
3689If there is no limit, return -1.";
3690
3691static PyObject *
3692posix_pathconf(self, args)
3693 PyObject *self;
3694 PyObject *args;
3695{
3696 PyObject *result = NULL;
3697 int name;
3698 char *path;
3699
3700 if (PyArg_ParseTuple(args, "sO&:pathconf", &path,
3701 conv_path_confname, &name)) {
3702 long limit;
3703
3704 errno = 0;
3705 limit = pathconf(path, name);
Fred Drake12c6e2d1999-12-14 21:25:03 +00003706 if (limit == -1 && errno != 0) {
Fred Drakec9680921999-12-13 16:37:25 +00003707 if (errno == EINVAL)
3708 /* could be a path or name problem */
3709 posix_error();
3710 else
3711 posix_error_with_filename(path);
Fred Drake12c6e2d1999-12-14 21:25:03 +00003712 }
Fred Drakec9680921999-12-13 16:37:25 +00003713 else
3714 result = PyInt_FromLong(limit);
3715 }
3716 return result;
3717}
3718#endif
3719
3720#ifdef HAVE_CONFSTR
3721static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +00003722#ifdef _CS_ARCHITECTURE
3723 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
3724#endif
3725#ifdef _CS_HOSTNAME
3726 {"CS_HOSTNAME", _CS_HOSTNAME},
3727#endif
3728#ifdef _CS_HW_PROVIDER
3729 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
3730#endif
3731#ifdef _CS_HW_SERIAL
3732 {"CS_HW_SERIAL", _CS_HW_SERIAL},
3733#endif
3734#ifdef _CS_INITTAB_NAME
3735 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
3736#endif
Fred Drakec9680921999-12-13 16:37:25 +00003737#ifdef _CS_LFS64_CFLAGS
3738 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
3739#endif
3740#ifdef _CS_LFS64_LDFLAGS
3741 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
3742#endif
3743#ifdef _CS_LFS64_LIBS
3744 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
3745#endif
3746#ifdef _CS_LFS64_LINTFLAGS
3747 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
3748#endif
3749#ifdef _CS_LFS_CFLAGS
3750 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
3751#endif
3752#ifdef _CS_LFS_LDFLAGS
3753 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
3754#endif
3755#ifdef _CS_LFS_LIBS
3756 {"CS_LFS_LIBS", _CS_LFS_LIBS},
3757#endif
3758#ifdef _CS_LFS_LINTFLAGS
3759 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
3760#endif
Fred Draked86ed291999-12-15 15:34:33 +00003761#ifdef _CS_MACHINE
3762 {"CS_MACHINE", _CS_MACHINE},
3763#endif
Fred Drakec9680921999-12-13 16:37:25 +00003764#ifdef _CS_PATH
3765 {"CS_PATH", _CS_PATH},
3766#endif
Fred Draked86ed291999-12-15 15:34:33 +00003767#ifdef _CS_RELEASE
3768 {"CS_RELEASE", _CS_RELEASE},
3769#endif
3770#ifdef _CS_SRPC_DOMAIN
3771 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
3772#endif
3773#ifdef _CS_SYSNAME
3774 {"CS_SYSNAME", _CS_SYSNAME},
3775#endif
3776#ifdef _CS_VERSION
3777 {"CS_VERSION", _CS_VERSION},
3778#endif
Fred Drakec9680921999-12-13 16:37:25 +00003779#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
3780 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
3781#endif
3782#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
3783 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
3784#endif
3785#ifdef _CS_XBS5_ILP32_OFF32_LIBS
3786 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
3787#endif
3788#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
3789 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
3790#endif
3791#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
3792 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
3793#endif
3794#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
3795 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
3796#endif
3797#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
3798 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
3799#endif
3800#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
3801 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
3802#endif
3803#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
3804 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
3805#endif
3806#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
3807 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
3808#endif
3809#ifdef _CS_XBS5_LP64_OFF64_LIBS
3810 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
3811#endif
3812#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
3813 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
3814#endif
3815#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
3816 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
3817#endif
3818#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
3819 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
3820#endif
3821#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
3822 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
3823#endif
3824#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
3825 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
3826#endif
Fred Draked86ed291999-12-15 15:34:33 +00003827#ifdef _MIPS_CS_AVAIL_PROCESSORS
3828 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
3829#endif
3830#ifdef _MIPS_CS_BASE
3831 {"MIPS_CS_BASE", _MIPS_CS_BASE},
3832#endif
3833#ifdef _MIPS_CS_HOSTID
3834 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
3835#endif
3836#ifdef _MIPS_CS_HW_NAME
3837 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
3838#endif
3839#ifdef _MIPS_CS_NUM_PROCESSORS
3840 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
3841#endif
3842#ifdef _MIPS_CS_OSREL_MAJ
3843 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
3844#endif
3845#ifdef _MIPS_CS_OSREL_MIN
3846 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
3847#endif
3848#ifdef _MIPS_CS_OSREL_PATCH
3849 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
3850#endif
3851#ifdef _MIPS_CS_OS_NAME
3852 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
3853#endif
3854#ifdef _MIPS_CS_OS_PROVIDER
3855 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
3856#endif
3857#ifdef _MIPS_CS_PROCESSORS
3858 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
3859#endif
3860#ifdef _MIPS_CS_SERIAL
3861 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
3862#endif
3863#ifdef _MIPS_CS_VENDOR
3864 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
3865#endif
Fred Drakec9680921999-12-13 16:37:25 +00003866};
3867
3868static int
3869conv_confstr_confname(arg, valuep)
3870 PyObject *arg;
3871 int *valuep;
3872{
3873 return conv_confname(arg, valuep, posix_constants_confstr,
3874 sizeof(posix_constants_confstr)
3875 / sizeof(struct constdef));
3876}
3877
3878static char posix_confstr__doc__[] = "\
3879confstr(name) -> string\n\
3880Return a string-valued system configuration variable.";
3881
3882static PyObject *
3883posix_confstr(self, args)
3884 PyObject *self;
3885 PyObject *args;
3886{
3887 PyObject *result = NULL;
3888 int name;
3889 char buffer[64];
3890
3891 if (PyArg_ParseTuple(args, "O&:confstr", conv_confstr_confname, &name)) {
3892 int len = confstr(name, buffer, sizeof(buffer));
3893
Fred Drakec9680921999-12-13 16:37:25 +00003894 errno = 0;
3895 if (len == 0) {
3896 if (errno != 0)
3897 posix_error();
3898 else
3899 result = PyString_FromString("");
3900 }
3901 else {
3902 if (len >= sizeof(buffer)) {
3903 result = PyString_FromStringAndSize(NULL, len);
3904 if (result != NULL)
3905 confstr(name, PyString_AS_STRING(result), len+1);
3906 }
3907 else
3908 result = PyString_FromString(buffer);
3909 }
3910 }
3911 return result;
3912}
3913#endif
3914
3915
3916#ifdef HAVE_SYSCONF
3917static struct constdef posix_constants_sysconf[] = {
3918#ifdef _SC_2_CHAR_TERM
3919 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
3920#endif
3921#ifdef _SC_2_C_BIND
3922 {"SC_2_C_BIND", _SC_2_C_BIND},
3923#endif
3924#ifdef _SC_2_C_DEV
3925 {"SC_2_C_DEV", _SC_2_C_DEV},
3926#endif
3927#ifdef _SC_2_C_VERSION
3928 {"SC_2_C_VERSION", _SC_2_C_VERSION},
3929#endif
3930#ifdef _SC_2_FORT_DEV
3931 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
3932#endif
3933#ifdef _SC_2_FORT_RUN
3934 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
3935#endif
3936#ifdef _SC_2_LOCALEDEF
3937 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
3938#endif
3939#ifdef _SC_2_SW_DEV
3940 {"SC_2_SW_DEV", _SC_2_SW_DEV},
3941#endif
3942#ifdef _SC_2_UPE
3943 {"SC_2_UPE", _SC_2_UPE},
3944#endif
3945#ifdef _SC_2_VERSION
3946 {"SC_2_VERSION", _SC_2_VERSION},
3947#endif
Fred Draked86ed291999-12-15 15:34:33 +00003948#ifdef _SC_ABI_ASYNCHRONOUS_IO
3949 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
3950#endif
3951#ifdef _SC_ACL
3952 {"SC_ACL", _SC_ACL},
3953#endif
Fred Drakec9680921999-12-13 16:37:25 +00003954#ifdef _SC_AIO_LISTIO_MAX
3955 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
3956#endif
Fred Drakec9680921999-12-13 16:37:25 +00003957#ifdef _SC_AIO_MAX
3958 {"SC_AIO_MAX", _SC_AIO_MAX},
3959#endif
3960#ifdef _SC_AIO_PRIO_DELTA_MAX
3961 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
3962#endif
3963#ifdef _SC_ARG_MAX
3964 {"SC_ARG_MAX", _SC_ARG_MAX},
3965#endif
3966#ifdef _SC_ASYNCHRONOUS_IO
3967 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
3968#endif
3969#ifdef _SC_ATEXIT_MAX
3970 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
3971#endif
Fred Draked86ed291999-12-15 15:34:33 +00003972#ifdef _SC_AUDIT
3973 {"SC_AUDIT", _SC_AUDIT},
3974#endif
Fred Drakec9680921999-12-13 16:37:25 +00003975#ifdef _SC_AVPHYS_PAGES
3976 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
3977#endif
3978#ifdef _SC_BC_BASE_MAX
3979 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
3980#endif
3981#ifdef _SC_BC_DIM_MAX
3982 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
3983#endif
3984#ifdef _SC_BC_SCALE_MAX
3985 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
3986#endif
3987#ifdef _SC_BC_STRING_MAX
3988 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
3989#endif
Fred Draked86ed291999-12-15 15:34:33 +00003990#ifdef _SC_CAP
3991 {"SC_CAP", _SC_CAP},
3992#endif
Fred Drakec9680921999-12-13 16:37:25 +00003993#ifdef _SC_CHARCLASS_NAME_MAX
3994 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
3995#endif
3996#ifdef _SC_CHAR_BIT
3997 {"SC_CHAR_BIT", _SC_CHAR_BIT},
3998#endif
3999#ifdef _SC_CHAR_MAX
4000 {"SC_CHAR_MAX", _SC_CHAR_MAX},
4001#endif
4002#ifdef _SC_CHAR_MIN
4003 {"SC_CHAR_MIN", _SC_CHAR_MIN},
4004#endif
4005#ifdef _SC_CHILD_MAX
4006 {"SC_CHILD_MAX", _SC_CHILD_MAX},
4007#endif
4008#ifdef _SC_CLK_TCK
4009 {"SC_CLK_TCK", _SC_CLK_TCK},
4010#endif
4011#ifdef _SC_COHER_BLKSZ
4012 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
4013#endif
4014#ifdef _SC_COLL_WEIGHTS_MAX
4015 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
4016#endif
4017#ifdef _SC_DCACHE_ASSOC
4018 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
4019#endif
4020#ifdef _SC_DCACHE_BLKSZ
4021 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
4022#endif
4023#ifdef _SC_DCACHE_LINESZ
4024 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
4025#endif
4026#ifdef _SC_DCACHE_SZ
4027 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
4028#endif
4029#ifdef _SC_DCACHE_TBLKSZ
4030 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
4031#endif
4032#ifdef _SC_DELAYTIMER_MAX
4033 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
4034#endif
4035#ifdef _SC_EQUIV_CLASS_MAX
4036 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
4037#endif
4038#ifdef _SC_EXPR_NEST_MAX
4039 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
4040#endif
4041#ifdef _SC_FSYNC
4042 {"SC_FSYNC", _SC_FSYNC},
4043#endif
4044#ifdef _SC_GETGR_R_SIZE_MAX
4045 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
4046#endif
4047#ifdef _SC_GETPW_R_SIZE_MAX
4048 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
4049#endif
4050#ifdef _SC_ICACHE_ASSOC
4051 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
4052#endif
4053#ifdef _SC_ICACHE_BLKSZ
4054 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
4055#endif
4056#ifdef _SC_ICACHE_LINESZ
4057 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
4058#endif
4059#ifdef _SC_ICACHE_SZ
4060 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
4061#endif
Fred Draked86ed291999-12-15 15:34:33 +00004062#ifdef _SC_INF
4063 {"SC_INF", _SC_INF},
4064#endif
Fred Drakec9680921999-12-13 16:37:25 +00004065#ifdef _SC_INT_MAX
4066 {"SC_INT_MAX", _SC_INT_MAX},
4067#endif
4068#ifdef _SC_INT_MIN
4069 {"SC_INT_MIN", _SC_INT_MIN},
4070#endif
4071#ifdef _SC_IOV_MAX
4072 {"SC_IOV_MAX", _SC_IOV_MAX},
4073#endif
Fred Draked86ed291999-12-15 15:34:33 +00004074#ifdef _SC_IP_SECOPTS
4075 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
4076#endif
Fred Drakec9680921999-12-13 16:37:25 +00004077#ifdef _SC_JOB_CONTROL
4078 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
4079#endif
Fred Draked86ed291999-12-15 15:34:33 +00004080#ifdef _SC_KERN_POINTERS
4081 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
4082#endif
4083#ifdef _SC_KERN_SIM
4084 {"SC_KERN_SIM", _SC_KERN_SIM},
4085#endif
Fred Drakec9680921999-12-13 16:37:25 +00004086#ifdef _SC_LINE_MAX
4087 {"SC_LINE_MAX", _SC_LINE_MAX},
4088#endif
4089#ifdef _SC_LOGIN_NAME_MAX
4090 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
4091#endif
4092#ifdef _SC_LOGNAME_MAX
4093 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
4094#endif
4095#ifdef _SC_LONG_BIT
4096 {"SC_LONG_BIT", _SC_LONG_BIT},
4097#endif
Fred Draked86ed291999-12-15 15:34:33 +00004098#ifdef _SC_MAC
4099 {"SC_MAC", _SC_MAC},
4100#endif
Fred Drakec9680921999-12-13 16:37:25 +00004101#ifdef _SC_MAPPED_FILES
4102 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
4103#endif
4104#ifdef _SC_MAXPID
4105 {"SC_MAXPID", _SC_MAXPID},
4106#endif
4107#ifdef _SC_MB_LEN_MAX
4108 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
4109#endif
4110#ifdef _SC_MEMLOCK
4111 {"SC_MEMLOCK", _SC_MEMLOCK},
4112#endif
4113#ifdef _SC_MEMLOCK_RANGE
4114 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
4115#endif
4116#ifdef _SC_MEMORY_PROTECTION
4117 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
4118#endif
4119#ifdef _SC_MESSAGE_PASSING
4120 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
4121#endif
Fred Draked86ed291999-12-15 15:34:33 +00004122#ifdef _SC_MMAP_FIXED_ALIGNMENT
4123 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
4124#endif
Fred Drakec9680921999-12-13 16:37:25 +00004125#ifdef _SC_MQ_OPEN_MAX
4126 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
4127#endif
4128#ifdef _SC_MQ_PRIO_MAX
4129 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
4130#endif
Fred Draked86ed291999-12-15 15:34:33 +00004131#ifdef _SC_NACLS_MAX
4132 {"SC_NACLS_MAX", _SC_NACLS_MAX},
4133#endif
Fred Drakec9680921999-12-13 16:37:25 +00004134#ifdef _SC_NGROUPS_MAX
4135 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
4136#endif
4137#ifdef _SC_NL_ARGMAX
4138 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
4139#endif
4140#ifdef _SC_NL_LANGMAX
4141 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
4142#endif
4143#ifdef _SC_NL_MSGMAX
4144 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
4145#endif
4146#ifdef _SC_NL_NMAX
4147 {"SC_NL_NMAX", _SC_NL_NMAX},
4148#endif
4149#ifdef _SC_NL_SETMAX
4150 {"SC_NL_SETMAX", _SC_NL_SETMAX},
4151#endif
4152#ifdef _SC_NL_TEXTMAX
4153 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
4154#endif
4155#ifdef _SC_NPROCESSORS_CONF
4156 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
4157#endif
4158#ifdef _SC_NPROCESSORS_ONLN
4159 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
4160#endif
Fred Draked86ed291999-12-15 15:34:33 +00004161#ifdef _SC_NPROC_CONF
4162 {"SC_NPROC_CONF", _SC_NPROC_CONF},
4163#endif
4164#ifdef _SC_NPROC_ONLN
4165 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
4166#endif
Fred Drakec9680921999-12-13 16:37:25 +00004167#ifdef _SC_NZERO
4168 {"SC_NZERO", _SC_NZERO},
4169#endif
4170#ifdef _SC_OPEN_MAX
4171 {"SC_OPEN_MAX", _SC_OPEN_MAX},
4172#endif
4173#ifdef _SC_PAGESIZE
4174 {"SC_PAGESIZE", _SC_PAGESIZE},
4175#endif
4176#ifdef _SC_PAGE_SIZE
4177 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
4178#endif
4179#ifdef _SC_PASS_MAX
4180 {"SC_PASS_MAX", _SC_PASS_MAX},
4181#endif
4182#ifdef _SC_PHYS_PAGES
4183 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
4184#endif
4185#ifdef _SC_PII
4186 {"SC_PII", _SC_PII},
4187#endif
4188#ifdef _SC_PII_INTERNET
4189 {"SC_PII_INTERNET", _SC_PII_INTERNET},
4190#endif
4191#ifdef _SC_PII_INTERNET_DGRAM
4192 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
4193#endif
4194#ifdef _SC_PII_INTERNET_STREAM
4195 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
4196#endif
4197#ifdef _SC_PII_OSI
4198 {"SC_PII_OSI", _SC_PII_OSI},
4199#endif
4200#ifdef _SC_PII_OSI_CLTS
4201 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
4202#endif
4203#ifdef _SC_PII_OSI_COTS
4204 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
4205#endif
4206#ifdef _SC_PII_OSI_M
4207 {"SC_PII_OSI_M", _SC_PII_OSI_M},
4208#endif
4209#ifdef _SC_PII_SOCKET
4210 {"SC_PII_SOCKET", _SC_PII_SOCKET},
4211#endif
4212#ifdef _SC_PII_XTI
4213 {"SC_PII_XTI", _SC_PII_XTI},
4214#endif
4215#ifdef _SC_POLL
4216 {"SC_POLL", _SC_POLL},
4217#endif
4218#ifdef _SC_PRIORITIZED_IO
4219 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
4220#endif
4221#ifdef _SC_PRIORITY_SCHEDULING
4222 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
4223#endif
4224#ifdef _SC_REALTIME_SIGNALS
4225 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
4226#endif
4227#ifdef _SC_RE_DUP_MAX
4228 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
4229#endif
4230#ifdef _SC_RTSIG_MAX
4231 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
4232#endif
4233#ifdef _SC_SAVED_IDS
4234 {"SC_SAVED_IDS", _SC_SAVED_IDS},
4235#endif
4236#ifdef _SC_SCHAR_MAX
4237 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
4238#endif
4239#ifdef _SC_SCHAR_MIN
4240 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
4241#endif
4242#ifdef _SC_SELECT
4243 {"SC_SELECT", _SC_SELECT},
4244#endif
4245#ifdef _SC_SEMAPHORES
4246 {"SC_SEMAPHORES", _SC_SEMAPHORES},
4247#endif
4248#ifdef _SC_SEM_NSEMS_MAX
4249 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
4250#endif
4251#ifdef _SC_SEM_VALUE_MAX
4252 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
4253#endif
4254#ifdef _SC_SHARED_MEMORY_OBJECTS
4255 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
4256#endif
4257#ifdef _SC_SHRT_MAX
4258 {"SC_SHRT_MAX", _SC_SHRT_MAX},
4259#endif
4260#ifdef _SC_SHRT_MIN
4261 {"SC_SHRT_MIN", _SC_SHRT_MIN},
4262#endif
4263#ifdef _SC_SIGQUEUE_MAX
4264 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
4265#endif
4266#ifdef _SC_SIGRT_MAX
4267 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
4268#endif
4269#ifdef _SC_SIGRT_MIN
4270 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
4271#endif
Fred Draked86ed291999-12-15 15:34:33 +00004272#ifdef _SC_SOFTPOWER
4273 {"SC_SOFTPOWER", _SC_SOFTPOWER},
4274#endif
Fred Drakec9680921999-12-13 16:37:25 +00004275#ifdef _SC_SPLIT_CACHE
4276 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
4277#endif
4278#ifdef _SC_SSIZE_MAX
4279 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
4280#endif
4281#ifdef _SC_STACK_PROT
4282 {"SC_STACK_PROT", _SC_STACK_PROT},
4283#endif
4284#ifdef _SC_STREAM_MAX
4285 {"SC_STREAM_MAX", _SC_STREAM_MAX},
4286#endif
4287#ifdef _SC_SYNCHRONIZED_IO
4288 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
4289#endif
4290#ifdef _SC_THREADS
4291 {"SC_THREADS", _SC_THREADS},
4292#endif
4293#ifdef _SC_THREAD_ATTR_STACKADDR
4294 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
4295#endif
4296#ifdef _SC_THREAD_ATTR_STACKSIZE
4297 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
4298#endif
4299#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
4300 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
4301#endif
4302#ifdef _SC_THREAD_KEYS_MAX
4303 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
4304#endif
4305#ifdef _SC_THREAD_PRIORITY_SCHEDULING
4306 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
4307#endif
4308#ifdef _SC_THREAD_PRIO_INHERIT
4309 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
4310#endif
4311#ifdef _SC_THREAD_PRIO_PROTECT
4312 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
4313#endif
4314#ifdef _SC_THREAD_PROCESS_SHARED
4315 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
4316#endif
4317#ifdef _SC_THREAD_SAFE_FUNCTIONS
4318 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
4319#endif
4320#ifdef _SC_THREAD_STACK_MIN
4321 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
4322#endif
4323#ifdef _SC_THREAD_THREADS_MAX
4324 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
4325#endif
4326#ifdef _SC_TIMERS
4327 {"SC_TIMERS", _SC_TIMERS},
4328#endif
4329#ifdef _SC_TIMER_MAX
4330 {"SC_TIMER_MAX", _SC_TIMER_MAX},
4331#endif
4332#ifdef _SC_TTY_NAME_MAX
4333 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
4334#endif
4335#ifdef _SC_TZNAME_MAX
4336 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
4337#endif
4338#ifdef _SC_T_IOV_MAX
4339 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
4340#endif
4341#ifdef _SC_UCHAR_MAX
4342 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
4343#endif
4344#ifdef _SC_UINT_MAX
4345 {"SC_UINT_MAX", _SC_UINT_MAX},
4346#endif
4347#ifdef _SC_UIO_MAXIOV
4348 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
4349#endif
4350#ifdef _SC_ULONG_MAX
4351 {"SC_ULONG_MAX", _SC_ULONG_MAX},
4352#endif
4353#ifdef _SC_USHRT_MAX
4354 {"SC_USHRT_MAX", _SC_USHRT_MAX},
4355#endif
4356#ifdef _SC_VERSION
4357 {"SC_VERSION", _SC_VERSION},
4358#endif
4359#ifdef _SC_WORD_BIT
4360 {"SC_WORD_BIT", _SC_WORD_BIT},
4361#endif
4362#ifdef _SC_XBS5_ILP32_OFF32
4363 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
4364#endif
4365#ifdef _SC_XBS5_ILP32_OFFBIG
4366 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
4367#endif
4368#ifdef _SC_XBS5_LP64_OFF64
4369 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
4370#endif
4371#ifdef _SC_XBS5_LPBIG_OFFBIG
4372 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
4373#endif
4374#ifdef _SC_XOPEN_CRYPT
4375 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
4376#endif
4377#ifdef _SC_XOPEN_ENH_I18N
4378 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
4379#endif
4380#ifdef _SC_XOPEN_LEGACY
4381 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
4382#endif
4383#ifdef _SC_XOPEN_REALTIME
4384 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
4385#endif
4386#ifdef _SC_XOPEN_REALTIME_THREADS
4387 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
4388#endif
4389#ifdef _SC_XOPEN_SHM
4390 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
4391#endif
4392#ifdef _SC_XOPEN_UNIX
4393 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
4394#endif
4395#ifdef _SC_XOPEN_VERSION
4396 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
4397#endif
4398#ifdef _SC_XOPEN_XCU_VERSION
4399 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
4400#endif
4401#ifdef _SC_XOPEN_XPG2
4402 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
4403#endif
4404#ifdef _SC_XOPEN_XPG3
4405 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
4406#endif
4407#ifdef _SC_XOPEN_XPG4
4408 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
4409#endif
4410};
4411
4412static int
4413conv_sysconf_confname(arg, valuep)
4414 PyObject *arg;
4415 int *valuep;
4416{
4417 return conv_confname(arg, valuep, posix_constants_sysconf,
4418 sizeof(posix_constants_sysconf)
4419 / sizeof(struct constdef));
4420}
4421
4422static char posix_sysconf__doc__[] = "\
4423sysconf(name) -> integer\n\
4424Return an integer-valued system configuration variable.";
4425
4426static PyObject *
4427posix_sysconf(self, args)
4428 PyObject *self;
4429 PyObject *args;
4430{
4431 PyObject *result = NULL;
4432 int name;
4433
4434 if (PyArg_ParseTuple(args, "O&:sysconf", conv_sysconf_confname, &name)) {
4435 int value;
4436
4437 errno = 0;
4438 value = sysconf(name);
4439 if (value == -1 && errno != 0)
4440 posix_error();
4441 else
4442 result = PyInt_FromLong(value);
4443 }
4444 return result;
4445}
4446#endif
4447
4448
Fred Drakebec628d1999-12-15 18:31:10 +00004449/* This code is used to ensure that the tables of configuration value names
4450 * are in sorted order as required by conv_confname(), and also to build the
4451 * the exported dictionaries that are used to publish information about the
4452 * names available on the host platform.
4453 *
4454 * Sorting the table at runtime ensures that the table is properly ordered
4455 * when used, even for platforms we're not able to test on. It also makes
4456 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +00004457 */
Fred Drakebec628d1999-12-15 18:31:10 +00004458
4459static int
4460cmp_constdefs(v1, v2)
4461 const void *v1;
4462 const void *v2;
4463{
4464 const struct constdef *c1 =
4465 (const struct constdef *) v1;
4466 const struct constdef *c2 =
4467 (const struct constdef *) v2;
4468
4469 return strcmp(c1->name, c2->name);
4470}
4471
4472static int
4473setup_confname_table(table, tablesize, tablename, moddict)
Fred Draked86ed291999-12-15 15:34:33 +00004474 struct constdef *table;
4475 size_t tablesize;
Fred Drakebec628d1999-12-15 18:31:10 +00004476 char * tablename;
4477 PyObject *moddict;
Fred Draked86ed291999-12-15 15:34:33 +00004478{
Fred Drakebec628d1999-12-15 18:31:10 +00004479 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +00004480 size_t i;
4481 int status;
Fred Drakebec628d1999-12-15 18:31:10 +00004482
4483 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
4484 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +00004485 if (d == NULL)
4486 return -1;
Fred Draked86ed291999-12-15 15:34:33 +00004487
Barry Warsaw3155db32000-04-13 15:20:40 +00004488 for (i=0; i < tablesize; ++i) {
4489 PyObject *o = PyInt_FromLong(table[i].value);
4490 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
4491 Py_XDECREF(o);
4492 Py_DECREF(d);
4493 return -1;
Fred Draked86ed291999-12-15 15:34:33 +00004494 }
Barry Warsaw3155db32000-04-13 15:20:40 +00004495 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +00004496 }
Barry Warsaw3155db32000-04-13 15:20:40 +00004497 status = PyDict_SetItemString(moddict, tablename, d);
4498 Py_DECREF(d);
4499 return status;
Fred Draked86ed291999-12-15 15:34:33 +00004500}
4501
Fred Drakebec628d1999-12-15 18:31:10 +00004502/* Return -1 on failure, 0 on success. */
4503static int
4504setup_confname_tables(moddict)
4505 PyObject *moddict;
Fred Draked86ed291999-12-15 15:34:33 +00004506{
4507#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +00004508 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +00004509 sizeof(posix_constants_pathconf)
4510 / sizeof(struct constdef),
Fred Drakebec628d1999-12-15 18:31:10 +00004511 "pathconf_names", moddict))
4512 return -1;
Fred Draked86ed291999-12-15 15:34:33 +00004513#endif
4514#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +00004515 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +00004516 sizeof(posix_constants_confstr)
4517 / sizeof(struct constdef),
Fred Drakebec628d1999-12-15 18:31:10 +00004518 "confstr_names", moddict))
4519 return -1;
Fred Draked86ed291999-12-15 15:34:33 +00004520#endif
4521#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +00004522 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +00004523 sizeof(posix_constants_sysconf)
4524 / sizeof(struct constdef),
Fred Drakebec628d1999-12-15 18:31:10 +00004525 "sysconf_names", moddict))
4526 return -1;
Fred Draked86ed291999-12-15 15:34:33 +00004527#endif
Fred Drakebec628d1999-12-15 18:31:10 +00004528 return 0;
Fred Draked86ed291999-12-15 15:34:33 +00004529}
Fred Draked86ed291999-12-15 15:34:33 +00004530
4531
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004532static char posix_abort__doc__[] = "\
4533abort() -> does not return!\n\
4534Abort the interpreter immediately. This 'dumps core' or otherwise fails\n\
4535in the hardest way possible on the hosting operating system.";
4536
4537static PyObject *
4538posix_abort(self, args)
4539 PyObject *self;
4540 PyObject *args;
4541{
4542 if (!PyArg_ParseTuple(args, ":abort"))
4543 return NULL;
4544 abort();
4545 /*NOTREACHED*/
4546 Py_FatalError("abort() called from Python code didn't abort!");
4547 return NULL;
4548}
Fred Drakebec628d1999-12-15 18:31:10 +00004549
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004550
4551static PyMethodDef posix_methods[] = {
4552 {"access", posix_access, METH_VARARGS, posix_access__doc__},
4553#ifdef HAVE_TTYNAME
4554 {"ttyname", posix_ttyname, METH_VARARGS, posix_ttyname__doc__},
4555#endif
4556 {"chdir", posix_chdir, METH_VARARGS, posix_chdir__doc__},
4557 {"chmod", posix_chmod, METH_VARARGS, posix_chmod__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004558#ifdef HAVE_CHOWN
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004559 {"chown", posix_chown, METH_VARARGS, posix_chown__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004560#endif /* HAVE_CHOWN */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004561#ifdef HAVE_CTERMID
4562 {"ctermid", posix_ctermid, METH_VARARGS, posix_ctermid__doc__},
4563#endif
Guido van Rossum36bc6801995-06-14 22:54:23 +00004564#ifdef HAVE_GETCWD
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004565 {"getcwd", posix_getcwd, METH_VARARGS, posix_getcwd__doc__},
Guido van Rossum36bc6801995-06-14 22:54:23 +00004566#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +00004567#ifdef HAVE_LINK
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004568 {"link", posix_link, METH_VARARGS, posix_link__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004569#endif /* HAVE_LINK */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004570 {"listdir", posix_listdir, METH_VARARGS, posix_listdir__doc__},
4571 {"lstat", posix_lstat, METH_VARARGS, posix_lstat__doc__},
4572 {"mkdir", posix_mkdir, METH_VARARGS, posix_mkdir__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004573#ifdef HAVE_NICE
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004574 {"nice", posix_nice, METH_VARARGS, posix_nice__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004575#endif /* HAVE_NICE */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004576#ifdef HAVE_READLINK
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004577 {"readlink", posix_readlink, METH_VARARGS, posix_readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004578#endif /* HAVE_READLINK */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004579 {"rename", posix_rename, METH_VARARGS, posix_rename__doc__},
4580 {"rmdir", posix_rmdir, METH_VARARGS, posix_rmdir__doc__},
4581 {"stat", posix_stat, METH_VARARGS, posix_stat__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004582#ifdef HAVE_SYMLINK
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004583 {"symlink", posix_symlink, METH_VARARGS, posix_symlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004584#endif /* HAVE_SYMLINK */
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004585#ifdef HAVE_SYSTEM
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004586 {"system", posix_system, METH_VARARGS, posix_system__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004587#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004588 {"umask", posix_umask, METH_VARARGS, posix_umask__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004589#ifdef HAVE_UNAME
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004590 {"uname", posix_uname, METH_VARARGS, posix_uname__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004591#endif /* HAVE_UNAME */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004592 {"unlink", posix_unlink, METH_VARARGS, posix_unlink__doc__},
4593 {"remove", posix_unlink, METH_VARARGS, posix_remove__doc__},
4594 {"utime", posix_utime, METH_VARARGS, posix_utime__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004595#ifdef HAVE_TIMES
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004596 {"times", posix_times, METH_VARARGS, posix_times__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004597#endif /* HAVE_TIMES */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004598 {"_exit", posix__exit, METH_VARARGS, posix__exit__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004599#ifdef HAVE_EXECV
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004600 {"execv", posix_execv, METH_VARARGS, posix_execv__doc__},
4601 {"execve", posix_execve, METH_VARARGS, posix_execve__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004602#endif /* HAVE_EXECV */
Guido van Rossuma1065681999-01-25 23:20:23 +00004603#ifdef HAVE_SPAWNV
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004604 {"spawnv", posix_spawnv, METH_VARARGS, posix_spawnv__doc__},
4605 {"spawnve", posix_spawnve, METH_VARARGS, posix_spawnve__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00004606#endif /* HAVE_SPAWNV */
Guido van Rossumad0ee831995-03-01 10:34:45 +00004607#ifdef HAVE_FORK
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004608 {"fork", posix_fork, METH_VARARGS, posix_fork__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004609#endif /* HAVE_FORK */
Fred Drake8cef4cf2000-06-28 16:40:38 +00004610#ifdef HAVE_OPENPTY
4611 {"openpty", posix_openpty, METH_VARARGS, posix_openpty__doc__},
4612#endif /* HAVE_OPENPTY */
4613#ifdef HAVE_FORKPTY
4614 {"forkpty", posix_forkpty, METH_VARARGS, posix_forkpty__doc__},
4615#endif /* HAVE_FORKPTY */
Guido van Rossumad0ee831995-03-01 10:34:45 +00004616#ifdef HAVE_GETEGID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004617 {"getegid", posix_getegid, METH_VARARGS, posix_getegid__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004618#endif /* HAVE_GETEGID */
4619#ifdef HAVE_GETEUID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004620 {"geteuid", posix_geteuid, METH_VARARGS, posix_geteuid__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004621#endif /* HAVE_GETEUID */
4622#ifdef HAVE_GETGID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004623 {"getgid", posix_getgid, METH_VARARGS, posix_getgid__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004624#endif /* HAVE_GETGID */
Fred Drakec9680921999-12-13 16:37:25 +00004625#ifdef HAVE_GETGROUPS
4626 {"getgroups", posix_getgroups, METH_VARARGS, posix_getgroups__doc__},
4627#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004628 {"getpid", posix_getpid, METH_VARARGS, posix_getpid__doc__},
Guido van Rossumb6775db1994-08-01 11:34:53 +00004629#ifdef HAVE_GETPGRP
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004630 {"getpgrp", posix_getpgrp, METH_VARARGS, posix_getpgrp__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004631#endif /* HAVE_GETPGRP */
Guido van Rossumad0ee831995-03-01 10:34:45 +00004632#ifdef HAVE_GETPPID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004633 {"getppid", posix_getppid, METH_VARARGS, posix_getppid__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004634#endif /* HAVE_GETPPID */
4635#ifdef HAVE_GETUID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004636 {"getuid", posix_getuid, METH_VARARGS, posix_getuid__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004637#endif /* HAVE_GETUID */
Fred Drake12c6e2d1999-12-14 21:25:03 +00004638#ifdef HAVE_GETLOGIN
4639 {"getlogin", posix_getlogin, METH_VARARGS, posix_getlogin__doc__},
4640#endif
Guido van Rossumad0ee831995-03-01 10:34:45 +00004641#ifdef HAVE_KILL
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004642 {"kill", posix_kill, METH_VARARGS, posix_kill__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004643#endif /* HAVE_KILL */
Guido van Rossumc0125471996-06-28 18:55:32 +00004644#ifdef HAVE_PLOCK
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004645 {"plock", posix_plock, METH_VARARGS, posix_plock__doc__},
Guido van Rossumc0125471996-06-28 18:55:32 +00004646#endif /* HAVE_PLOCK */
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004647#ifdef HAVE_POPEN
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004648 {"popen", posix_popen, METH_VARARGS, posix_popen__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004649#endif /* HAVE_POPEN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004650#ifdef HAVE_SETUID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004651 {"setuid", posix_setuid, METH_VARARGS, posix_setuid__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004652#endif /* HAVE_SETUID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004653#ifdef HAVE_SETGID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004654 {"setgid", posix_setgid, METH_VARARGS, posix_setgid__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004655#endif /* HAVE_SETGID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004656#ifdef HAVE_SETPGRP
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004657 {"setpgrp", posix_setpgrp, METH_VARARGS, posix_setpgrp__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004658#endif /* HAVE_SETPGRP */
Guido van Rossumad0ee831995-03-01 10:34:45 +00004659#ifdef HAVE_WAIT
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004660 {"wait", posix_wait, METH_VARARGS, posix_wait__doc__},
Guido van Rossumad0ee831995-03-01 10:34:45 +00004661#endif /* HAVE_WAIT */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004662#ifdef HAVE_WAITPID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004663 {"waitpid", posix_waitpid, METH_VARARGS, posix_waitpid__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004664#endif /* HAVE_WAITPID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004665#ifdef HAVE_SETSID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004666 {"setsid", posix_setsid, METH_VARARGS, posix_setsid__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004667#endif /* HAVE_SETSID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004668#ifdef HAVE_SETPGID
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004669 {"setpgid", posix_setpgid, METH_VARARGS, posix_setpgid__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004670#endif /* HAVE_SETPGID */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004671#ifdef HAVE_TCGETPGRP
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004672 {"tcgetpgrp", posix_tcgetpgrp, METH_VARARGS, posix_tcgetpgrp__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004673#endif /* HAVE_TCGETPGRP */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004674#ifdef HAVE_TCSETPGRP
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004675 {"tcsetpgrp", posix_tcsetpgrp, METH_VARARGS, posix_tcsetpgrp__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004676#endif /* HAVE_TCSETPGRP */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004677 {"open", posix_open, METH_VARARGS, posix_open__doc__},
4678 {"close", posix_close, METH_VARARGS, posix_close__doc__},
4679 {"dup", posix_dup, METH_VARARGS, posix_dup__doc__},
4680 {"dup2", posix_dup2, METH_VARARGS, posix_dup2__doc__},
4681 {"lseek", posix_lseek, METH_VARARGS, posix_lseek__doc__},
4682 {"read", posix_read, METH_VARARGS, posix_read__doc__},
4683 {"write", posix_write, METH_VARARGS, posix_write__doc__},
4684 {"fstat", posix_fstat, METH_VARARGS, posix_fstat__doc__},
4685 {"fdopen", posix_fdopen, METH_VARARGS, posix_fdopen__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004686#ifdef HAVE_PIPE
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004687 {"pipe", posix_pipe, METH_VARARGS, posix_pipe__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004688#endif
4689#ifdef HAVE_MKFIFO
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004690 {"mkfifo", posix_mkfifo, METH_VARARGS, posix_mkfifo__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004691#endif
4692#ifdef HAVE_FTRUNCATE
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004693 {"ftruncate", posix_ftruncate, METH_VARARGS, posix_ftruncate__doc__},
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004694#endif
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00004695#ifdef HAVE_PUTENV
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004696 {"putenv", posix_putenv, METH_VARARGS, posix_putenv__doc__},
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00004697#endif
Guido van Rossumb6a47161997-09-15 22:54:34 +00004698#ifdef HAVE_STRERROR
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004699 {"strerror", posix_strerror, METH_VARARGS, posix_strerror__doc__},
Guido van Rossumb6a47161997-09-15 22:54:34 +00004700#endif
Guido van Rossum21142a01999-01-08 21:05:37 +00004701#ifdef HAVE_FSYNC
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004702 {"fsync", posix_fsync, METH_VARARGS, posix_fsync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00004703#endif
4704#ifdef HAVE_FDATASYNC
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004705 {"fdatasync", posix_fdatasync, METH_VARARGS, posix_fdatasync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00004706#endif
Guido van Rossumc9641791998-08-04 15:26:23 +00004707#ifdef HAVE_SYS_WAIT_H
4708#ifdef WIFSTOPPED
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004709 {"WIFSTOPPED", posix_WIFSTOPPED, METH_VARARGS, posix_WIFSTOPPED__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004710#endif /* WIFSTOPPED */
4711#ifdef WIFSIGNALED
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004712 {"WIFSIGNALED", posix_WIFSIGNALED, METH_VARARGS, posix_WIFSIGNALED__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004713#endif /* WIFSIGNALED */
4714#ifdef WIFEXITED
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004715 {"WIFEXITED", posix_WIFEXITED, METH_VARARGS, posix_WIFEXITED__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004716#endif /* WIFEXITED */
4717#ifdef WEXITSTATUS
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004718 {"WEXITSTATUS", posix_WEXITSTATUS, METH_VARARGS, posix_WEXITSTATUS__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004719#endif /* WEXITSTATUS */
4720#ifdef WTERMSIG
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004721 {"WTERMSIG", posix_WTERMSIG, METH_VARARGS, posix_WTERMSIG__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004722#endif /* WTERMSIG */
4723#ifdef WSTOPSIG
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004724 {"WSTOPSIG", posix_WSTOPSIG, METH_VARARGS, posix_WSTOPSIG__doc__},
Guido van Rossumc9641791998-08-04 15:26:23 +00004725#endif /* WSTOPSIG */
4726#endif /* HAVE_SYS_WAIT_H */
Guido van Rossum94f6f721999-01-06 18:42:14 +00004727#ifdef HAVE_FSTATVFS
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004728 {"fstatvfs", posix_fstatvfs, METH_VARARGS, posix_fstatvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +00004729#endif
4730#ifdef HAVE_STATVFS
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004731 {"statvfs", posix_statvfs, METH_VARARGS, posix_statvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +00004732#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004733#ifdef HAVE_TMPNAM
4734 {"tmpfile", posix_tmpfile, METH_VARARGS, posix_tmpfile__doc__},
4735#endif
4736#ifdef HAVE_TEMPNAM
4737 {"tempnam", posix_tempnam, METH_VARARGS, posix_tempnam__doc__},
4738#endif
4739#ifdef HAVE_TMPNAM
4740 {"tmpnam", posix_tmpnam, METH_VARARGS, posix_tmpnam__doc__},
4741#endif
Fred Drakec9680921999-12-13 16:37:25 +00004742#ifdef HAVE_CONFSTR
4743 {"confstr", posix_confstr, METH_VARARGS, posix_confstr__doc__},
4744#endif
4745#ifdef HAVE_SYSCONF
4746 {"sysconf", posix_sysconf, METH_VARARGS, posix_sysconf__doc__},
4747#endif
4748#ifdef HAVE_FPATHCONF
4749 {"fpathconf", posix_fpathconf, METH_VARARGS, posix_fpathconf__doc__},
4750#endif
4751#ifdef HAVE_PATHCONF
4752 {"pathconf", posix_pathconf, METH_VARARGS, posix_pathconf__doc__},
4753#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004754 {"abort", posix_abort, METH_VARARGS, posix_abort__doc__},
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004755 {NULL, NULL} /* Sentinel */
4756};
4757
4758
Barry Warsaw4a342091996-12-19 23:50:02 +00004759static int
4760ins(d, symbol, value)
4761 PyObject* d;
4762 char* symbol;
4763 long value;
4764{
4765 PyObject* v = PyInt_FromLong(value);
4766 if (!v || PyDict_SetItemString(d, symbol, v) < 0)
4767 return -1; /* triggers fatal error */
4768
4769 Py_DECREF(v);
4770 return 0;
4771}
4772
Guido van Rossumd48f2521997-12-05 22:19:34 +00004773#if defined(PYOS_OS2)
4774/* Insert Platform-Specific Constant Values (Strings & Numbers) of Common Use */
4775static int insertvalues(PyObject *d)
4776{
4777 APIRET rc;
4778 ULONG values[QSV_MAX+1];
4779 PyObject *v;
4780 char *ver, tmp[10];
4781
4782 Py_BEGIN_ALLOW_THREADS
4783 rc = DosQuerySysInfo(1, QSV_MAX, &values[1], sizeof(values));
4784 Py_END_ALLOW_THREADS
4785
4786 if (rc != NO_ERROR) {
4787 os2_error(rc);
4788 return -1;
4789 }
4790
4791 if (ins(d, "meminstalled", values[QSV_TOTPHYSMEM])) return -1;
4792 if (ins(d, "memkernel", values[QSV_TOTRESMEM])) return -1;
4793 if (ins(d, "memvirtual", values[QSV_TOTAVAILMEM])) return -1;
4794 if (ins(d, "maxpathlen", values[QSV_MAX_PATH_LENGTH])) return -1;
4795 if (ins(d, "maxnamelen", values[QSV_MAX_COMP_LENGTH])) return -1;
4796 if (ins(d, "revision", values[QSV_VERSION_REVISION])) return -1;
4797 if (ins(d, "timeslice", values[QSV_MIN_SLICE])) return -1;
4798
4799 switch (values[QSV_VERSION_MINOR]) {
4800 case 0: ver = "2.00"; break;
4801 case 10: ver = "2.10"; break;
4802 case 11: ver = "2.11"; break;
4803 case 30: ver = "3.00"; break;
4804 case 40: ver = "4.00"; break;
4805 case 50: ver = "5.00"; break;
4806 default:
4807 sprintf(tmp, "%d-%d", values[QSV_VERSION_MAJOR],
4808 values[QSV_VERSION_MINOR]);
4809 ver = &tmp[0];
4810 }
4811
4812 /* Add Indicator of the Version of the Operating System */
4813 v = PyString_FromString(ver);
4814 if (!v || PyDict_SetItemString(d, "version", v) < 0)
4815 return -1;
4816 Py_DECREF(v);
4817
4818 /* Add Indicator of Which Drive was Used to Boot the System */
4819 tmp[0] = 'A' + values[QSV_BOOT_DRIVE] - 1;
4820 tmp[1] = ':';
4821 tmp[2] = '\0';
4822
4823 v = PyString_FromString(tmp);
4824 if (!v || PyDict_SetItemString(d, "bootdrive", v) < 0)
4825 return -1;
4826 Py_DECREF(v);
4827
4828 return 0;
4829}
4830#endif
4831
Barry Warsaw4a342091996-12-19 23:50:02 +00004832static int
4833all_ins(d)
4834 PyObject* d;
4835{
Guido van Rossum94f6f721999-01-06 18:42:14 +00004836#ifdef F_OK
4837 if (ins(d, "F_OK", (long)F_OK)) return -1;
4838#endif
4839#ifdef R_OK
4840 if (ins(d, "R_OK", (long)R_OK)) return -1;
4841#endif
4842#ifdef W_OK
4843 if (ins(d, "W_OK", (long)W_OK)) return -1;
4844#endif
4845#ifdef X_OK
4846 if (ins(d, "X_OK", (long)X_OK)) return -1;
4847#endif
Fred Drakec9680921999-12-13 16:37:25 +00004848#ifdef NGROUPS_MAX
4849 if (ins(d, "NGROUPS_MAX", (long)NGROUPS_MAX)) return -1;
4850#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +00004851#ifdef TMP_MAX
4852 if (ins(d, "TMP_MAX", (long)TMP_MAX)) return -1;
4853#endif
Barry Warsaw4a342091996-12-19 23:50:02 +00004854#ifdef WNOHANG
4855 if (ins(d, "WNOHANG", (long)WNOHANG)) return -1;
4856#endif
4857#ifdef O_RDONLY
4858 if (ins(d, "O_RDONLY", (long)O_RDONLY)) return -1;
4859#endif
4860#ifdef O_WRONLY
4861 if (ins(d, "O_WRONLY", (long)O_WRONLY)) return -1;
4862#endif
4863#ifdef O_RDWR
4864 if (ins(d, "O_RDWR", (long)O_RDWR)) return -1;
4865#endif
4866#ifdef O_NDELAY
4867 if (ins(d, "O_NDELAY", (long)O_NDELAY)) return -1;
4868#endif
4869#ifdef O_NONBLOCK
4870 if (ins(d, "O_NONBLOCK", (long)O_NONBLOCK)) return -1;
4871#endif
4872#ifdef O_APPEND
4873 if (ins(d, "O_APPEND", (long)O_APPEND)) return -1;
4874#endif
4875#ifdef O_DSYNC
4876 if (ins(d, "O_DSYNC", (long)O_DSYNC)) return -1;
4877#endif
4878#ifdef O_RSYNC
4879 if (ins(d, "O_RSYNC", (long)O_RSYNC)) return -1;
4880#endif
4881#ifdef O_SYNC
4882 if (ins(d, "O_SYNC", (long)O_SYNC)) return -1;
4883#endif
4884#ifdef O_NOCTTY
4885 if (ins(d, "O_NOCTTY", (long)O_NOCTTY)) return -1;
4886#endif
4887#ifdef O_CREAT
4888 if (ins(d, "O_CREAT", (long)O_CREAT)) return -1;
4889#endif
4890#ifdef O_EXCL
4891 if (ins(d, "O_EXCL", (long)O_EXCL)) return -1;
4892#endif
4893#ifdef O_TRUNC
4894 if (ins(d, "O_TRUNC", (long)O_TRUNC)) return -1;
4895#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +00004896#ifdef O_BINARY
4897 if (ins(d, "O_BINARY", (long)O_BINARY)) return -1;
4898#endif
4899#ifdef O_TEXT
4900 if (ins(d, "O_TEXT", (long)O_TEXT)) return -1;
4901#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00004902
Guido van Rossum246bc171999-02-01 23:54:31 +00004903#ifdef HAVE_SPAWNV
Guido van Rossum7d385291999-02-16 19:38:04 +00004904 if (ins(d, "P_WAIT", (long)_P_WAIT)) return -1;
4905 if (ins(d, "P_NOWAIT", (long)_P_NOWAIT)) return -1;
4906 if (ins(d, "P_OVERLAY", (long)_OLD_P_OVERLAY)) return -1;
4907 if (ins(d, "P_NOWAITO", (long)_P_NOWAITO)) return -1;
4908 if (ins(d, "P_DETACH", (long)_P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +00004909#endif
4910
Guido van Rossumd48f2521997-12-05 22:19:34 +00004911#if defined(PYOS_OS2)
4912 if (insertvalues(d)) return -1;
4913#endif
Barry Warsaw4a342091996-12-19 23:50:02 +00004914 return 0;
4915}
4916
4917
Guido van Rossumc5a0f531997-12-02 20:36:02 +00004918#if ( defined(_MSC_VER) || defined(__WATCOMC__) ) && !defined(__QNX__)
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004919#define INITFUNC initnt
4920#define MODNAME "nt"
4921#else
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00004922#if defined(PYOS_OS2)
4923#define INITFUNC initos2
4924#define MODNAME "os2"
4925#else
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004926#define INITFUNC initposix
4927#define MODNAME "posix"
4928#endif
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +00004929#endif
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004930
Guido van Rossum3886bb61998-12-04 18:50:17 +00004931DL_EXPORT(void)
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004932INITFUNC()
Guido van Rossumb6775db1994-08-01 11:34:53 +00004933{
Barry Warsaw53699e91996-12-10 23:23:01 +00004934 PyObject *m, *d, *v;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004935
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004936 m = Py_InitModule4(MODNAME,
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004937 posix_methods,
4938 posix__doc__,
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004939 (PyObject *)NULL,
4940 PYTHON_API_VERSION);
Barry Warsaw53699e91996-12-10 23:23:01 +00004941 d = PyModule_GetDict(m);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004942
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004943 /* Initialize environ dictionary */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004944 v = convertenviron();
Barry Warsaw53699e91996-12-10 23:23:01 +00004945 if (v == NULL || PyDict_SetItemString(d, "environ", v) != 0)
Guido van Rossum0cb96de1997-10-01 04:29:29 +00004946 return;
Barry Warsaw53699e91996-12-10 23:23:01 +00004947 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +00004948
Barry Warsaw4a342091996-12-19 23:50:02 +00004949 if (all_ins(d))
Barry Warsaw4a342091996-12-19 23:50:02 +00004950 return;
4951
Fred Drakebec628d1999-12-15 18:31:10 +00004952 if (setup_confname_tables(d))
4953 return;
4954
Barry Warsawca74da41999-02-09 19:31:45 +00004955 PyDict_SetItemString(d, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +00004956
Guido van Rossumb3d39562000-01-31 18:41:26 +00004957#ifdef HAVE_PUTENV
Fred Drake762e2061999-08-26 17:23:54 +00004958 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +00004959#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +00004960}