2 /* POSIX module implementation */
4 /* This file is also used for Windows NT/MS-Win and OS/2. In that case the
5 module actually calls itself 'nt' or 'os2', not 'posix', and a few
6 functions are either unimplemented or implemented differently. The source
7 assumes that for Windows NT, the macro 'MS_WINDOWS' is defined independent
8 of the compiler used. Different compilers define their own feature
9 test macro, e.g. '__BORLANDC__' or '_MSC_VER'. For OS/2, the compiler
10 independent macro PYOS_OS2 should be defined. On OS/2 the default
11 compiler is assumed to be IBM's VisualAge C++ (VACPP). PYCC_GCC is used
12 as the compiler specific macro for the EMX port of gcc to OS/2. */
14 /* See also ../Dos/dosmodule.c */
17 #include "structseq.h"
21 #endif /* defined(__VMS) */
23 PyDoc_STRVAR(posix__doc__
,
24 "This module provides access to operating system functionality that is\n\
25 standardized by the C Standard and the POSIX standard (a thinly\n\
26 disguised Unix interface). Refer to the library manual and\n\
27 corresponding Unix manual entries for more information on calls.");
29 #ifndef Py_USING_UNICODE
30 /* This is used in signatures of functions. */
31 #define Py_UNICODE void
36 #define INCL_DOSERRORS
37 #define INCL_DOSPROCESS
49 #include <sys/types.h>
52 #ifdef HAVE_SYS_WAIT_H
53 #include <sys/wait.h> /* For WNOHANG */
60 #endif /* HAVE_FCNTL_H */
66 #ifdef HAVE_SYSEXITS_H
68 #endif /* HAVE_SYSEXITS_H */
70 #ifdef HAVE_SYS_LOADAVG_H
71 #include <sys/loadavg.h>
74 /* Various compilers have only certain posix functions */
75 /* XXX Gosh I wish these were all moved into pyconfig.h */
76 #if defined(PYCC_VACPP) && defined(PYOS_OS2)
79 #if defined(__WATCOMC__) && !defined(__QNX__) /* Watcom compiler */
81 #define HAVE_OPENDIR 1
89 #ifdef __BORLANDC__ /* Borland compiler */
92 #define HAVE_OPENDIR 1
98 #ifdef _MSC_VER /* Microsoft compiler */
100 #define HAVE_SPAWNV 1
104 #define HAVE_SYSTEM 1
107 #define fsync _commit
109 #if defined(PYOS_OS2) && defined(PYCC_GCC) || defined(__VMS)
110 /* Everything needed is defined in PC/os2emx/pyconfig.h or vms/pyconfig.h */
111 #else /* all other compilers */
112 /* Unix functions that the configure script doesn't check for */
115 #if defined(__USLC__) && defined(__SCO_VERSION__) /* SCO UDK Compiler */
118 #define HAVE_GETCWD 1
119 #define HAVE_GETEGID 1
120 #define HAVE_GETEUID 1
121 #define HAVE_GETGID 1
122 #define HAVE_GETPPID 1
123 #define HAVE_GETUID 1
125 #define HAVE_OPENDIR 1
130 #define HAVE_SYSTEM 1
132 #define HAVE_TTYNAME 1
133 #endif /* PYOS_OS2 && PYCC_GCC && __VMS */
134 #endif /* _MSC_VER */
135 #endif /* __BORLANDC__ */
136 #endif /* ! __WATCOMC__ || __QNX__ */
137 #endif /* ! __IBMC__ */
141 #if defined(__sgi)&&_COMPILER_VERSION>=700
142 /* declare ctermid_r if compiling with MIPSPro 7.x in ANSI C mode
144 extern char *ctermid_r(char *);
147 #ifndef HAVE_UNISTD_H
148 #if defined(PYCC_VACPP)
149 extern int mkdir(char *);
151 #if ( defined(__WATCOMC__) || defined(_MSC_VER) ) && !defined(__QNX__)
152 extern int mkdir(const char *);
154 extern int mkdir(const char *, mode_t
);
157 #if defined(__IBMC__) || defined(__IBMCPP__)
158 extern int chdir(char *);
159 extern int rmdir(char *);
161 extern int chdir(const char *);
162 extern int rmdir(const char *);
165 extern int chmod(const char *, int);
167 extern int chmod(const char *, mode_t
);
169 extern int chown(const char *, uid_t
, gid_t
);
170 extern char *getcwd(char *, int);
171 extern char *strerror(int);
172 extern int link(const char *, const char *);
173 extern int rename(const char *, const char *);
174 extern int stat(const char *, struct stat
*);
175 extern int unlink(const char *);
176 extern int pclose(FILE *);
178 extern int symlink(const char *, const char *);
179 #endif /* HAVE_SYMLINK */
181 extern int lstat(const char *, struct stat
*);
182 #endif /* HAVE_LSTAT */
183 #endif /* !HAVE_UNISTD_H */
185 #endif /* !_MSC_VER */
189 #endif /* HAVE_UTIME_H */
191 #ifdef HAVE_SYS_UTIME_H
192 #include <sys/utime.h>
193 #define HAVE_UTIME_H /* pretend we do for the rest of this file */
194 #endif /* HAVE_SYS_UTIME_H */
196 #ifdef HAVE_SYS_TIMES_H
197 #include <sys/times.h>
198 #endif /* HAVE_SYS_TIMES_H */
200 #ifdef HAVE_SYS_PARAM_H
201 #include <sys/param.h>
202 #endif /* HAVE_SYS_PARAM_H */
204 #ifdef HAVE_SYS_UTSNAME_H
205 #include <sys/utsname.h>
206 #endif /* HAVE_SYS_UTSNAME_H */
210 #define NAMLEN(dirent) strlen((dirent)->d_name)
212 #if defined(__WATCOMC__) && !defined(__QNX__)
214 #define NAMLEN(dirent) strlen((dirent)->d_name)
216 #define dirent direct
217 #define NAMLEN(dirent) (dirent)->d_namlen
219 #ifdef HAVE_SYS_NDIR_H
220 #include <sys/ndir.h>
222 #ifdef HAVE_SYS_DIR_H
235 #define _WIN32_WINNT 0x0400 /* Needed for CryptoAPI on some systems */
237 #include <shellapi.h> /* for ShellExecute() */
239 #define pclose _pclose
240 #endif /* _MSC_VER */
242 #if defined(PYCC_VACPP) && defined(PYOS_OS2)
247 #define MAXPATHLEN 1024
248 #endif /* MAXPATHLEN */
251 /* Emulate some macros on systems that have a union instead of macros */
254 #define WIFEXITED(u_wait) (!(u_wait).w_termsig && !(u_wait).w_coredump)
258 #define WEXITSTATUS(u_wait) (WIFEXITED(u_wait)?((u_wait).w_retcode):-1)
262 #define WTERMSIG(u_wait) ((u_wait).w_termsig)
265 #endif /* UNION_WAIT */
267 /* Don't use the "_r" form if we don't need it (also, won't have a
268 prototype for it, at least on Solaris -- maybe others as well?). */
269 #if defined(HAVE_CTERMID_R) && defined(WITH_THREAD)
270 #define USE_CTERMID_R
273 #if defined(HAVE_TMPNAM_R) && defined(WITH_THREAD)
277 /* choose the appropriate stat and fstat functions and return structs */
279 #if defined(MS_WIN64) || defined(MS_WINDOWS)
280 # define STAT _stati64
281 # define FSTAT _fstati64
282 # define STRUCT_STAT struct _stati64
286 # define STRUCT_STAT struct stat
289 #if defined(MAJOR_IN_MKDEV)
290 #include <sys/mkdev.h>
292 #if defined(MAJOR_IN_SYSMACROS)
293 #include <sys/sysmacros.h>
295 #if defined(HAVE_MKNOD) && defined(HAVE_SYS_MKDEV_H)
296 #include <sys/mkdev.h>
300 /* Return a dictionary corresponding to the POSIX environment table */
301 #ifdef WITH_NEXT_FRAMEWORK
302 /* On Darwin/MacOSX a shared library or framework has no access to
303 ** environ directly, we must obtain it with _NSGetEnviron().
305 #include <crt_externs.h>
306 static char **environ
;
307 #elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
308 extern char **environ
;
309 #endif /* !_MSC_VER */
319 #ifdef WITH_NEXT_FRAMEWORK
321 environ
= *_NSGetEnviron();
325 /* This part ignores errors */
326 for (e
= environ
; *e
!= NULL
; e
++) {
329 char *p
= strchr(*e
, '=');
332 k
= PyString_FromStringAndSize(*e
, (int)(p
-*e
));
337 v
= PyString_FromString(p
+1);
343 if (PyDict_GetItem(d
, k
) == NULL
) {
344 if (PyDict_SetItem(d
, k
, v
) != 0)
350 #if defined(PYOS_OS2)
353 char buffer
[1024]; /* OS/2 Provides a Documented Max of 1024 Chars */
355 rc
= DosQueryExtLIBPATH(buffer
, BEGIN_LIBPATH
);
356 if (rc
== NO_ERROR
) { /* (not a type, envname is NOT 'BEGIN_LIBPATH') */
357 PyObject
*v
= PyString_FromString(buffer
);
358 PyDict_SetItemString(d
, "BEGINLIBPATH", v
);
361 rc
= DosQueryExtLIBPATH(buffer
, END_LIBPATH
);
362 if (rc
== NO_ERROR
) { /* (not a typo, envname is NOT 'END_LIBPATH') */
363 PyObject
*v
= PyString_FromString(buffer
);
364 PyDict_SetItemString(d
, "ENDLIBPATH", v
);
373 /* Set a POSIX-specific error from errno, and return NULL */
378 return PyErr_SetFromErrno(PyExc_OSError
);
381 posix_error_with_filename(char* name
)
383 return PyErr_SetFromErrnoWithFilename(PyExc_OSError
, name
);
386 #ifdef Py_WIN_WIDE_FILENAMES
388 posix_error_with_unicode_filename(Py_UNICODE
* name
)
390 return PyErr_SetFromErrnoWithUnicodeFilename(PyExc_OSError
, name
);
392 #endif /* Py_WIN_WIDE_FILENAMES */
396 posix_error_with_allocated_filename(char* name
)
398 PyObject
*rc
= PyErr_SetFromErrnoWithFilename(PyExc_OSError
, name
);
405 win32_error(char* function
, char* filename
)
407 /* XXX We should pass the function name along in the future.
408 (_winreg.c also wants to pass the function name.)
409 This would however require an additional param to the
410 Windows error object, which is non-trivial.
412 errno
= GetLastError();
414 return PyErr_SetFromWindowsErrWithFilename(errno
, filename
);
416 return PyErr_SetFromWindowsErr(errno
);
419 #ifdef Py_WIN_WIDE_FILENAMES
421 win32_error_unicode(char* function
, Py_UNICODE
* filename
)
423 /* XXX - see win32_error for comments on 'function' */
424 errno
= GetLastError();
426 return PyErr_SetFromWindowsErrWithUnicodeFilename(errno
, filename
);
428 return PyErr_SetFromWindowsErr(errno
);
431 static PyObject
*_PyUnicode_FromFileSystemEncodedObject(register PyObject
*obj
)
433 /* XXX Perhaps we should make this API an alias of
434 PyObject_Unicode() instead ?! */
435 if (PyUnicode_CheckExact(obj
)) {
439 if (PyUnicode_Check(obj
)) {
440 /* For a Unicode subtype that's not a Unicode object,
441 return a true Unicode object with the same data. */
442 return PyUnicode_FromUnicode(PyUnicode_AS_UNICODE(obj
),
443 PyUnicode_GET_SIZE(obj
));
445 return PyUnicode_FromEncodedObject(obj
,
446 Py_FileSystemDefaultEncoding
,
450 #endif /* Py_WIN_WIDE_FILENAMES */
454 #if defined(PYOS_OS2)
455 /**********************************************************************
456 * Helper Function to Trim and Format OS/2 Messages
457 **********************************************************************/
459 os2_formatmsg(char *msgbuf
, int msglen
, char *reason
)
461 msgbuf
[msglen
] = '\0'; /* OS/2 Doesn't Guarantee a Terminator */
463 if (strlen(msgbuf
) > 0) { /* If Non-Empty Msg, Trim CRLF */
464 char *lastc
= &msgbuf
[ strlen(msgbuf
)-1 ];
466 while (lastc
> msgbuf
&& isspace(Py_CHARMASK(*lastc
)))
467 *lastc
-- = '\0'; /* Trim Trailing Whitespace (CRLF) */
470 /* Add Optional Reason Text */
472 strcat(msgbuf
, " : ");
473 strcat(msgbuf
, reason
);
477 /**********************************************************************
478 * Decode an OS/2 Operating System Error Code
480 * A convenience function to lookup an OS/2 error code and return a
481 * text message we can use to raise a Python exception.
484 * The messages for errors returned from the OS/2 kernel reside in
485 * the file OSO001.MSG in the \OS2 directory hierarchy.
487 **********************************************************************/
489 os2_strerror(char *msgbuf
, int msgbuflen
, int errorcode
, char *reason
)
494 /* Retrieve Kernel-Related Error Message from OSO001.MSG File */
495 Py_BEGIN_ALLOW_THREADS
496 rc
= DosGetMessage(NULL
, 0, msgbuf
, msgbuflen
,
497 errorcode
, "oso001.msg", &msglen
);
501 os2_formatmsg(msgbuf
, msglen
, reason
);
503 PyOS_snprintf(msgbuf
, msgbuflen
,
504 "unknown OS error #%d", errorcode
);
509 /* Set an OS/2-specific error and return NULL. OS/2 kernel
510 errors are not in a global variable e.g. 'errno' nor are
511 they congruent with posix error numbers. */
513 static PyObject
* os2_error(int code
)
518 os2_strerror(text
, sizeof(text
), code
, "");
520 v
= Py_BuildValue("(is)", code
, text
);
522 PyErr_SetObject(PyExc_OSError
, v
);
525 return NULL
; /* Signal to Python that an Exception is Pending */
530 /* POSIX generic methods */
533 posix_fildes(PyObject
*fdobj
, int (*func
)(int))
537 fd
= PyObject_AsFileDescriptor(fdobj
);
540 Py_BEGIN_ALLOW_THREADS
544 return posix_error();
549 #ifdef Py_WIN_WIDE_FILENAMES
551 unicode_file_names(void)
553 static int canusewide
= -1;
554 if (canusewide
== -1) {
555 /* As per doc for ::GetVersion(), this is the correct test for
556 the Windows NT family. */
557 canusewide
= (GetVersion() < 0x80000000) ? 1 : 0;
564 posix_1str(PyObject
*args
, char *format
, int (*func
)(const char*),
565 char *wformat
, int (*wfunc
)(const Py_UNICODE
*))
569 #ifdef Py_WIN_WIDE_FILENAMES
570 if (unicode_file_names()) {
572 if (PyArg_ParseTuple(args
, wformat
, &po
)) {
573 Py_BEGIN_ALLOW_THREADS
574 /* PyUnicode_AS_UNICODE OK without thread
575 lock as it is a simple dereference. */
576 res
= (*wfunc
)(PyUnicode_AS_UNICODE(po
));
579 return posix_error_with_unicode_filename(PyUnicode_AS_UNICODE(po
));
583 /* Drop the argument parsing error as narrow
584 strings are also valid. */
588 /* Platforms that don't support Unicode filenames
589 shouldn't be passing these extra params */
590 assert(wformat
==NULL
&& wfunc
== NULL
);
593 if (!PyArg_ParseTuple(args
, format
,
594 Py_FileSystemDefaultEncoding
, &path1
))
596 Py_BEGIN_ALLOW_THREADS
597 res
= (*func
)(path1
);
600 return posix_error_with_allocated_filename(path1
);
607 posix_2str(PyObject
*args
,
609 int (*func
)(const char *, const char *),
611 int (*wfunc
)(const Py_UNICODE
*, const Py_UNICODE
*))
613 char *path1
= NULL
, *path2
= NULL
;
615 #ifdef Py_WIN_WIDE_FILENAMES
616 if (unicode_file_names()) {
619 if (PyArg_ParseTuple(args
, wformat
, &po1
, &po2
)) {
620 if (PyUnicode_Check(po1
) || PyUnicode_Check(po2
)) {
623 wpath1
= _PyUnicode_FromFileSystemEncodedObject(po1
);
624 wpath2
= _PyUnicode_FromFileSystemEncodedObject(po2
);
625 if (!wpath1
|| !wpath2
) {
630 Py_BEGIN_ALLOW_THREADS
631 /* PyUnicode_AS_UNICODE OK without thread
632 lock as it is a simple dereference. */
633 res
= (*wfunc
)(PyUnicode_AS_UNICODE(wpath1
),
634 PyUnicode_AS_UNICODE(wpath2
));
639 return posix_error();
643 /* Else flow through as neither is Unicode. */
645 /* Drop the argument parsing error as narrow
646 strings are also valid. */
650 /* Platforms that don't support Unicode filenames
651 shouldn't be passing these extra params */
652 assert(wformat
==NULL
&& wfunc
== NULL
);
655 if (!PyArg_ParseTuple(args
, format
,
656 Py_FileSystemDefaultEncoding
, &path1
,
657 Py_FileSystemDefaultEncoding
, &path2
))
659 Py_BEGIN_ALLOW_THREADS
660 res
= (*func
)(path1
, path2
);
665 /* XXX how to report both path1 and path2??? */
666 return posix_error();
671 PyDoc_STRVAR(stat_result__doc__
,
672 "stat_result: Result from stat or lstat.\n\n\
673 This object may be accessed either as a tuple of\n\
674 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
675 or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
677 Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
678 or st_flags, they are available as attributes only.\n\
680 See os.stat for more information.");
682 static PyStructSequence_Field stat_result_fields
[] = {
683 {"st_mode", "protection bits"},
685 {"st_dev", "device"},
686 {"st_nlink", "number of hard links"},
687 {"st_uid", "user ID of owner"},
688 {"st_gid", "group ID of owner"},
689 {"st_size", "total size, in bytes"},
690 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
691 {NULL
, "integer time of last access"},
692 {NULL
, "integer time of last modification"},
693 {NULL
, "integer time of last change"},
694 {"st_atime", "time of last access"},
695 {"st_mtime", "time of last modification"},
696 {"st_ctime", "time of last change"},
697 #ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
698 {"st_blksize", "blocksize for filesystem I/O"},
700 #ifdef HAVE_STRUCT_STAT_ST_BLOCKS
701 {"st_blocks", "number of blocks allocated"},
703 #ifdef HAVE_STRUCT_STAT_ST_RDEV
704 {"st_rdev", "device type (if inode device)"},
706 #ifdef HAVE_STRUCT_STAT_ST_FLAGS
707 {"st_flags", "user defined flags for file"},
709 #ifdef HAVE_STRUCT_STAT_ST_GEN
710 {"st_gen", "generation number"},
712 #ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
713 {"st_birthtime", "time of creation"},
718 #ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
719 #define ST_BLKSIZE_IDX 13
721 #define ST_BLKSIZE_IDX 12
724 #ifdef HAVE_STRUCT_STAT_ST_BLOCKS
725 #define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
727 #define ST_BLOCKS_IDX ST_BLKSIZE_IDX
730 #ifdef HAVE_STRUCT_STAT_ST_RDEV
731 #define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
733 #define ST_RDEV_IDX ST_BLOCKS_IDX
736 #ifdef HAVE_STRUCT_STAT_ST_FLAGS
737 #define ST_FLAGS_IDX (ST_RDEV_IDX+1)
739 #define ST_FLAGS_IDX ST_RDEV_IDX
742 #ifdef HAVE_STRUCT_STAT_ST_GEN
743 #define ST_GEN_IDX (ST_FLAGS_IDX+1)
745 #define ST_GEN_IDX ST_FLAGS_IDX
748 #ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
749 #define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
751 #define ST_BIRTHTIME_IDX ST_GEN_IDX
754 static PyStructSequence_Desc stat_result_desc
= {
755 "stat_result", /* name */
756 stat_result__doc__
, /* doc */
761 PyDoc_STRVAR(statvfs_result__doc__
,
762 "statvfs_result: Result from statvfs or fstatvfs.\n\n\
763 This object may be accessed either as a tuple of\n\
764 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
765 or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
767 See os.statvfs for more information.");
769 static PyStructSequence_Field statvfs_result_fields
[] = {
783 static PyStructSequence_Desc statvfs_result_desc
= {
784 "statvfs_result", /* name */
785 statvfs_result__doc__
, /* doc */
786 statvfs_result_fields
,
790 static PyTypeObject StatResultType
;
791 static PyTypeObject StatVFSResultType
;
792 static newfunc structseq_new
;
795 statresult_new(PyTypeObject
*type
, PyObject
*args
, PyObject
*kwds
)
797 PyStructSequence
*result
;
800 result
= (PyStructSequence
*)structseq_new(type
, args
, kwds
);
803 /* If we have been initialized from a tuple,
804 st_?time might be set to None. Initialize it
805 from the int slots. */
806 for (i
= 7; i
<= 9; i
++) {
807 if (result
->ob_item
[i
+3] == Py_None
) {
809 Py_INCREF(result
->ob_item
[i
]);
810 result
->ob_item
[i
+3] = result
->ob_item
[i
];
813 return (PyObject
*)result
;
818 /* If true, st_?time is float. */
819 static int _stat_float_times
= 1;
821 PyDoc_STRVAR(stat_float_times__doc__
,
822 "stat_float_times([newval]) -> oldval\n\n\
823 Determine whether os.[lf]stat represents time stamps as float objects.\n\
824 If newval is True, future calls to stat() return floats, if it is False,\n\
825 future calls return ints. \n\
826 If newval is omitted, return the current setting.\n");
829 stat_float_times(PyObject
* self
, PyObject
*args
)
832 if (!PyArg_ParseTuple(args
, "|i:stat_float_times", &newval
))
835 /* Return old value */
836 return PyBool_FromLong(_stat_float_times
);
837 _stat_float_times
= newval
;
843 fill_time(PyObject
*v
, int index
, time_t sec
, unsigned long nsec
)
845 PyObject
*fval
,*ival
;
846 #if SIZEOF_TIME_T > SIZEOF_LONG
847 ival
= PyLong_FromLongLong((PY_LONG_LONG
)sec
);
849 ival
= PyInt_FromLong((long)sec
);
851 if (_stat_float_times
) {
852 fval
= PyFloat_FromDouble(sec
+ 1e-9*nsec
);
857 PyStructSequence_SET_ITEM(v
, index
, ival
);
858 PyStructSequence_SET_ITEM(v
, index
+3, fval
);
861 /* pack a system stat C structure into the Python stat tuple
862 (used by posix_stat() and posix_fstat()) */
864 _pystat_fromstructstat(STRUCT_STAT st
)
866 unsigned long ansec
, mnsec
, cnsec
;
867 PyObject
*v
= PyStructSequence_New(&StatResultType
);
871 PyStructSequence_SET_ITEM(v
, 0, PyInt_FromLong((long)st
.st_mode
));
872 #ifdef HAVE_LARGEFILE_SUPPORT
873 PyStructSequence_SET_ITEM(v
, 1,
874 PyLong_FromLongLong((PY_LONG_LONG
)st
.st_ino
));
876 PyStructSequence_SET_ITEM(v
, 1, PyInt_FromLong((long)st
.st_ino
));
878 #if defined(HAVE_LONG_LONG) && !defined(MS_WINDOWS)
879 PyStructSequence_SET_ITEM(v
, 2,
880 PyLong_FromLongLong((PY_LONG_LONG
)st
.st_dev
));
882 PyStructSequence_SET_ITEM(v
, 2, PyInt_FromLong((long)st
.st_dev
));
884 PyStructSequence_SET_ITEM(v
, 3, PyInt_FromLong((long)st
.st_nlink
));
885 PyStructSequence_SET_ITEM(v
, 4, PyInt_FromLong((long)st
.st_uid
));
886 PyStructSequence_SET_ITEM(v
, 5, PyInt_FromLong((long)st
.st_gid
));
887 #ifdef HAVE_LARGEFILE_SUPPORT
888 PyStructSequence_SET_ITEM(v
, 6,
889 PyLong_FromLongLong((PY_LONG_LONG
)st
.st_size
));
891 PyStructSequence_SET_ITEM(v
, 6, PyInt_FromLong(st
.st_size
));
894 #ifdef HAVE_STAT_TV_NSEC
895 ansec
= st
.st_atim
.tv_nsec
;
896 mnsec
= st
.st_mtim
.tv_nsec
;
897 cnsec
= st
.st_ctim
.tv_nsec
;
899 #ifdef HAVE_STAT_TV_NSEC2
900 ansec
= st
.st_atimespec
.tv_nsec
;
901 mnsec
= st
.st_mtimespec
.tv_nsec
;
902 cnsec
= st
.st_ctimespec
.tv_nsec
;
904 ansec
= mnsec
= cnsec
= 0;
907 fill_time(v
, 7, st
.st_atime
, ansec
);
908 fill_time(v
, 8, st
.st_mtime
, mnsec
);
909 fill_time(v
, 9, st
.st_ctime
, cnsec
);
911 #ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
912 PyStructSequence_SET_ITEM(v
, ST_BLKSIZE_IDX
,
913 PyInt_FromLong((long)st
.st_blksize
));
915 #ifdef HAVE_STRUCT_STAT_ST_BLOCKS
916 PyStructSequence_SET_ITEM(v
, ST_BLOCKS_IDX
,
917 PyInt_FromLong((long)st
.st_blocks
));
919 #ifdef HAVE_STRUCT_STAT_ST_RDEV
920 PyStructSequence_SET_ITEM(v
, ST_RDEV_IDX
,
921 PyInt_FromLong((long)st
.st_rdev
));
923 #ifdef HAVE_STRUCT_STAT_ST_GEN
924 PyStructSequence_SET_ITEM(v
, ST_GEN_IDX
,
925 PyInt_FromLong((long)st
.st_gen
));
927 #ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
930 unsigned long bsec
,bnsec
;
931 bsec
= (long)st
.st_birthtime
;
932 #ifdef HAVE_STAT_TV_NSEC2
933 bnsec
= st
.st_birthtimespec
.tv_nsec
;
937 if (_stat_float_times
) {
938 val
= PyFloat_FromDouble(bsec
+ 1e-9*bnsec
);
940 val
= PyInt_FromLong((long)bsec
);
942 PyStructSequence_SET_ITEM(v
, ST_BIRTHTIME_IDX
,
946 #ifdef HAVE_STRUCT_STAT_ST_FLAGS
947 PyStructSequence_SET_ITEM(v
, ST_FLAGS_IDX
,
948 PyInt_FromLong((long)st
.st_flags
));
951 if (PyErr_Occurred()) {
961 /* IsUNCRoot -- test whether the supplied path is of the form \\SERVER\SHARE\,
962 where / can be used in place of \ and the trailing slash is optional.
963 Both SERVER and SHARE must have at least one character.
966 #define ISSLASHA(c) ((c) == '\\' || (c) == '/')
967 #define ISSLASHW(c) ((c) == L'\\' || (c) == L'/')
968 #define ARRAYSIZE(a) (sizeof(a) / sizeof(a[0]))
971 IsUNCRootA(char *path
, int pathlen
)
973 #define ISSLASH ISSLASHA
977 if (pathlen
< 5 || !ISSLASH(path
[0]) || !ISSLASH(path
[1]))
978 /* minimum UNCRoot is \\x\y */
980 for (i
= 2; i
< pathlen
; i
++)
981 if (ISSLASH(path
[i
])) break;
982 if (i
== 2 || i
== pathlen
)
983 /* do not allow \\\SHARE or \\SERVER */
986 for (i
= share
; i
< pathlen
; i
++)
987 if (ISSLASH(path
[i
])) break;
988 return (i
!= share
&& (i
== pathlen
|| i
== pathlen
-1));
993 #ifdef Py_WIN_WIDE_FILENAMES
995 IsUNCRootW(Py_UNICODE
*path
, int pathlen
)
997 #define ISSLASH ISSLASHW
1001 if (pathlen
< 5 || !ISSLASH(path
[0]) || !ISSLASH(path
[1]))
1002 /* minimum UNCRoot is \\x\y */
1004 for (i
= 2; i
< pathlen
; i
++)
1005 if (ISSLASH(path
[i
])) break;
1006 if (i
== 2 || i
== pathlen
)
1007 /* do not allow \\\SHARE or \\SERVER */
1010 for (i
= share
; i
< pathlen
; i
++)
1011 if (ISSLASH(path
[i
])) break;
1012 return (i
!= share
&& (i
== pathlen
|| i
== pathlen
-1));
1016 #endif /* Py_WIN_WIDE_FILENAMES */
1017 #endif /* MS_WINDOWS */
1020 posix_do_stat(PyObject
*self
, PyObject
*args
,
1023 int (*statfunc
)(const char *, STRUCT_STAT
*, ...),
1025 int (*statfunc
)(const char *, STRUCT_STAT
*),
1028 int (*wstatfunc
)(const Py_UNICODE
*, STRUCT_STAT
*))
1031 char *path
= NULL
; /* pass this to stat; do not free() it */
1032 char *pathfree
= NULL
; /* this memory must be free'd */
1037 char pathcopy
[MAX_PATH
];
1038 #endif /* MS_WINDOWS */
1041 #ifdef Py_WIN_WIDE_FILENAMES
1042 /* If on wide-character-capable OS see if argument
1043 is Unicode and if so use wide API. */
1044 if (unicode_file_names()) {
1045 PyUnicodeObject
*po
;
1046 if (PyArg_ParseTuple(args
, wformat
, &po
)) {
1047 Py_UNICODE wpath
[MAX_PATH
+1];
1048 pathlen
= wcslen(PyUnicode_AS_UNICODE(po
));
1049 /* the library call can blow up if the file name is too long! */
1050 if (pathlen
> MAX_PATH
) {
1051 errno
= ENAMETOOLONG
;
1052 return posix_error();
1054 wcscpy(wpath
, PyUnicode_AS_UNICODE(po
));
1055 /* Remove trailing slash or backslash, unless it's the current
1056 drive root (/ or \) or a specific drive's root (like c:\ or c:/).
1059 if (ISSLASHW(wpath
[pathlen
-1])) {
1060 /* It does end with a slash -- exempt the root drive cases. */
1061 if (pathlen
== 1 || (pathlen
== 3 && wpath
[1] == L
':') ||
1062 IsUNCRootW(wpath
, pathlen
))
1063 /* leave it alone */;
1065 /* nuke the trailing backslash */
1066 wpath
[pathlen
-1] = L
'\0';
1069 else if (ISSLASHW(wpath
[1]) && pathlen
< ARRAYSIZE(wpath
)-1 &&
1070 IsUNCRootW(wpath
, pathlen
)) {
1071 /* UNC root w/o trailing slash: add one when there's room */
1072 wpath
[pathlen
++] = L
'\\';
1073 wpath
[pathlen
] = L
'\0';
1076 Py_BEGIN_ALLOW_THREADS
1077 /* PyUnicode_AS_UNICODE result OK without
1078 thread lock as it is a simple dereference. */
1079 res
= wstatfunc(wpath
, &st
);
1080 Py_END_ALLOW_THREADS
1082 return posix_error_with_unicode_filename(wpath
);
1083 return _pystat_fromstructstat(st
);
1085 /* Drop the argument parsing error as narrow strings
1091 if (!PyArg_ParseTuple(args
, format
,
1092 Py_FileSystemDefaultEncoding
, &path
))
1097 pathlen
= strlen(path
);
1098 /* the library call can blow up if the file name is too long! */
1099 if (pathlen
> MAX_PATH
) {
1100 PyMem_Free(pathfree
);
1101 errno
= ENAMETOOLONG
;
1102 return posix_error();
1105 /* Remove trailing slash or backslash, unless it's the current
1106 drive root (/ or \) or a specific drive's root (like c:\ or c:/).
1109 if (ISSLASHA(path
[pathlen
-1])) {
1110 /* It does end with a slash -- exempt the root drive cases. */
1111 if (pathlen
== 1 || (pathlen
== 3 && path
[1] == ':') ||
1112 IsUNCRootA(path
, pathlen
))
1113 /* leave it alone */;
1115 /* nuke the trailing backslash */
1116 strncpy(pathcopy
, path
, pathlen
);
1117 pathcopy
[pathlen
-1] = '\0';
1121 else if (ISSLASHA(path
[1]) && pathlen
< ARRAYSIZE(pathcopy
)-1 &&
1122 IsUNCRootA(path
, pathlen
)) {
1123 /* UNC root w/o trailing slash: add one when there's room */
1124 strncpy(pathcopy
, path
, pathlen
);
1125 pathcopy
[pathlen
++] = '\\';
1126 pathcopy
[pathlen
] = '\0';
1130 #endif /* MS_WINDOWS */
1132 Py_BEGIN_ALLOW_THREADS
1133 res
= (*statfunc
)(path
, &st
);
1134 Py_END_ALLOW_THREADS
1136 return posix_error_with_allocated_filename(pathfree
);
1138 PyMem_Free(pathfree
);
1139 return _pystat_fromstructstat(st
);
1145 PyDoc_STRVAR(posix_access__doc__
,
1146 "access(path, mode) -> 1 if granted, 0 otherwise\n\n\
1147 Use the real uid/gid to test for access to a path. Note that most\n\
1148 operations will use the effective uid/gid, therefore this routine can\n\
1149 be used in a suid/sgid environment to test if the invoking user has the\n\
1150 specified access to the path. The mode argument can be F_OK to test\n\
1151 existence, or the inclusive-OR of R_OK, W_OK, and X_OK.");
1154 posix_access(PyObject
*self
, PyObject
*args
)
1160 #ifdef Py_WIN_WIDE_FILENAMES
1161 if (unicode_file_names()) {
1162 PyUnicodeObject
*po
;
1163 if (PyArg_ParseTuple(args
, "Ui:access", &po
, &mode
)) {
1164 Py_BEGIN_ALLOW_THREADS
1165 /* PyUnicode_AS_UNICODE OK without thread lock as
1166 it is a simple dereference. */
1167 res
= _waccess(PyUnicode_AS_UNICODE(po
), mode
);
1168 Py_END_ALLOW_THREADS
1169 return PyBool_FromLong(res
== 0);
1171 /* Drop the argument parsing error as narrow strings
1176 if (!PyArg_ParseTuple(args
, "eti:access",
1177 Py_FileSystemDefaultEncoding
, &path
, &mode
))
1179 Py_BEGIN_ALLOW_THREADS
1180 res
= access(path
, mode
);
1181 Py_END_ALLOW_THREADS
1183 return PyBool_FromLong(res
== 0);
1200 PyDoc_STRVAR(posix_ttyname__doc__
,
1201 "ttyname(fd) -> string\n\n\
1202 Return the name of the terminal device connected to 'fd'.");
1205 posix_ttyname(PyObject
*self
, PyObject
*args
)
1210 if (!PyArg_ParseTuple(args
, "i:ttyname", &id
))
1214 /* file descriptor 0 only, the default input device (stdin) */
1225 return posix_error();
1226 return PyString_FromString(ret
);
1231 PyDoc_STRVAR(posix_ctermid__doc__
,
1232 "ctermid() -> string\n\n\
1233 Return the name of the controlling terminal for this process.");
1236 posix_ctermid(PyObject
*self
, PyObject
*noargs
)
1239 char buffer
[L_ctermid
];
1241 #ifdef USE_CTERMID_R
1242 ret
= ctermid_r(buffer
);
1244 ret
= ctermid(buffer
);
1247 return posix_error();
1248 return PyString_FromString(buffer
);
1252 PyDoc_STRVAR(posix_chdir__doc__
,
1254 Change the current working directory to the specified path.");
1257 posix_chdir(PyObject
*self
, PyObject
*args
)
1260 return posix_1str(args
, "et:chdir", chdir
, "U:chdir", _wchdir
);
1261 #elif defined(PYOS_OS2) && defined(PYCC_GCC)
1262 return posix_1str(args
, "et:chdir", _chdir2
, NULL
, NULL
);
1263 #elif defined(__VMS)
1264 return posix_1str(args
, "et:chdir", (int (*)(const char *))chdir
,
1267 return posix_1str(args
, "et:chdir", chdir
, NULL
, NULL
);
1272 PyDoc_STRVAR(posix_fchdir__doc__
,
1273 "fchdir(fildes)\n\n\
1274 Change to the directory of the given file descriptor. fildes must be\n\
1275 opened on a directory, not a file.");
1278 posix_fchdir(PyObject
*self
, PyObject
*fdobj
)
1280 return posix_fildes(fdobj
, fchdir
);
1282 #endif /* HAVE_FCHDIR */
1285 PyDoc_STRVAR(posix_chmod__doc__
,
1286 "chmod(path, mode)\n\n\
1287 Change the access permissions of a file.");
1290 posix_chmod(PyObject
*self
, PyObject
*args
)
1295 #ifdef Py_WIN_WIDE_FILENAMES
1296 if (unicode_file_names()) {
1297 PyUnicodeObject
*po
;
1298 if (PyArg_ParseTuple(args
, "Ui|:chmod", &po
, &i
)) {
1299 Py_BEGIN_ALLOW_THREADS
1300 res
= _wchmod(PyUnicode_AS_UNICODE(po
), i
);
1301 Py_END_ALLOW_THREADS
1303 return posix_error_with_unicode_filename(
1304 PyUnicode_AS_UNICODE(po
));
1308 /* Drop the argument parsing error as narrow strings
1312 #endif /* Py_WIN_WIDE_FILENAMES */
1313 if (!PyArg_ParseTuple(args
, "eti:chmod", Py_FileSystemDefaultEncoding
,
1316 Py_BEGIN_ALLOW_THREADS
1317 res
= chmod(path
, i
);
1318 Py_END_ALLOW_THREADS
1320 return posix_error_with_allocated_filename(path
);
1328 PyDoc_STRVAR(posix_chroot__doc__
,
1330 Change root directory to path.");
1333 posix_chroot(PyObject
*self
, PyObject
*args
)
1335 return posix_1str(args
, "et:chroot", chroot
, NULL
, NULL
);
1340 PyDoc_STRVAR(posix_fsync__doc__
,
1342 force write of file with filedescriptor to disk.");
1345 posix_fsync(PyObject
*self
, PyObject
*fdobj
)
1347 return posix_fildes(fdobj
, fsync
);
1349 #endif /* HAVE_FSYNC */
1351 #ifdef HAVE_FDATASYNC
1354 extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
1357 PyDoc_STRVAR(posix_fdatasync__doc__
,
1358 "fdatasync(fildes)\n\n\
1359 force write of file with filedescriptor to disk.\n\
1360 does not force update of metadata.");
1363 posix_fdatasync(PyObject
*self
, PyObject
*fdobj
)
1365 return posix_fildes(fdobj
, fdatasync
);
1367 #endif /* HAVE_FDATASYNC */
1371 PyDoc_STRVAR(posix_chown__doc__
,
1372 "chown(path, uid, gid)\n\n\
1373 Change the owner and group id of path to the numeric uid and gid.");
1376 posix_chown(PyObject
*self
, PyObject
*args
)
1381 if (!PyArg_ParseTuple(args
, "etii:chown",
1382 Py_FileSystemDefaultEncoding
, &path
,
1385 Py_BEGIN_ALLOW_THREADS
1386 res
= chown(path
, (uid_t
) uid
, (gid_t
) gid
);
1387 Py_END_ALLOW_THREADS
1389 return posix_error_with_allocated_filename(path
);
1394 #endif /* HAVE_CHOWN */
1397 PyDoc_STRVAR(posix_lchown__doc__
,
1398 "lchown(path, uid, gid)\n\n\
1399 Change the owner and group id of path to the numeric uid and gid.\n\
1400 This function will not follow symbolic links.");
1403 posix_lchown(PyObject
*self
, PyObject
*args
)
1408 if (!PyArg_ParseTuple(args
, "etii:lchown",
1409 Py_FileSystemDefaultEncoding
, &path
,
1412 Py_BEGIN_ALLOW_THREADS
1413 res
= lchown(path
, (uid_t
) uid
, (gid_t
) gid
);
1414 Py_END_ALLOW_THREADS
1416 return posix_error_with_allocated_filename(path
);
1421 #endif /* HAVE_LCHOWN */
1425 PyDoc_STRVAR(posix_getcwd__doc__
,
1426 "getcwd() -> path\n\n\
1427 Return a string representing the current working directory.");
1430 posix_getcwd(PyObject
*self
, PyObject
*noargs
)
1435 Py_BEGIN_ALLOW_THREADS
1436 #if defined(PYOS_OS2) && defined(PYCC_GCC)
1437 res
= _getcwd2(buf
, sizeof buf
);
1439 res
= getcwd(buf
, sizeof buf
);
1441 Py_END_ALLOW_THREADS
1443 return posix_error();
1444 return PyString_FromString(buf
);
1447 #ifdef Py_USING_UNICODE
1448 PyDoc_STRVAR(posix_getcwdu__doc__
,
1449 "getcwdu() -> path\n\n\
1450 Return a unicode string representing the current working directory.");
1453 posix_getcwdu(PyObject
*self
, PyObject
*noargs
)
1458 #ifdef Py_WIN_WIDE_FILENAMES
1459 if (unicode_file_names()) {
1462 Py_BEGIN_ALLOW_THREADS
1463 wres
= _wgetcwd(wbuf
, sizeof wbuf
/ sizeof wbuf
[0]);
1464 Py_END_ALLOW_THREADS
1466 return posix_error();
1467 return PyUnicode_FromWideChar(wbuf
, wcslen(wbuf
));
1471 Py_BEGIN_ALLOW_THREADS
1472 #if defined(PYOS_OS2) && defined(PYCC_GCC)
1473 res
= _getcwd2(buf
, sizeof buf
);
1475 res
= getcwd(buf
, sizeof buf
);
1477 Py_END_ALLOW_THREADS
1479 return posix_error();
1480 return PyUnicode_Decode(buf
, strlen(buf
), Py_FileSystemDefaultEncoding
,"strict");
1487 PyDoc_STRVAR(posix_link__doc__
,
1488 "link(src, dst)\n\n\
1489 Create a hard link to a file.");
1492 posix_link(PyObject
*self
, PyObject
*args
)
1494 return posix_2str(args
, "etet:link", link
, NULL
, NULL
);
1496 #endif /* HAVE_LINK */
1499 PyDoc_STRVAR(posix_listdir__doc__
,
1500 "listdir(path) -> list_of_strings\n\n\
1501 Return a list containing the names of the entries in the directory.\n\
1503 path: path of directory to list\n\
1505 The list is in arbitrary order. It does not include the special\n\
1506 entries '.' and '..' even if they are present in the directory.");
1509 posix_listdir(PyObject
*self
, PyObject
*args
)
1511 /* XXX Should redo this putting the (now four) versions of opendir
1512 in separate files instead of having them all here... */
1513 #if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
1517 WIN32_FIND_DATA FileData
;
1518 /* MAX_PATH characters could mean a bigger encoded string */
1519 char namebuf
[MAX_PATH
*2+5];
1520 char *bufptr
= namebuf
;
1521 int len
= sizeof(namebuf
)/sizeof(namebuf
[0]);
1523 #ifdef Py_WIN_WIDE_FILENAMES
1524 /* If on wide-character-capable OS see if argument
1525 is Unicode and if so use wide API. */
1526 if (unicode_file_names()) {
1527 PyUnicodeObject
*po
;
1528 if (PyArg_ParseTuple(args
, "U:listdir", &po
)) {
1529 WIN32_FIND_DATAW wFileData
;
1530 Py_UNICODE wnamebuf
[MAX_PATH
*2+5];
1532 wcsncpy(wnamebuf
, PyUnicode_AS_UNICODE(po
), MAX_PATH
);
1533 wnamebuf
[MAX_PATH
] = L
'\0';
1534 len
= wcslen(wnamebuf
);
1535 wch
= (len
> 0) ? wnamebuf
[len
-1] : L
'\0';
1536 if (wch
!= L
'/' && wch
!= L
'\\' && wch
!= L
':')
1537 wnamebuf
[len
++] = L
'/';
1538 wcscpy(wnamebuf
+ len
, L
"*.*");
1539 if ((d
= PyList_New(0)) == NULL
)
1541 hFindFile
= FindFirstFileW(wnamebuf
, &wFileData
);
1542 if (hFindFile
== INVALID_HANDLE_VALUE
) {
1543 errno
= GetLastError();
1544 if (errno
== ERROR_FILE_NOT_FOUND
) {
1548 return win32_error_unicode("FindFirstFileW", wnamebuf
);
1551 if (wFileData
.cFileName
[0] == L
'.' &&
1552 (wFileData
.cFileName
[1] == L
'\0' ||
1553 wFileData
.cFileName
[1] == L
'.' &&
1554 wFileData
.cFileName
[2] == L
'\0'))
1556 v
= PyUnicode_FromUnicode(wFileData
.cFileName
, wcslen(wFileData
.cFileName
));
1562 if (PyList_Append(d
, v
) != 0) {
1569 } while (FindNextFileW(hFindFile
, &wFileData
) == TRUE
);
1571 if (FindClose(hFindFile
) == FALSE
) {
1573 return win32_error_unicode("FindClose", wnamebuf
);
1577 /* Drop the argument parsing error as narrow strings
1583 if (!PyArg_ParseTuple(args
, "et#:listdir",
1584 Py_FileSystemDefaultEncoding
, &bufptr
, &len
))
1587 char ch
= namebuf
[len
-1];
1588 if (ch
!= SEP
&& ch
!= ALTSEP
&& ch
!= ':')
1589 namebuf
[len
++] = '/';
1591 strcpy(namebuf
+ len
, "*.*");
1593 if ((d
= PyList_New(0)) == NULL
)
1596 hFindFile
= FindFirstFile(namebuf
, &FileData
);
1597 if (hFindFile
== INVALID_HANDLE_VALUE
) {
1598 errno
= GetLastError();
1599 if (errno
== ERROR_FILE_NOT_FOUND
)
1602 return win32_error("FindFirstFile", namebuf
);
1605 if (FileData
.cFileName
[0] == '.' &&
1606 (FileData
.cFileName
[1] == '\0' ||
1607 FileData
.cFileName
[1] == '.' &&
1608 FileData
.cFileName
[2] == '\0'))
1610 v
= PyString_FromString(FileData
.cFileName
);
1616 if (PyList_Append(d
, v
) != 0) {
1623 } while (FindNextFile(hFindFile
, &FileData
) == TRUE
);
1625 if (FindClose(hFindFile
) == FALSE
) {
1627 return win32_error("FindClose", namebuf
);
1632 #elif defined(PYOS_OS2)
1635 #define MAX_PATH CCHMAXPATH
1640 char namebuf
[MAX_PATH
+5];
1646 if (!PyArg_ParseTuple(args
, "t#:listdir", &name
, &len
))
1648 if (len
>= MAX_PATH
) {
1649 PyErr_SetString(PyExc_ValueError
, "path too long");
1652 strcpy(namebuf
, name
);
1653 for (pt
= namebuf
; *pt
; pt
++)
1656 if (namebuf
[len
-1] != SEP
)
1657 namebuf
[len
++] = SEP
;
1658 strcpy(namebuf
+ len
, "*.*");
1660 if ((d
= PyList_New(0)) == NULL
)
1663 rc
= DosFindFirst(namebuf
, /* Wildcard Pattern to Match */
1664 &hdir
, /* Handle to Use While Search Directory */
1665 FILE_READONLY
| FILE_HIDDEN
| FILE_SYSTEM
| FILE_DIRECTORY
,
1666 &ep
, sizeof(ep
), /* Structure to Receive Directory Entry */
1667 &srchcnt
, /* Max and Actual Count of Entries Per Iteration */
1668 FIL_STANDARD
); /* Format of Entry (EAs or Not) */
1670 if (rc
!= NO_ERROR
) {
1672 return posix_error_with_filename(name
);
1675 if (srchcnt
> 0) { /* If Directory is NOT Totally Empty, */
1677 if (ep
.achName
[0] == '.'
1678 && (ep
.achName
[1] == '\0' || (ep
.achName
[1] == '.' && ep
.achName
[2] == '\0')))
1679 continue; /* Skip Over "." and ".." Names */
1681 strcpy(namebuf
, ep
.achName
);
1683 /* Leave Case of Name Alone -- In Native Form */
1684 /* (Removed Forced Lowercasing Code) */
1686 v
= PyString_FromString(namebuf
);
1692 if (PyList_Append(d
, v
) != 0) {
1699 } while (DosFindNext(hdir
, &ep
, sizeof(ep
), &srchcnt
) == NO_ERROR
&& srchcnt
> 0);
1709 int arg_is_unicode
= 1;
1711 if (!PyArg_ParseTuple(args
, "U:listdir", &v
)) {
1715 if (!PyArg_ParseTuple(args
, "et:listdir", Py_FileSystemDefaultEncoding
, &name
))
1717 if ((dirp
= opendir(name
)) == NULL
) {
1718 return posix_error_with_allocated_filename(name
);
1720 if ((d
= PyList_New(0)) == NULL
) {
1725 while ((ep
= readdir(dirp
)) != NULL
) {
1726 if (ep
->d_name
[0] == '.' &&
1728 (ep
->d_name
[1] == '.' && NAMLEN(ep
) == 2)))
1730 v
= PyString_FromStringAndSize(ep
->d_name
, NAMLEN(ep
));
1736 #ifdef Py_USING_UNICODE
1737 if (arg_is_unicode
) {
1740 w
= PyUnicode_FromEncodedObject(v
,
1741 Py_FileSystemDefaultEncoding
,
1748 /* fall back to the original byte string, as
1749 discussed in patch #683592 */
1754 if (PyList_Append(d
, v
) != 0) {
1767 #endif /* which OS */
1768 } /* end of posix_listdir */
1771 /* A helper function for abspath on win32 */
1773 posix__getfullpathname(PyObject
*self
, PyObject
*args
)
1775 /* assume encoded strings wont more than double no of chars */
1776 char inbuf
[MAX_PATH
*2];
1777 char *inbufp
= inbuf
;
1778 int insize
= sizeof(inbuf
)/sizeof(inbuf
[0]);
1779 char outbuf
[MAX_PATH
*2];
1781 #ifdef Py_WIN_WIDE_FILENAMES
1782 if (unicode_file_names()) {
1783 PyUnicodeObject
*po
;
1784 if (PyArg_ParseTuple(args
, "U|:_getfullpathname", &po
)) {
1785 Py_UNICODE woutbuf
[MAX_PATH
*2];
1787 if (!GetFullPathNameW(PyUnicode_AS_UNICODE(po
),
1788 sizeof(woutbuf
)/sizeof(woutbuf
[0]),
1790 return win32_error("GetFullPathName", "");
1791 return PyUnicode_FromUnicode(woutbuf
, wcslen(woutbuf
));
1793 /* Drop the argument parsing error as narrow strings
1798 if (!PyArg_ParseTuple (args
, "et#:_getfullpathname",
1799 Py_FileSystemDefaultEncoding
, &inbufp
,
1802 if (!GetFullPathName(inbuf
, sizeof(outbuf
)/sizeof(outbuf
[0]),
1804 return win32_error("GetFullPathName", inbuf
);
1805 if (PyUnicode_Check(PyTuple_GetItem(args
, 0))) {
1806 return PyUnicode_Decode(outbuf
, strlen(outbuf
),
1807 Py_FileSystemDefaultEncoding
, NULL
);
1809 return PyString_FromString(outbuf
);
1810 } /* end of posix__getfullpathname */
1811 #endif /* MS_WINDOWS */
1813 PyDoc_STRVAR(posix_mkdir__doc__
,
1814 "mkdir(path [, mode=0777])\n\n\
1815 Create a directory.");
1818 posix_mkdir(PyObject
*self
, PyObject
*args
)
1824 #ifdef Py_WIN_WIDE_FILENAMES
1825 if (unicode_file_names()) {
1826 PyUnicodeObject
*po
;
1827 if (PyArg_ParseTuple(args
, "U|i:mkdir", &po
, &mode
)) {
1828 Py_BEGIN_ALLOW_THREADS
1829 /* PyUnicode_AS_UNICODE OK without thread lock as
1830 it is a simple dereference. */
1831 res
= _wmkdir(PyUnicode_AS_UNICODE(po
));
1832 Py_END_ALLOW_THREADS
1834 return posix_error();
1838 /* Drop the argument parsing error as narrow strings
1844 if (!PyArg_ParseTuple(args
, "et|i:mkdir",
1845 Py_FileSystemDefaultEncoding
, &path
, &mode
))
1847 Py_BEGIN_ALLOW_THREADS
1848 #if ( defined(__WATCOMC__) || defined(_MSC_VER) || defined(PYCC_VACPP) ) && !defined(__QNX__)
1851 res
= mkdir(path
, mode
);
1853 Py_END_ALLOW_THREADS
1855 return posix_error_with_allocated_filename(path
);
1863 #if defined(HAVE_BROKEN_NICE) && defined(HAVE_SYS_RESOURCE_H)
1864 #if defined(HAVE_GETPRIORITY) && !defined(PRIO_PROCESS)
1865 #include <sys/resource.h>
1869 PyDoc_STRVAR(posix_nice__doc__
,
1870 "nice(inc) -> new_priority\n\n\
1871 Decrease the priority of process by inc and return the new priority.");
1874 posix_nice(PyObject
*self
, PyObject
*args
)
1876 int increment
, value
;
1878 if (!PyArg_ParseTuple(args
, "i:nice", &increment
))
1881 /* There are two flavours of 'nice': one that returns the new
1882 priority (as required by almost all standards out there) and the
1883 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
1884 the use of getpriority() to get the new priority.
1886 If we are of the nice family that returns the new priority, we
1887 need to clear errno before the call, and check if errno is filled
1888 before calling posix_error() on a returnvalue of -1, because the
1889 -1 may be the actual new priority! */
1892 value
= nice(increment
);
1893 #if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
1895 value
= getpriority(PRIO_PROCESS
, 0);
1897 if (value
== -1 && errno
!= 0)
1898 /* either nice() or getpriority() returned an error */
1899 return posix_error();
1900 return PyInt_FromLong((long) value
);
1902 #endif /* HAVE_NICE */
1905 PyDoc_STRVAR(posix_rename__doc__
,
1906 "rename(old, new)\n\n\
1907 Rename a file or directory.");
1910 posix_rename(PyObject
*self
, PyObject
*args
)
1913 return posix_2str(args
, "etet:rename", rename
, "OO:rename", _wrename
);
1915 return posix_2str(args
, "etet:rename", rename
, NULL
, NULL
);
1920 PyDoc_STRVAR(posix_rmdir__doc__
,
1922 Remove a directory.");
1925 posix_rmdir(PyObject
*self
, PyObject
*args
)
1928 return posix_1str(args
, "et:rmdir", rmdir
, "U:rmdir", _wrmdir
);
1930 return posix_1str(args
, "et:rmdir", rmdir
, NULL
, NULL
);
1935 PyDoc_STRVAR(posix_stat__doc__
,
1936 "stat(path) -> stat result\n\n\
1937 Perform a stat system call on the given path.");
1940 posix_stat(PyObject
*self
, PyObject
*args
)
1943 return posix_do_stat(self
, args
, "et:stat", STAT
, "U:stat", _wstati64
);
1945 return posix_do_stat(self
, args
, "et:stat", STAT
, NULL
, NULL
);
1951 PyDoc_STRVAR(posix_system__doc__
,
1952 "system(command) -> exit_status\n\n\
1953 Execute the command (a string) in a subshell.");
1956 posix_system(PyObject
*self
, PyObject
*args
)
1960 if (!PyArg_ParseTuple(args
, "s:system", &command
))
1962 Py_BEGIN_ALLOW_THREADS
1963 sts
= system(command
);
1964 Py_END_ALLOW_THREADS
1965 return PyInt_FromLong(sts
);
1970 PyDoc_STRVAR(posix_umask__doc__
,
1971 "umask(new_mask) -> old_mask\n\n\
1972 Set the current numeric umask and return the previous umask.");
1975 posix_umask(PyObject
*self
, PyObject
*args
)
1978 if (!PyArg_ParseTuple(args
, "i:umask", &i
))
1982 return posix_error();
1983 return PyInt_FromLong((long)i
);
1987 PyDoc_STRVAR(posix_unlink__doc__
,
1989 Remove a file (same as remove(path)).");
1991 PyDoc_STRVAR(posix_remove__doc__
,
1993 Remove a file (same as unlink(path)).");
1996 posix_unlink(PyObject
*self
, PyObject
*args
)
1999 return posix_1str(args
, "et:remove", unlink
, "U:remove", _wunlink
);
2001 return posix_1str(args
, "et:remove", unlink
, NULL
, NULL
);
2007 PyDoc_STRVAR(posix_uname__doc__
,
2008 "uname() -> (sysname, nodename, release, version, machine)\n\n\
2009 Return a tuple identifying the current operating system.");
2012 posix_uname(PyObject
*self
, PyObject
*noargs
)
2017 Py_BEGIN_ALLOW_THREADS
2019 Py_END_ALLOW_THREADS
2021 return posix_error();
2022 return Py_BuildValue("(sssss)",
2029 #endif /* HAVE_UNAME */
2032 extract_time(PyObject
*t
, long* sec
, long* usec
)
2035 if (PyFloat_Check(t
)) {
2036 double tval
= PyFloat_AsDouble(t
);
2037 PyObject
*intobj
= t
->ob_type
->tp_as_number
->nb_int(t
);
2040 intval
= PyInt_AsLong(intobj
);
2042 if (intval
== -1 && PyErr_Occurred())
2045 *usec
= (long)((tval
- intval
) * 1e6
); /* can't exceed 1000000 */
2047 /* If rounding gave us a negative number,
2052 intval
= PyInt_AsLong(t
);
2053 if (intval
== -1 && PyErr_Occurred())
2060 PyDoc_STRVAR(posix_utime__doc__
,
2061 "utime(path, (atime, utime))\n\
2062 utime(path, None)\n\n\
2063 Set the access and modified time of the file to the given values. If the\n\
2064 second form is used, set the access and modified times to the current time.");
2067 posix_utime(PyObject
*self
, PyObject
*args
)
2070 long atime
, mtime
, ausec
, musec
;
2074 #if defined(HAVE_UTIMES)
2075 struct timeval buf
[2];
2076 #define ATIME buf[0].tv_sec
2077 #define MTIME buf[1].tv_sec
2078 #elif defined(HAVE_UTIME_H)
2079 /* XXX should define struct utimbuf instead, above */
2081 #define ATIME buf.actime
2082 #define MTIME buf.modtime
2083 #define UTIME_ARG &buf
2084 #else /* HAVE_UTIMES */
2086 #define ATIME buf[0]
2087 #define MTIME buf[1]
2088 #define UTIME_ARG buf
2089 #endif /* HAVE_UTIMES */
2091 int have_unicode_filename
= 0;
2092 #ifdef Py_WIN_WIDE_FILENAMES
2093 PyUnicodeObject
*obwpath
;
2095 if (unicode_file_names()) {
2096 if (PyArg_ParseTuple(args
, "UO|:utime", &obwpath
, &arg
)) {
2097 wpath
= PyUnicode_AS_UNICODE(obwpath
);
2098 have_unicode_filename
= 1;
2100 /* Drop the argument parsing error as narrow strings
2104 #endif /* Py_WIN_WIDE_FILENAMES */
2106 if (!have_unicode_filename
&& \
2107 !PyArg_ParseTuple(args
, "etO:utime",
2108 Py_FileSystemDefaultEncoding
, &path
, &arg
))
2110 if (arg
== Py_None
) {
2111 /* optional time values not given */
2112 Py_BEGIN_ALLOW_THREADS
2113 #ifdef Py_WIN_WIDE_FILENAMES
2114 if (have_unicode_filename
)
2115 res
= _wutime(wpath
, NULL
);
2117 #endif /* Py_WIN_WIDE_FILENAMES */
2118 res
= utime(path
, NULL
);
2119 Py_END_ALLOW_THREADS
2121 else if (!PyTuple_Check(arg
) || PyTuple_Size(arg
) != 2) {
2122 PyErr_SetString(PyExc_TypeError
,
2123 "utime() arg 2 must be a tuple (atime, mtime)");
2128 if (extract_time(PyTuple_GET_ITEM(arg
, 0),
2129 &atime
, &ausec
) == -1) {
2133 if (extract_time(PyTuple_GET_ITEM(arg
, 1),
2134 &mtime
, &musec
) == -1) {
2141 buf
[0].tv_usec
= ausec
;
2142 buf
[1].tv_usec
= musec
;
2143 Py_BEGIN_ALLOW_THREADS
2144 res
= utimes(path
, buf
);
2145 Py_END_ALLOW_THREADS
2147 Py_BEGIN_ALLOW_THREADS
2148 #ifdef Py_WIN_WIDE_FILENAMES
2149 if (have_unicode_filename
)
2150 /* utime is OK with utimbuf, but _wutime insists
2151 on _utimbuf (the msvc headers assert the
2152 underscore version is ansi) */
2153 res
= _wutime(wpath
, (struct _utimbuf
*)UTIME_ARG
);
2155 #endif /* Py_WIN_WIDE_FILENAMES */
2156 res
= utime(path
, UTIME_ARG
);
2157 Py_END_ALLOW_THREADS
2158 #endif /* HAVE_UTIMES */
2161 #ifdef Py_WIN_WIDE_FILENAMES
2162 if (have_unicode_filename
)
2163 return posix_error_with_unicode_filename(wpath
);
2164 #endif /* Py_WIN_WIDE_FILENAMES */
2165 return posix_error_with_allocated_filename(path
);
2176 /* Process operations */
2178 PyDoc_STRVAR(posix__exit__doc__
,
2180 Exit to the system with specified status, without normal exit processing.");
2183 posix__exit(PyObject
*self
, PyObject
*args
)
2186 if (!PyArg_ParseTuple(args
, "i:_exit", &sts
))
2189 return NULL
; /* Make gcc -Wall happy */
2192 #if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
2194 free_string_array(char **array
, int count
)
2197 for (i
= 0; i
< count
; i
++)
2198 PyMem_Free(array
[i
]);
2205 PyDoc_STRVAR(posix_execv__doc__
,
2206 "execv(path, args)\n\n\
2207 Execute an executable path with arguments, replacing current process.\n\
2209 path: path of executable file\n\
2210 args: tuple or list of strings");
2213 posix_execv(PyObject
*self
, PyObject
*args
)
2219 PyObject
*(*getitem
)(PyObject
*, int);
2221 /* execv has two arguments: (path, argv), where
2222 argv is a list or tuple of strings. */
2224 if (!PyArg_ParseTuple(args
, "etO:execv",
2225 Py_FileSystemDefaultEncoding
,
2228 if (PyList_Check(argv
)) {
2229 argc
= PyList_Size(argv
);
2230 getitem
= PyList_GetItem
;
2232 else if (PyTuple_Check(argv
)) {
2233 argc
= PyTuple_Size(argv
);
2234 getitem
= PyTuple_GetItem
;
2237 PyErr_SetString(PyExc_TypeError
, "execv() arg 2 must be a tuple or list");
2242 argvlist
= PyMem_NEW(char *, argc
+1);
2243 if (argvlist
== NULL
) {
2245 return PyErr_NoMemory();
2247 for (i
= 0; i
< argc
; i
++) {
2248 if (!PyArg_Parse((*getitem
)(argv
, i
), "et",
2249 Py_FileSystemDefaultEncoding
,
2251 free_string_array(argvlist
, i
);
2252 PyErr_SetString(PyExc_TypeError
,
2253 "execv() arg 2 must contain only strings");
2259 argvlist
[argc
] = NULL
;
2261 execv(path
, argvlist
);
2263 /* If we get here it's definitely an error */
2265 free_string_array(argvlist
, argc
);
2267 return posix_error();
2271 PyDoc_STRVAR(posix_execve__doc__
,
2272 "execve(path, args, env)\n\n\
2273 Execute a path with arguments and environment, replacing current process.\n\
2275 path: path of executable file\n\
2276 args: tuple or list of arguments\n\
2277 env: dictionary of strings mapping to strings");
2280 posix_execve(PyObject
*self
, PyObject
*args
)
2283 PyObject
*argv
, *env
;
2286 PyObject
*key
, *val
, *keys
=NULL
, *vals
=NULL
;
2287 int i
, pos
, argc
, envc
;
2288 PyObject
*(*getitem
)(PyObject
*, int);
2291 /* execve has three arguments: (path, argv, env), where
2292 argv is a list or tuple of strings and env is a dictionary
2293 like posix.environ. */
2295 if (!PyArg_ParseTuple(args
, "etOO:execve",
2296 Py_FileSystemDefaultEncoding
,
2297 &path
, &argv
, &env
))
2299 if (PyList_Check(argv
)) {
2300 argc
= PyList_Size(argv
);
2301 getitem
= PyList_GetItem
;
2303 else if (PyTuple_Check(argv
)) {
2304 argc
= PyTuple_Size(argv
);
2305 getitem
= PyTuple_GetItem
;
2308 PyErr_SetString(PyExc_TypeError
,
2309 "execve() arg 2 must be a tuple or list");
2312 if (!PyMapping_Check(env
)) {
2313 PyErr_SetString(PyExc_TypeError
,
2314 "execve() arg 3 must be a mapping object");
2318 argvlist
= PyMem_NEW(char *, argc
+1);
2319 if (argvlist
== NULL
) {
2323 for (i
= 0; i
< argc
; i
++) {
2324 if (!PyArg_Parse((*getitem
)(argv
, i
),
2325 "et;execve() arg 2 must contain only strings",
2326 Py_FileSystemDefaultEncoding
,
2334 argvlist
[argc
] = NULL
;
2336 i
= PyMapping_Size(env
);
2339 envlist
= PyMem_NEW(char *, i
+ 1);
2340 if (envlist
== NULL
) {
2345 keys
= PyMapping_Keys(env
);
2346 vals
= PyMapping_Values(env
);
2349 if (!PyList_Check(keys
) || !PyList_Check(vals
)) {
2350 PyErr_SetString(PyExc_TypeError
,
2351 "execve(): env.keys() or env.values() is not a list");
2355 for (pos
= 0; pos
< i
; pos
++) {
2359 key
= PyList_GetItem(keys
, pos
);
2360 val
= PyList_GetItem(vals
, pos
);
2366 "s;execve() arg 3 contains a non-string key",
2370 "s;execve() arg 3 contains a non-string value",
2376 #if defined(PYOS_OS2)
2377 /* Omit Pseudo-Env Vars that Would Confuse Programs if Passed On */
2378 if (stricmp(k
, "BEGINLIBPATH") != 0 && stricmp(k
, "ENDLIBPATH") != 0) {
2380 len
= PyString_Size(key
) + PyString_Size(val
) + 2;
2381 p
= PyMem_NEW(char, len
);
2386 PyOS_snprintf(p
, len
, "%s=%s", k
, v
);
2387 envlist
[envc
++] = p
;
2388 #if defined(PYOS_OS2)
2394 execve(path
, argvlist
, envlist
);
2396 /* If we get here it's definitely an error */
2398 (void) posix_error();
2402 PyMem_DEL(envlist
[envc
]);
2405 free_string_array(argvlist
, lastarg
);
2412 #endif /* HAVE_EXECV */
2416 PyDoc_STRVAR(posix_spawnv__doc__
,
2417 "spawnv(mode, path, args)\n\n\
2418 Execute the program 'path' in a new process.\n\
2420 mode: mode of process creation\n\
2421 path: path of executable file\n\
2422 args: tuple or list of strings");
2425 posix_spawnv(PyObject
*self
, PyObject
*args
)
2431 Py_intptr_t spawnval
;
2432 PyObject
*(*getitem
)(PyObject
*, int);
2434 /* spawnv has three arguments: (mode, path, argv), where
2435 argv is a list or tuple of strings. */
2437 if (!PyArg_ParseTuple(args
, "ietO:spawnv", &mode
,
2438 Py_FileSystemDefaultEncoding
,
2441 if (PyList_Check(argv
)) {
2442 argc
= PyList_Size(argv
);
2443 getitem
= PyList_GetItem
;
2445 else if (PyTuple_Check(argv
)) {
2446 argc
= PyTuple_Size(argv
);
2447 getitem
= PyTuple_GetItem
;
2450 PyErr_SetString(PyExc_TypeError
,
2451 "spawnv() arg 2 must be a tuple or list");
2456 argvlist
= PyMem_NEW(char *, argc
+1);
2457 if (argvlist
== NULL
) {
2459 return PyErr_NoMemory();
2461 for (i
= 0; i
< argc
; i
++) {
2462 if (!PyArg_Parse((*getitem
)(argv
, i
), "et",
2463 Py_FileSystemDefaultEncoding
,
2465 free_string_array(argvlist
, i
);
2468 "spawnv() arg 2 must contain only strings");
2473 argvlist
[argc
] = NULL
;
2475 #if defined(PYOS_OS2) && defined(PYCC_GCC)
2476 Py_BEGIN_ALLOW_THREADS
2477 spawnval
= spawnv(mode
, path
, argvlist
);
2478 Py_END_ALLOW_THREADS
2480 if (mode
== _OLD_P_OVERLAY
)
2483 Py_BEGIN_ALLOW_THREADS
2484 spawnval
= _spawnv(mode
, path
, argvlist
);
2485 Py_END_ALLOW_THREADS
2488 free_string_array(argvlist
, argc
);
2492 return posix_error();
2494 #if SIZEOF_LONG == SIZEOF_VOID_P
2495 return Py_BuildValue("l", (long) spawnval
);
2497 return Py_BuildValue("L", (PY_LONG_LONG
) spawnval
);
2502 PyDoc_STRVAR(posix_spawnve__doc__
,
2503 "spawnve(mode, path, args, env)\n\n\
2504 Execute the program 'path' in a new process.\n\
2506 mode: mode of process creation\n\
2507 path: path of executable file\n\
2508 args: tuple or list of arguments\n\
2509 env: dictionary of strings mapping to strings");
2512 posix_spawnve(PyObject
*self
, PyObject
*args
)
2515 PyObject
*argv
, *env
;
2518 PyObject
*key
, *val
, *keys
=NULL
, *vals
=NULL
, *res
=NULL
;
2519 int mode
, i
, pos
, argc
, envc
;
2520 Py_intptr_t spawnval
;
2521 PyObject
*(*getitem
)(PyObject
*, int);
2524 /* spawnve has four arguments: (mode, path, argv, env), where
2525 argv is a list or tuple of strings and env is a dictionary
2526 like posix.environ. */
2528 if (!PyArg_ParseTuple(args
, "ietOO:spawnve", &mode
,
2529 Py_FileSystemDefaultEncoding
,
2530 &path
, &argv
, &env
))
2532 if (PyList_Check(argv
)) {
2533 argc
= PyList_Size(argv
);
2534 getitem
= PyList_GetItem
;
2536 else if (PyTuple_Check(argv
)) {
2537 argc
= PyTuple_Size(argv
);
2538 getitem
= PyTuple_GetItem
;
2541 PyErr_SetString(PyExc_TypeError
,
2542 "spawnve() arg 2 must be a tuple or list");
2545 if (!PyMapping_Check(env
)) {
2546 PyErr_SetString(PyExc_TypeError
,
2547 "spawnve() arg 3 must be a mapping object");
2551 argvlist
= PyMem_NEW(char *, argc
+1);
2552 if (argvlist
== NULL
) {
2556 for (i
= 0; i
< argc
; i
++) {
2557 if (!PyArg_Parse((*getitem
)(argv
, i
),
2558 "et;spawnve() arg 2 must contain only strings",
2559 Py_FileSystemDefaultEncoding
,
2567 argvlist
[argc
] = NULL
;
2569 i
= PyMapping_Size(env
);
2572 envlist
= PyMem_NEW(char *, i
+ 1);
2573 if (envlist
== NULL
) {
2578 keys
= PyMapping_Keys(env
);
2579 vals
= PyMapping_Values(env
);
2582 if (!PyList_Check(keys
) || !PyList_Check(vals
)) {
2583 PyErr_SetString(PyExc_TypeError
,
2584 "spawnve(): env.keys() or env.values() is not a list");
2588 for (pos
= 0; pos
< i
; pos
++) {
2592 key
= PyList_GetItem(keys
, pos
);
2593 val
= PyList_GetItem(vals
, pos
);
2599 "s;spawnve() arg 3 contains a non-string key",
2603 "s;spawnve() arg 3 contains a non-string value",
2608 len
= PyString_Size(key
) + PyString_Size(val
) + 2;
2609 p
= PyMem_NEW(char, len
);
2614 PyOS_snprintf(p
, len
, "%s=%s", k
, v
);
2615 envlist
[envc
++] = p
;
2619 #if defined(PYOS_OS2) && defined(PYCC_GCC)
2620 Py_BEGIN_ALLOW_THREADS
2621 spawnval
= spawnve(mode
, path
, argvlist
, envlist
);
2622 Py_END_ALLOW_THREADS
2624 if (mode
== _OLD_P_OVERLAY
)
2627 Py_BEGIN_ALLOW_THREADS
2628 spawnval
= _spawnve(mode
, path
, argvlist
, envlist
);
2629 Py_END_ALLOW_THREADS
2633 (void) posix_error();
2635 #if SIZEOF_LONG == SIZEOF_VOID_P
2636 res
= Py_BuildValue("l", (long) spawnval
);
2638 res
= Py_BuildValue("L", (PY_LONG_LONG
) spawnval
);
2643 PyMem_DEL(envlist
[envc
]);
2646 free_string_array(argvlist
, lastarg
);
2654 /* OS/2 supports spawnvp & spawnvpe natively */
2655 #if defined(PYOS_OS2)
2656 PyDoc_STRVAR(posix_spawnvp__doc__
,
2657 "spawnvp(mode, file, args)\n\n\
2658 Execute the program 'file' in a new process, using the environment\n\
2659 search path to find the file.\n\
2661 mode: mode of process creation\n\
2662 file: executable file name\n\
2663 args: tuple or list of strings");
2666 posix_spawnvp(PyObject
*self
, PyObject
*args
)
2672 Py_intptr_t spawnval
;
2673 PyObject
*(*getitem
)(PyObject
*, int);
2675 /* spawnvp has three arguments: (mode, path, argv), where
2676 argv is a list or tuple of strings. */
2678 if (!PyArg_ParseTuple(args
, "ietO:spawnvp", &mode
,
2679 Py_FileSystemDefaultEncoding
,
2682 if (PyList_Check(argv
)) {
2683 argc
= PyList_Size(argv
);
2684 getitem
= PyList_GetItem
;
2686 else if (PyTuple_Check(argv
)) {
2687 argc
= PyTuple_Size(argv
);
2688 getitem
= PyTuple_GetItem
;
2691 PyErr_SetString(PyExc_TypeError
,
2692 "spawnvp() arg 2 must be a tuple or list");
2697 argvlist
= PyMem_NEW(char *, argc
+1);
2698 if (argvlist
== NULL
) {
2700 return PyErr_NoMemory();
2702 for (i
= 0; i
< argc
; i
++) {
2703 if (!PyArg_Parse((*getitem
)(argv
, i
), "et",
2704 Py_FileSystemDefaultEncoding
,
2706 free_string_array(argvlist
, i
);
2709 "spawnvp() arg 2 must contain only strings");
2714 argvlist
[argc
] = NULL
;
2716 Py_BEGIN_ALLOW_THREADS
2717 #if defined(PYCC_GCC)
2718 spawnval
= spawnvp(mode
, path
, argvlist
);
2720 spawnval
= _spawnvp(mode
, path
, argvlist
);
2722 Py_END_ALLOW_THREADS
2724 free_string_array(argvlist
, argc
);
2728 return posix_error();
2730 return Py_BuildValue("l", (long) spawnval
);
2734 PyDoc_STRVAR(posix_spawnvpe__doc__
,
2735 "spawnvpe(mode, file, args, env)\n\n\
2736 Execute the program 'file' in a new process, using the environment\n\
2737 search path to find the file.\n\
2739 mode: mode of process creation\n\
2740 file: executable file name\n\
2741 args: tuple or list of arguments\n\
2742 env: dictionary of strings mapping to strings");
2745 posix_spawnvpe(PyObject
*self
, PyObject
*args
)
2748 PyObject
*argv
, *env
;
2751 PyObject
*key
, *val
, *keys
=NULL
, *vals
=NULL
, *res
=NULL
;
2752 int mode
, i
, pos
, argc
, envc
;
2753 Py_intptr_t spawnval
;
2754 PyObject
*(*getitem
)(PyObject
*, int);
2757 /* spawnvpe has four arguments: (mode, path, argv, env), where
2758 argv is a list or tuple of strings and env is a dictionary
2759 like posix.environ. */
2761 if (!PyArg_ParseTuple(args
, "ietOO:spawnvpe", &mode
,
2762 Py_FileSystemDefaultEncoding
,
2763 &path
, &argv
, &env
))
2765 if (PyList_Check(argv
)) {
2766 argc
= PyList_Size(argv
);
2767 getitem
= PyList_GetItem
;
2769 else if (PyTuple_Check(argv
)) {
2770 argc
= PyTuple_Size(argv
);
2771 getitem
= PyTuple_GetItem
;
2774 PyErr_SetString(PyExc_TypeError
,
2775 "spawnvpe() arg 2 must be a tuple or list");
2778 if (!PyMapping_Check(env
)) {
2779 PyErr_SetString(PyExc_TypeError
,
2780 "spawnvpe() arg 3 must be a mapping object");
2784 argvlist
= PyMem_NEW(char *, argc
+1);
2785 if (argvlist
== NULL
) {
2789 for (i
= 0; i
< argc
; i
++) {
2790 if (!PyArg_Parse((*getitem
)(argv
, i
),
2791 "et;spawnvpe() arg 2 must contain only strings",
2792 Py_FileSystemDefaultEncoding
,
2800 argvlist
[argc
] = NULL
;
2802 i
= PyMapping_Size(env
);
2805 envlist
= PyMem_NEW(char *, i
+ 1);
2806 if (envlist
== NULL
) {
2811 keys
= PyMapping_Keys(env
);
2812 vals
= PyMapping_Values(env
);
2815 if (!PyList_Check(keys
) || !PyList_Check(vals
)) {
2816 PyErr_SetString(PyExc_TypeError
,
2817 "spawnvpe(): env.keys() or env.values() is not a list");
2821 for (pos
= 0; pos
< i
; pos
++) {
2825 key
= PyList_GetItem(keys
, pos
);
2826 val
= PyList_GetItem(vals
, pos
);
2832 "s;spawnvpe() arg 3 contains a non-string key",
2836 "s;spawnvpe() arg 3 contains a non-string value",
2841 len
= PyString_Size(key
) + PyString_Size(val
) + 2;
2842 p
= PyMem_NEW(char, len
);
2847 PyOS_snprintf(p
, len
, "%s=%s", k
, v
);
2848 envlist
[envc
++] = p
;
2852 Py_BEGIN_ALLOW_THREADS
2853 #if defined(PYCC_GCC)
2854 spawnval
= spawnve(mode
, path
, argvlist
, envlist
);
2856 spawnval
= _spawnve(mode
, path
, argvlist
, envlist
);
2858 Py_END_ALLOW_THREADS
2861 (void) posix_error();
2863 res
= Py_BuildValue("l", (long) spawnval
);
2867 PyMem_DEL(envlist
[envc
]);
2870 free_string_array(argvlist
, lastarg
);
2877 #endif /* PYOS_OS2 */
2878 #endif /* HAVE_SPAWNV */
2882 PyDoc_STRVAR(posix_fork1__doc__
,
2883 "fork1() -> pid\n\n\
2884 Fork a child process with a single multiplexed (i.e., not bound) thread.\n\
2886 Return 0 to child process and PID of child to parent process.");
2889 posix_fork1(PyObject
*self
, PyObject
*noargs
)
2893 return posix_error();
2895 return PyInt_FromLong((long)pid
);
2901 PyDoc_STRVAR(posix_fork__doc__
,
2903 Fork a child process.\n\
2904 Return 0 to child process and PID of child to parent process.");
2907 posix_fork(PyObject
*self
, PyObject
*noargs
)
2911 return posix_error();
2914 return PyInt_FromLong((long)pid
);
2918 /* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
2919 /* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
2920 #if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
2921 #define DEV_PTY_FILE "/dev/ptc"
2922 #define HAVE_DEV_PTMX
2924 #define DEV_PTY_FILE "/dev/ptmx"
2927 #if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
2931 #ifdef HAVE_LIBUTIL_H
2932 #include <libutil.h>
2933 #endif /* HAVE_LIBUTIL_H */
2934 #endif /* HAVE_PTY_H */
2935 #ifdef HAVE_STROPTS_H
2936 #include <stropts.h>
2938 #endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
2940 #if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
2941 PyDoc_STRVAR(posix_openpty__doc__
,
2942 "openpty() -> (master_fd, slave_fd)\n\n\
2943 Open a pseudo-terminal, returning open fd's for both master and slave end.\n");
2946 posix_openpty(PyObject
*self
, PyObject
*noargs
)
2948 int master_fd
, slave_fd
;
2949 #ifndef HAVE_OPENPTY
2952 #if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
2953 PyOS_sighandler_t sig_saved
;
2955 extern char *ptsname();
2960 if (openpty(&master_fd
, &slave_fd
, NULL
, NULL
, NULL
) != 0)
2961 return posix_error();
2962 #elif defined(HAVE__GETPTY)
2963 slave_name
= _getpty(&master_fd
, O_RDWR
, 0666, 0);
2964 if (slave_name
== NULL
)
2965 return posix_error();
2967 slave_fd
= open(slave_name
, O_RDWR
);
2969 return posix_error();
2971 master_fd
= open(DEV_PTY_FILE
, O_RDWR
| O_NOCTTY
); /* open master */
2973 return posix_error();
2974 sig_saved
= PyOS_setsig(SIGCHLD
, SIG_DFL
);
2975 /* change permission of slave */
2976 if (grantpt(master_fd
) < 0) {
2977 PyOS_setsig(SIGCHLD
, sig_saved
);
2978 return posix_error();
2981 if (unlockpt(master_fd
) < 0) {
2982 PyOS_setsig(SIGCHLD
, sig_saved
);
2983 return posix_error();
2985 PyOS_setsig(SIGCHLD
, sig_saved
);
2986 slave_name
= ptsname(master_fd
); /* get name of slave */
2987 if (slave_name
== NULL
)
2988 return posix_error();
2989 slave_fd
= open(slave_name
, O_RDWR
| O_NOCTTY
); /* open slave */
2991 return posix_error();
2992 #if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
2993 ioctl(slave_fd
, I_PUSH
, "ptem"); /* push ptem */
2994 ioctl(slave_fd
, I_PUSH
, "ldterm"); /* push ldterm */
2996 ioctl(slave_fd
, I_PUSH
, "ttcompat"); /* push ttcompat */
2998 #endif /* HAVE_CYGWIN */
2999 #endif /* HAVE_OPENPTY */
3001 return Py_BuildValue("(ii)", master_fd
, slave_fd
);
3004 #endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
3007 PyDoc_STRVAR(posix_forkpty__doc__
,
3008 "forkpty() -> (pid, master_fd)\n\n\
3009 Fork a new process with a new pseudo-terminal as controlling tty.\n\n\
3010 Like fork(), return 0 as pid to child process, and PID of child to parent.\n\
3011 To both, return fd of newly opened pseudo-terminal.\n");
3014 posix_forkpty(PyObject
*self
, PyObject
*noargs
)
3016 int master_fd
= -1, pid
;
3018 pid
= forkpty(&master_fd
, NULL
, NULL
, NULL
);
3020 return posix_error();
3023 return Py_BuildValue("(ii)", pid
, master_fd
);
3028 PyDoc_STRVAR(posix_getegid__doc__
,
3029 "getegid() -> egid\n\n\
3030 Return the current process's effective group id.");
3033 posix_getegid(PyObject
*self
, PyObject
*noargs
)
3035 return PyInt_FromLong((long)getegid());
3041 PyDoc_STRVAR(posix_geteuid__doc__
,
3042 "geteuid() -> euid\n\n\
3043 Return the current process's effective user id.");
3046 posix_geteuid(PyObject
*self
, PyObject
*noargs
)
3048 return PyInt_FromLong((long)geteuid());
3054 PyDoc_STRVAR(posix_getgid__doc__
,
3055 "getgid() -> gid\n\n\
3056 Return the current process's group id.");
3059 posix_getgid(PyObject
*self
, PyObject
*noargs
)
3061 return PyInt_FromLong((long)getgid());
3066 PyDoc_STRVAR(posix_getpid__doc__
,
3067 "getpid() -> pid\n\n\
3068 Return the current process id");
3071 posix_getpid(PyObject
*self
, PyObject
*noargs
)
3073 return PyInt_FromLong((long)getpid());
3077 #ifdef HAVE_GETGROUPS
3078 PyDoc_STRVAR(posix_getgroups__doc__
,
3079 "getgroups() -> list of group IDs\n\n\
3080 Return list of supplemental group IDs for the process.");
3083 posix_getgroups(PyObject
*self
, PyObject
*noargs
)
3085 PyObject
*result
= NULL
;
3088 #define MAX_GROUPS NGROUPS_MAX
3090 /* defined to be 16 on Solaris7, so this should be a small number */
3091 #define MAX_GROUPS 64
3093 gid_t grouplist
[MAX_GROUPS
];
3096 n
= getgroups(MAX_GROUPS
, grouplist
);
3100 result
= PyList_New(n
);
3101 if (result
!= NULL
) {
3103 for (i
= 0; i
< n
; ++i
) {
3104 PyObject
*o
= PyInt_FromLong((long)grouplist
[i
]);
3110 PyList_SET_ITEM(result
, i
, o
);
3120 PyDoc_STRVAR(posix_getpgid__doc__
,
3121 "getpgid(pid) -> pgid\n\n\
3122 Call the system call getpgid().");
3125 posix_getpgid(PyObject
*self
, PyObject
*args
)
3128 if (!PyArg_ParseTuple(args
, "i:getpgid", &pid
))
3130 pgid
= getpgid(pid
);
3132 return posix_error();
3133 return PyInt_FromLong((long)pgid
);
3135 #endif /* HAVE_GETPGID */
3139 PyDoc_STRVAR(posix_getpgrp__doc__
,
3140 "getpgrp() -> pgrp\n\n\
3141 Return the current process group id.");
3144 posix_getpgrp(PyObject
*self
, PyObject
*noargs
)
3146 #ifdef GETPGRP_HAVE_ARG
3147 return PyInt_FromLong((long)getpgrp(0));
3148 #else /* GETPGRP_HAVE_ARG */
3149 return PyInt_FromLong((long)getpgrp());
3150 #endif /* GETPGRP_HAVE_ARG */
3152 #endif /* HAVE_GETPGRP */
3156 PyDoc_STRVAR(posix_setpgrp__doc__
,
3158 Make this process a session leader.");
3161 posix_setpgrp(PyObject
*self
, PyObject
*noargs
)
3163 #ifdef SETPGRP_HAVE_ARG
3164 if (setpgrp(0, 0) < 0)
3165 #else /* SETPGRP_HAVE_ARG */
3167 #endif /* SETPGRP_HAVE_ARG */
3168 return posix_error();
3173 #endif /* HAVE_SETPGRP */
3176 PyDoc_STRVAR(posix_getppid__doc__
,
3177 "getppid() -> ppid\n\n\
3178 Return the parent's process id.");
3181 posix_getppid(PyObject
*self
, PyObject
*noargs
)
3183 return PyInt_FromLong((long)getppid());
3188 #ifdef HAVE_GETLOGIN
3189 PyDoc_STRVAR(posix_getlogin__doc__
,
3190 "getlogin() -> string\n\n\
3191 Return the actual login name.");
3194 posix_getlogin(PyObject
*self
, PyObject
*noargs
)
3196 PyObject
*result
= NULL
;
3198 int old_errno
= errno
;
3206 PyErr_SetString(PyExc_OSError
,
3207 "unable to determine login name");
3210 result
= PyString_FromString(name
);
3218 PyDoc_STRVAR(posix_getuid__doc__
,
3219 "getuid() -> uid\n\n\
3220 Return the current process's user id.");
3223 posix_getuid(PyObject
*self
, PyObject
*noargs
)
3225 return PyInt_FromLong((long)getuid());
3231 PyDoc_STRVAR(posix_kill__doc__
,
3232 "kill(pid, sig)\n\n\
3233 Kill a process with a signal.");
3236 posix_kill(PyObject
*self
, PyObject
*args
)
3239 if (!PyArg_ParseTuple(args
, "ii:kill", &pid
, &sig
))
3241 #if defined(PYOS_OS2) && !defined(PYCC_GCC)
3242 if (sig
== XCPT_SIGNAL_INTR
|| sig
== XCPT_SIGNAL_BREAK
) {
3244 if ((rc
= DosSendSignalException(pid
, sig
)) != NO_ERROR
)
3245 return os2_error(rc
);
3247 } else if (sig
== XCPT_SIGNAL_KILLPROC
) {
3249 if ((rc
= DosKillProcess(DKP_PROCESS
, pid
)) != NO_ERROR
)
3250 return os2_error(rc
);
3253 return NULL
; /* Unrecognized Signal Requested */
3255 if (kill(pid
, sig
) == -1)
3256 return posix_error();
3264 PyDoc_STRVAR(posix_killpg__doc__
,
3265 "killpg(pgid, sig)\n\n\
3266 Kill a process group with a signal.");
3269 posix_killpg(PyObject
*self
, PyObject
*args
)
3272 if (!PyArg_ParseTuple(args
, "ii:killpg", &pgid
, &sig
))
3274 if (killpg(pgid
, sig
) == -1)
3275 return posix_error();
3283 #ifdef HAVE_SYS_LOCK_H
3284 #include <sys/lock.h>
3287 PyDoc_STRVAR(posix_plock__doc__
,
3289 Lock program segments into memory.");
3292 posix_plock(PyObject
*self
, PyObject
*args
)
3295 if (!PyArg_ParseTuple(args
, "i:plock", &op
))
3297 if (plock(op
) == -1)
3298 return posix_error();
3306 PyDoc_STRVAR(posix_popen__doc__
,
3307 "popen(command [, mode='r' [, bufsize]]) -> pipe\n\n\
3308 Open a pipe to/from a command returning a file object.");
3310 #if defined(PYOS_OS2)
3311 #if defined(PYCC_VACPP)
3313 async_system(const char *command
)
3315 char errormsg
[256], args
[1024];
3319 char *shell
= getenv("COMSPEC");
3323 /* avoid overflowing the argument buffer */
3324 if (strlen(shell
) + 3 + strlen(command
) >= 1024)
3325 return ERROR_NOT_ENOUGH_MEMORY
3328 strcat(args
, shell
);
3329 strcat(args
, "/c ");
3330 strcat(args
, command
);
3332 /* execute asynchronously, inheriting the environment */
3333 rc
= DosExecPgm(errormsg
,
3344 popen(const char *command
, const char *mode
, int pipesize
, int *err
)
3350 /* mode determines which of stdin or stdout is reconnected to
3351 * the pipe to the child
3353 if (strchr(mode
, 'r') != NULL
) {
3354 tgt_fd
= 1; /* stdout */
3355 } else if (strchr(mode
, 'w')) {
3356 tgt_fd
= 0; /* stdin */
3358 *err
= ERROR_INVALID_ACCESS
;
3362 /* setup the pipe */
3363 if ((rc
= DosCreatePipe(&pipeh
[0], &pipeh
[1], pipesize
)) != NO_ERROR
) {
3368 /* prevent other threads accessing stdio */
3371 /* reconnect stdio and execute child */
3374 if (dup2(pipeh
[tgtfd
], tgtfd
) == 0) {
3375 DosClose(pipeh
[tgtfd
]);
3376 rc
= async_system(command
);
3383 /* allow other threads access to stdio */
3386 /* if execution of child was successful return file stream */
3388 return fdopen(pipeh
[1 - tgtfd
], mode
);
3390 DosClose(pipeh
[1 - tgtfd
]);
3397 posix_popen(PyObject
*self
, PyObject
*args
)
3401 int err
, bufsize
= -1;
3404 if (!PyArg_ParseTuple(args
, "s|si:popen", &name
, &mode
, &bufsize
))
3406 Py_BEGIN_ALLOW_THREADS
3407 fp
= popen(name
, mode
, (bufsize
> 0) ? bufsize
: 4096, &err
);
3408 Py_END_ALLOW_THREADS
3410 return os2_error(err
);
3412 f
= PyFile_FromFile(fp
, name
, mode
, fclose
);
3414 PyFile_SetBufSize(f
, bufsize
);
3418 #elif defined(PYCC_GCC)
3420 /* standard posix version of popen() support */
3422 posix_popen(PyObject
*self
, PyObject
*args
)
3429 if (!PyArg_ParseTuple(args
, "s|si:popen", &name
, &mode
, &bufsize
))
3431 Py_BEGIN_ALLOW_THREADS
3432 fp
= popen(name
, mode
);
3433 Py_END_ALLOW_THREADS
3435 return posix_error();
3436 f
= PyFile_FromFile(fp
, name
, mode
, pclose
);
3438 PyFile_SetBufSize(f
, bufsize
);
3442 /* fork() under OS/2 has lots'o'warts
3443 * EMX supports pipe() and spawn*() so we can synthesize popen[234]()
3444 * most of this code is a ripoff of the win32 code, but using the
3445 * capabilities of EMX's C library routines
3448 /* These tell _PyPopen() whether to return 1, 2, or 3 file objects. */
3454 static PyObject
*_PyPopen(char *, int, int, int);
3455 static int _PyPclose(FILE *file
);
3458 * Internal dictionary mapping popen* file pointers to process handles,
3459 * for use when retrieving the process exit code. See _PyPclose() below
3460 * for more information on this dictionary's use.
3462 static PyObject
*_PyPopenProcs
= NULL
;
3464 /* os2emx version of popen2()
3466 * The result of this function is a pipe (file) connected to the
3467 * process's stdin, and a pipe connected to the process's stdout.
3471 os2emx_popen2(PyObject
*self
, PyObject
*args
)
3479 if (!PyArg_ParseTuple(args
, "s|si:popen2", &cmdstring
, &mode
, &bufsize
))
3484 else if (*mode
!= 'b') {
3485 PyErr_SetString(PyExc_ValueError
, "mode must be 't' or 'b'");
3490 f
= _PyPopen(cmdstring
, tm
, POPEN_2
, bufsize
);
3496 * Variation on os2emx.popen2
3498 * The result of this function is 3 pipes - the process's stdin,
3503 os2emx_popen3(PyObject
*self
, PyObject
*args
)
3511 if (!PyArg_ParseTuple(args
, "s|si:popen3", &cmdstring
, &mode
, &bufsize
))
3516 else if (*mode
!= 'b') {
3517 PyErr_SetString(PyExc_ValueError
, "mode must be 't' or 'b'");
3522 f
= _PyPopen(cmdstring
, tm
, POPEN_3
, bufsize
);
3528 * Variation on os2emx.popen2
3530 * The result of this function is 2 pipes - the processes stdin,
3531 * and stdout+stderr combined as a single pipe.
3535 os2emx_popen4(PyObject
*self
, PyObject
*args
)
3543 if (!PyArg_ParseTuple(args
, "s|si:popen4", &cmdstring
, &mode
, &bufsize
))
3548 else if (*mode
!= 'b') {
3549 PyErr_SetString(PyExc_ValueError
, "mode must be 't' or 'b'");
3554 f
= _PyPopen(cmdstring
, tm
, POPEN_4
, bufsize
);
3559 /* a couple of structures for convenient handling of multiple
3560 * file handles and pipes
3574 /* The following code is derived from the win32 code */
3577 _PyPopen(char *cmdstring
, int mode
, int n
, int bufsize
)
3579 struct file_ref stdio
[3];
3580 struct pipe_ref p_fd
[3];
3582 int file_count
, i
, pipe_err
, pipe_pid
;
3583 char *shell
, *sh_name
, *opt
, *rd_mode
, *wr_mode
;
3584 PyObject
*f
, *p_f
[3];
3586 /* file modes for subsequent fdopen's on pipe handles */
3598 /* prepare shell references */
3599 if ((shell
= getenv("EMXSHELL")) == NULL
)
3600 if ((shell
= getenv("COMSPEC")) == NULL
)
3603 return posix_error();
3606 sh_name
= _getname(shell
);
3607 if (stricmp(sh_name
, "cmd.exe") == 0 || stricmp(sh_name
, "4os2.exe") == 0)
3612 /* save current stdio fds + their flags, and set not inheritable */
3614 while (pipe_err
>= 0 && i
< 3)
3616 pipe_err
= stdio
[i
].handle
= dup(i
);
3617 stdio
[i
].flags
= fcntl(i
, F_GETFD
, 0);
3618 fcntl(stdio
[i
].handle
, F_SETFD
, stdio
[i
].flags
| FD_CLOEXEC
);
3623 /* didn't get them all saved - clean up and bail out */
3624 int saved_err
= errno
;
3627 close(stdio
[i
].handle
);
3630 return posix_error();
3633 /* create pipe ends */
3638 while ((pipe_err
== 0) && (i
< file_count
))
3639 pipe_err
= pipe((int *)&p_fd
[i
++]);
3642 /* didn't get them all made - clean up and bail out */
3649 return posix_error();
3652 /* change the actual standard IO streams over temporarily,
3653 * making the retained pipe ends non-inheritable
3658 if (dup2(p_fd
[0].rd
, 0) == 0)
3661 i
= fcntl(p_fd
[0].wr
, F_GETFD
, 0);
3662 fcntl(p_fd
[0].wr
, F_SETFD
, i
| FD_CLOEXEC
);
3663 if ((p_s
[0] = fdopen(p_fd
[0].wr
, wr_mode
)) == NULL
)
3677 if (dup2(p_fd
[1].wr
, 1) == 1)
3680 i
= fcntl(p_fd
[1].rd
, F_GETFD
, 0);
3681 fcntl(p_fd
[1].rd
, F_SETFD
, i
| FD_CLOEXEC
);
3682 if ((p_s
[1] = fdopen(p_fd
[1].rd
, rd_mode
)) == NULL
)
3694 /* - stderr, as required */
3700 if (dup2(p_fd
[2].wr
, 2) == 2)
3703 i
= fcntl(p_fd
[2].rd
, F_GETFD
, 0);
3704 fcntl(p_fd
[2].rd
, F_SETFD
, i
| FD_CLOEXEC
);
3705 if ((p_s
[2] = fdopen(p_fd
[2].rd
, rd_mode
)) == NULL
)
3720 if (dup2(1, 2) != 2)
3728 /* spawn the child process */
3731 pipe_pid
= spawnlp(P_NOWAIT
, shell
, shell
, opt
, cmdstring
, (char *)0);
3738 /* save the PID into the FILE structure
3739 * NOTE: this implementation doesn't actually
3740 * take advantage of this, but do it for
3741 * completeness - AIM Apr01
3743 for (i
= 0; i
< file_count
; i
++)
3744 p_s
[i
]->_pid
= pipe_pid
;
3748 /* reset standard IO to normal */
3749 for (i
= 0; i
< 3; i
++)
3751 dup2(stdio
[i
].handle
, i
);
3752 fcntl(i
, F_SETFD
, stdio
[i
].flags
);
3753 close(stdio
[i
].handle
);
3756 /* if any remnant problems, clean up and bail out */
3759 for (i
= 0; i
< 3; i
++)
3765 return posix_error_with_filename(cmdstring
);
3768 /* build tuple of file objects to return */
3769 if ((p_f
[0] = PyFile_FromFile(p_s
[0], cmdstring
, wr_mode
, _PyPclose
)) != NULL
)
3770 PyFile_SetBufSize(p_f
[0], bufsize
);
3771 if ((p_f
[1] = PyFile_FromFile(p_s
[1], cmdstring
, rd_mode
, _PyPclose
)) != NULL
)
3772 PyFile_SetBufSize(p_f
[1], bufsize
);
3775 if ((p_f
[2] = PyFile_FromFile(p_s
[2], cmdstring
, rd_mode
, _PyPclose
)) != NULL
)
3776 PyFile_SetBufSize(p_f
[0], bufsize
);
3777 f
= PyTuple_Pack(3, p_f
[0], p_f
[1], p_f
[2]);
3780 f
= PyTuple_Pack(2, p_f
[0], p_f
[1]);
3783 * Insert the files we've created into the process dictionary
3784 * all referencing the list with the process handle and the
3785 * initial number of files (see description below in _PyPclose).
3786 * Since if _PyPclose later tried to wait on a process when all
3787 * handles weren't closed, it could create a deadlock with the
3788 * child, we spend some energy here to try to ensure that we
3789 * either insert all file handles into the dictionary or none
3790 * at all. It's a little clumsy with the various popen modes
3791 * and variable number of files involved.
3795 _PyPopenProcs
= PyDict_New();
3800 PyObject
*procObj
, *pidObj
, *intObj
, *fileObj
[3];
3803 fileObj
[0] = fileObj
[1] = fileObj
[2] = NULL
;
3804 ins_rc
[0] = ins_rc
[1] = ins_rc
[2] = 0;
3806 procObj
= PyList_New(2);
3807 pidObj
= PyInt_FromLong((long) pipe_pid
);
3808 intObj
= PyInt_FromLong((long) file_count
);
3810 if (procObj
&& pidObj
&& intObj
)
3812 PyList_SetItem(procObj
, 0, pidObj
);
3813 PyList_SetItem(procObj
, 1, intObj
);
3815 fileObj
[0] = PyLong_FromVoidPtr(p_s
[0]);
3818 ins_rc
[0] = PyDict_SetItem(_PyPopenProcs
,
3822 fileObj
[1] = PyLong_FromVoidPtr(p_s
[1]);
3825 ins_rc
[1] = PyDict_SetItem(_PyPopenProcs
,
3829 if (file_count
>= 3)
3831 fileObj
[2] = PyLong_FromVoidPtr(p_s
[2]);
3834 ins_rc
[2] = PyDict_SetItem(_PyPopenProcs
,
3840 if (ins_rc
[0] < 0 || !fileObj
[0] ||
3841 ins_rc
[1] < 0 || (file_count
> 1 && !fileObj
[1]) ||
3842 ins_rc
[2] < 0 || (file_count
> 2 && !fileObj
[2]))
3844 /* Something failed - remove any dictionary
3845 * entries that did make it.
3847 if (!ins_rc
[0] && fileObj
[0])
3849 PyDict_DelItem(_PyPopenProcs
,
3852 if (!ins_rc
[1] && fileObj
[1])
3854 PyDict_DelItem(_PyPopenProcs
,
3857 if (!ins_rc
[2] && fileObj
[2])
3859 PyDict_DelItem(_PyPopenProcs
,
3866 * Clean up our localized references for the dictionary keys
3867 * and value since PyDict_SetItem will Py_INCREF any copies
3868 * that got placed in the dictionary.
3870 Py_XDECREF(procObj
);
3871 Py_XDECREF(fileObj
[0]);
3872 Py_XDECREF(fileObj
[1]);
3873 Py_XDECREF(fileObj
[2]);
3876 /* Child is launched. */
3881 * Wrapper for fclose() to use for popen* files, so we can retrieve the
3882 * exit code for the child process and return as a result of the close.
3884 * This function uses the _PyPopenProcs dictionary in order to map the
3885 * input file pointer to information about the process that was
3886 * originally created by the popen* call that created the file pointer.
3887 * The dictionary uses the file pointer as a key (with one entry
3888 * inserted for each file returned by the original popen* call) and a
3889 * single list object as the value for all files from a single call.
3890 * The list object contains the Win32 process handle at [0], and a file
3891 * count at [1], which is initialized to the total number of file
3892 * handles using that list.
3894 * This function closes whichever handle it is passed, and decrements
3895 * the file count in the dictionary for the process handle pointed to
3896 * by this file. On the last close (when the file count reaches zero),
3897 * this function will wait for the child process and then return its
3898 * exit code as the result of the close() operation. This permits the
3899 * files to be closed in any order - it is always the close() of the
3900 * final handle that will return the exit code.
3902 * NOTE: This function is currently called with the GIL released.
3903 * hence we use the GILState API to manage our state.
3906 static int _PyPclose(FILE *file
)
3911 PyObject
*procObj
, *pidObj
, *intObj
, *fileObj
;
3914 PyGILState_STATE state
;
3917 /* Close the file handle first, to ensure it can't block the
3918 * child from exiting if it's the last handle.
3920 result
= fclose(file
);
3923 state
= PyGILState_Ensure();
3927 if ((fileObj
= PyLong_FromVoidPtr(file
)) != NULL
&&
3928 (procObj
= PyDict_GetItem(_PyPopenProcs
,
3929 fileObj
)) != NULL
&&
3930 (pidObj
= PyList_GetItem(procObj
,0)) != NULL
&&
3931 (intObj
= PyList_GetItem(procObj
,1)) != NULL
)
3933 pipe_pid
= (int) PyInt_AsLong(pidObj
);
3934 file_count
= (int) PyInt_AsLong(intObj
);
3938 /* Still other files referencing process */
3940 PyList_SetItem(procObj
,1,
3941 PyInt_FromLong((long) file_count
));
3945 /* Last file for this process */
3946 if (result
!= EOF
&&
3947 waitpid(pipe_pid
, &exit_code
, 0) == pipe_pid
)
3949 /* extract exit status */
3950 if (WIFEXITED(exit_code
))
3952 result
= WEXITSTATUS(exit_code
);
3962 /* Indicate failure - this will cause the file object
3963 * to raise an I/O error and translate the last
3964 * error code from errno. We do have a problem with
3965 * last errors that overlap the normal errno table,
3966 * but that's a consistent problem with the file object.
3972 /* Remove this file pointer from dictionary */
3973 PyDict_DelItem(_PyPopenProcs
, fileObj
);
3975 if (PyDict_Size(_PyPopenProcs
) == 0)
3977 Py_DECREF(_PyPopenProcs
);
3978 _PyPopenProcs
= NULL
;
3981 } /* if object retrieval ok */
3983 Py_XDECREF(fileObj
);
3984 } /* if _PyPopenProcs */
3987 PyGILState_Release(state
);
3992 #endif /* PYCC_??? */
3994 #elif defined(MS_WINDOWS)
3997 * Portable 'popen' replacement for Win32.
3999 * Written by Bill Tutt <billtut@microsoft.com>. Minor tweaks
4000 * and 2.0 integration by Fredrik Lundh <fredrik@pythonware.com>
4001 * Return code handling by David Bolen <db3l@fitlinxx.com>.
4008 /* These tell _PyPopen() wether to return 1, 2, or 3 file objects. */
4014 static PyObject
*_PyPopen(char *, int, int);
4015 static int _PyPclose(FILE *file
);
4018 * Internal dictionary mapping popen* file pointers to process handles,
4019 * for use when retrieving the process exit code. See _PyPclose() below
4020 * for more information on this dictionary's use.
4022 static PyObject
*_PyPopenProcs
= NULL
;
4025 /* popen that works from a GUI.
4027 * The result of this function is a pipe (file) connected to the
4028 * processes stdin or stdout, depending on the requested mode.
4032 posix_popen(PyObject
*self
, PyObject
*args
)
4040 if (!PyArg_ParseTuple(args
, "s|si:popen", &cmdstring
, &mode
, &bufsize
))
4045 else if (*mode
!= 'w') {
4046 PyErr_SetString(PyExc_ValueError
, "popen() arg 2 must be 'r' or 'w'");
4051 if (bufsize
!= -1) {
4052 PyErr_SetString(PyExc_ValueError
, "popen() arg 3 must be -1");
4056 if (*(mode
+1) == 't')
4057 f
= _PyPopen(cmdstring
, tm
| _O_TEXT
, POPEN_1
);
4058 else if (*(mode
+1) == 'b')
4059 f
= _PyPopen(cmdstring
, tm
| _O_BINARY
, POPEN_1
);
4061 f
= _PyPopen(cmdstring
, tm
| _O_TEXT
, POPEN_1
);
4066 /* Variation on win32pipe.popen
4068 * The result of this function is a pipe (file) connected to the
4069 * process's stdin, and a pipe connected to the process's stdout.
4073 win32_popen2(PyObject
*self
, PyObject
*args
)
4081 if (!PyArg_ParseTuple(args
, "s|si:popen2", &cmdstring
, &mode
, &bufsize
))
4086 else if (*mode
!= 'b') {
4087 PyErr_SetString(PyExc_ValueError
, "popen2() arg 2 must be 't' or 'b'");
4092 if (bufsize
!= -1) {
4093 PyErr_SetString(PyExc_ValueError
, "popen2() arg 3 must be -1");
4097 f
= _PyPopen(cmdstring
, tm
, POPEN_2
);
4103 * Variation on <om win32pipe.popen>
4105 * The result of this function is 3 pipes - the process's stdin,
4110 win32_popen3(PyObject
*self
, PyObject
*args
)
4118 if (!PyArg_ParseTuple(args
, "s|si:popen3", &cmdstring
, &mode
, &bufsize
))
4123 else if (*mode
!= 'b') {
4124 PyErr_SetString(PyExc_ValueError
, "popen3() arg 2 must be 't' or 'b'");
4129 if (bufsize
!= -1) {
4130 PyErr_SetString(PyExc_ValueError
, "popen3() arg 3 must be -1");
4134 f
= _PyPopen(cmdstring
, tm
, POPEN_3
);
4140 * Variation on win32pipe.popen
4142 * The result of this function is 2 pipes - the processes stdin,
4143 * and stdout+stderr combined as a single pipe.
4147 win32_popen4(PyObject
*self
, PyObject
*args
)
4155 if (!PyArg_ParseTuple(args
, "s|si:popen4", &cmdstring
, &mode
, &bufsize
))
4160 else if (*mode
!= 'b') {
4161 PyErr_SetString(PyExc_ValueError
, "popen4() arg 2 must be 't' or 'b'");
4166 if (bufsize
!= -1) {
4167 PyErr_SetString(PyExc_ValueError
, "popen4() arg 3 must be -1");
4171 f
= _PyPopen(cmdstring
, tm
, POPEN_4
);
4177 _PyPopenCreateProcess(char *cmdstring
,
4183 PROCESS_INFORMATION piProcInfo
;
4184 STARTUPINFO siStartInfo
;
4185 DWORD dwProcessFlags
= 0; /* no NEW_CONSOLE by default for Ctrl+C handling */
4186 char *s1
,*s2
, *s3
= " /c ";
4187 const char *szConsoleSpawn
= "w9xpopen.exe";
4191 if (i
= GetEnvironmentVariable("COMSPEC",NULL
,0)) {
4194 s1
= (char *)alloca(i
);
4195 if (!(x
= GetEnvironmentVariable("COMSPEC", s1
, i
)))
4198 /* Explicitly check if we are using COMMAND.COM. If we are
4199 * then use the w9xpopen hack.
4202 while (comshell
>= s1
&& *comshell
!= '\\')
4206 if (GetVersion() < 0x80000000 &&
4207 _stricmp(comshell
, "command.com") != 0) {
4208 /* NT/2000 and not using command.com. */
4209 x
= i
+ strlen(s3
) + strlen(cmdstring
) + 1;
4210 s2
= (char *)alloca(x
);
4212 PyOS_snprintf(s2
, x
, "%s%s%s", s1
, s3
, cmdstring
);
4216 * Oh gag, we're on Win9x or using COMMAND.COM. Use
4217 * the workaround listed in KB: Q150956
4219 char modulepath
[_MAX_PATH
];
4220 struct stat statinfo
;
4221 GetModuleFileName(NULL
, modulepath
, sizeof(modulepath
));
4222 for (i
= x
= 0; modulepath
[i
]; i
++)
4223 if (modulepath
[i
] == SEP
)
4225 modulepath
[x
] = '\0';
4226 /* Create the full-name to w9xpopen, so we can test it exists */
4229 (sizeof(modulepath
)/sizeof(modulepath
[0]))
4230 -strlen(modulepath
));
4231 if (stat(modulepath
, &statinfo
) != 0) {
4232 /* Eeek - file-not-found - possibly an embedding
4233 situation - see if we can locate it in sys.prefix
4237 sizeof(modulepath
)/sizeof(modulepath
[0]));
4238 if (modulepath
[strlen(modulepath
)-1] != '\\')
4239 strcat(modulepath
, "\\");
4242 (sizeof(modulepath
)/sizeof(modulepath
[0]))
4243 -strlen(modulepath
));
4244 /* No where else to look - raise an easily identifiable
4245 error, rather than leaving Windows to report
4246 "file not found" - as the user is probably blissfully
4247 unaware this shim EXE is used, and it will confuse them.
4248 (well, it confused me for a while ;-)
4250 if (stat(modulepath
, &statinfo
) != 0) {
4251 PyErr_Format(PyExc_RuntimeError
,
4252 "Can not locate '%s' which is needed "
4253 "for popen to work with your shell "
4259 x
= i
+ strlen(s3
) + strlen(cmdstring
) + 1 +
4260 strlen(modulepath
) +
4261 strlen(szConsoleSpawn
) + 1;
4263 s2
= (char *)alloca(x
);
4265 /* To maintain correct argument passing semantics,
4266 we pass the command-line as it stands, and allow
4267 quoting to be applied. w9xpopen.exe will then
4268 use its argv vector, and re-quote the necessary
4269 args for the ultimate child process.
4278 /* Not passing CREATE_NEW_CONSOLE has been known to
4279 cause random failures on win9x. Specifically a
4281 "Your program accessed mem currently in use at xxx"
4282 and a hopeful warning about the stability of your
4284 Cost is Ctrl+C wont kill children, but anyone
4285 who cares can have a go!
4287 dwProcessFlags
|= CREATE_NEW_CONSOLE
;
4291 /* Could be an else here to try cmd.exe / command.com in the path
4292 Now we'll just error out.. */
4294 PyErr_SetString(PyExc_RuntimeError
,
4295 "Cannot locate a COMSPEC environment variable to "
4296 "use as the shell");
4300 ZeroMemory(&siStartInfo
, sizeof(STARTUPINFO
));
4301 siStartInfo
.cb
= sizeof(STARTUPINFO
);
4302 siStartInfo
.dwFlags
= STARTF_USESTDHANDLES
| STARTF_USESHOWWINDOW
;
4303 siStartInfo
.hStdInput
= hStdin
;
4304 siStartInfo
.hStdOutput
= hStdout
;
4305 siStartInfo
.hStdError
= hStderr
;
4306 siStartInfo
.wShowWindow
= SW_HIDE
;
4308 if (CreateProcess(NULL
,
4318 /* Close the handles now so anyone waiting is woken. */
4319 CloseHandle(piProcInfo
.hThread
);
4321 /* Return process handle */
4322 *hProcess
= piProcInfo
.hProcess
;
4325 win32_error("CreateProcess", s2
);
4329 /* The following code is based off of KB: Q190351 */
4332 _PyPopen(char *cmdstring
, int mode
, int n
)
4334 HANDLE hChildStdinRd
, hChildStdinWr
, hChildStdoutRd
, hChildStdoutWr
,
4335 hChildStderrRd
, hChildStderrWr
, hChildStdinWrDup
, hChildStdoutRdDup
,
4336 hChildStderrRdDup
, hProcess
; /* hChildStdoutWrDup; */
4338 SECURITY_ATTRIBUTES saAttr
;
4345 saAttr
.nLength
= sizeof(SECURITY_ATTRIBUTES
);
4346 saAttr
.bInheritHandle
= TRUE
;
4347 saAttr
.lpSecurityDescriptor
= NULL
;
4349 if (!CreatePipe(&hChildStdinRd
, &hChildStdinWr
, &saAttr
, 0))
4350 return win32_error("CreatePipe", NULL
);
4352 /* Create new output read handle and the input write handle. Set
4353 * the inheritance properties to FALSE. Otherwise, the child inherits
4354 * these handles; resulting in non-closeable handles to the pipes
4356 fSuccess
= DuplicateHandle(GetCurrentProcess(), hChildStdinWr
,
4357 GetCurrentProcess(), &hChildStdinWrDup
, 0,
4359 DUPLICATE_SAME_ACCESS
);
4361 return win32_error("DuplicateHandle", NULL
);
4363 /* Close the inheritable version of ChildStdin
4364 that we're using. */
4365 CloseHandle(hChildStdinWr
);
4367 if (!CreatePipe(&hChildStdoutRd
, &hChildStdoutWr
, &saAttr
, 0))
4368 return win32_error("CreatePipe", NULL
);
4370 fSuccess
= DuplicateHandle(GetCurrentProcess(), hChildStdoutRd
,
4371 GetCurrentProcess(), &hChildStdoutRdDup
, 0,
4372 FALSE
, DUPLICATE_SAME_ACCESS
);
4374 return win32_error("DuplicateHandle", NULL
);
4376 /* Close the inheritable version of ChildStdout
4377 that we're using. */
4378 CloseHandle(hChildStdoutRd
);
4381 if (!CreatePipe(&hChildStderrRd
, &hChildStderrWr
, &saAttr
, 0))
4382 return win32_error("CreatePipe", NULL
);
4383 fSuccess
= DuplicateHandle(GetCurrentProcess(),
4385 GetCurrentProcess(),
4386 &hChildStderrRdDup
, 0,
4387 FALSE
, DUPLICATE_SAME_ACCESS
);
4389 return win32_error("DuplicateHandle", NULL
);
4390 /* Close the inheritable version of ChildStdErr that we're using. */
4391 CloseHandle(hChildStderrRd
);
4396 switch (mode
& (_O_RDONLY
| _O_TEXT
| _O_BINARY
| _O_WRONLY
)) {
4397 case _O_WRONLY
| _O_TEXT
:
4398 /* Case for writing to child Stdin in text mode. */
4399 fd1
= _open_osfhandle((long)hChildStdinWrDup
, mode
);
4400 f1
= _fdopen(fd1
, "w");
4401 f
= PyFile_FromFile(f1
, cmdstring
, "w", _PyPclose
);
4402 PyFile_SetBufSize(f
, 0);
4403 /* We don't care about these pipes anymore, so close them. */
4404 CloseHandle(hChildStdoutRdDup
);
4405 CloseHandle(hChildStderrRdDup
);
4408 case _O_RDONLY
| _O_TEXT
:
4409 /* Case for reading from child Stdout in text mode. */
4410 fd1
= _open_osfhandle((long)hChildStdoutRdDup
, mode
);
4411 f1
= _fdopen(fd1
, "r");
4412 f
= PyFile_FromFile(f1
, cmdstring
, "r", _PyPclose
);
4413 PyFile_SetBufSize(f
, 0);
4414 /* We don't care about these pipes anymore, so close them. */
4415 CloseHandle(hChildStdinWrDup
);
4416 CloseHandle(hChildStderrRdDup
);
4419 case _O_RDONLY
| _O_BINARY
:
4420 /* Case for readinig from child Stdout in binary mode. */
4421 fd1
= _open_osfhandle((long)hChildStdoutRdDup
, mode
);
4422 f1
= _fdopen(fd1
, "rb");
4423 f
= PyFile_FromFile(f1
, cmdstring
, "rb", _PyPclose
);
4424 PyFile_SetBufSize(f
, 0);
4425 /* We don't care about these pipes anymore, so close them. */
4426 CloseHandle(hChildStdinWrDup
);
4427 CloseHandle(hChildStderrRdDup
);
4430 case _O_WRONLY
| _O_BINARY
:
4431 /* Case for writing to child Stdin in binary mode. */
4432 fd1
= _open_osfhandle((long)hChildStdinWrDup
, mode
);
4433 f1
= _fdopen(fd1
, "wb");
4434 f
= PyFile_FromFile(f1
, cmdstring
, "wb", _PyPclose
);
4435 PyFile_SetBufSize(f
, 0);
4436 /* We don't care about these pipes anymore, so close them. */
4437 CloseHandle(hChildStdoutRdDup
);
4438 CloseHandle(hChildStderrRdDup
);
4450 if (mode
& _O_TEXT
) {
4458 fd1
= _open_osfhandle((long)hChildStdinWrDup
, mode
);
4459 f1
= _fdopen(fd1
, m2
);
4460 fd2
= _open_osfhandle((long)hChildStdoutRdDup
, mode
);
4461 f2
= _fdopen(fd2
, m1
);
4462 p1
= PyFile_FromFile(f1
, cmdstring
, m2
, _PyPclose
);
4463 PyFile_SetBufSize(p1
, 0);
4464 p2
= PyFile_FromFile(f2
, cmdstring
, m1
, _PyPclose
);
4465 PyFile_SetBufSize(p2
, 0);
4468 CloseHandle(hChildStderrRdDup
);
4470 f
= PyTuple_Pack(2,p1
,p2
);
4480 PyObject
*p1
, *p2
, *p3
;
4482 if (mode
& _O_TEXT
) {
4490 fd1
= _open_osfhandle((long)hChildStdinWrDup
, mode
);
4491 f1
= _fdopen(fd1
, m2
);
4492 fd2
= _open_osfhandle((long)hChildStdoutRdDup
, mode
);
4493 f2
= _fdopen(fd2
, m1
);
4494 fd3
= _open_osfhandle((long)hChildStderrRdDup
, mode
);
4495 f3
= _fdopen(fd3
, m1
);
4496 p1
= PyFile_FromFile(f1
, cmdstring
, m2
, _PyPclose
);
4497 p2
= PyFile_FromFile(f2
, cmdstring
, m1
, _PyPclose
);
4498 p3
= PyFile_FromFile(f3
, cmdstring
, m1
, _PyPclose
);
4499 PyFile_SetBufSize(p1
, 0);
4500 PyFile_SetBufSize(p2
, 0);
4501 PyFile_SetBufSize(p3
, 0);
4502 f
= PyTuple_Pack(3,p1
,p2
,p3
);
4512 if (!_PyPopenCreateProcess(cmdstring
,
4520 if (!_PyPopenCreateProcess(cmdstring
,
4529 * Insert the files we've created into the process dictionary
4530 * all referencing the list with the process handle and the
4531 * initial number of files (see description below in _PyPclose).
4532 * Since if _PyPclose later tried to wait on a process when all
4533 * handles weren't closed, it could create a deadlock with the
4534 * child, we spend some energy here to try to ensure that we
4535 * either insert all file handles into the dictionary or none
4536 * at all. It's a little clumsy with the various popen modes
4537 * and variable number of files involved.
4539 if (!_PyPopenProcs
) {
4540 _PyPopenProcs
= PyDict_New();
4543 if (_PyPopenProcs
) {
4544 PyObject
*procObj
, *hProcessObj
, *intObj
, *fileObj
[3];
4547 fileObj
[0] = fileObj
[1] = fileObj
[2] = NULL
;
4548 ins_rc
[0] = ins_rc
[1] = ins_rc
[2] = 0;
4550 procObj
= PyList_New(2);
4551 hProcessObj
= PyLong_FromVoidPtr(hProcess
);
4552 intObj
= PyInt_FromLong(file_count
);
4554 if (procObj
&& hProcessObj
&& intObj
) {
4555 PyList_SetItem(procObj
,0,hProcessObj
);
4556 PyList_SetItem(procObj
,1,intObj
);
4558 fileObj
[0] = PyLong_FromVoidPtr(f1
);
4560 ins_rc
[0] = PyDict_SetItem(_PyPopenProcs
,
4564 if (file_count
>= 2) {
4565 fileObj
[1] = PyLong_FromVoidPtr(f2
);
4567 ins_rc
[1] = PyDict_SetItem(_PyPopenProcs
,
4572 if (file_count
>= 3) {
4573 fileObj
[2] = PyLong_FromVoidPtr(f3
);
4575 ins_rc
[2] = PyDict_SetItem(_PyPopenProcs
,
4581 if (ins_rc
[0] < 0 || !fileObj
[0] ||
4582 ins_rc
[1] < 0 || (file_count
> 1 && !fileObj
[1]) ||
4583 ins_rc
[2] < 0 || (file_count
> 2 && !fileObj
[2])) {
4584 /* Something failed - remove any dictionary
4585 * entries that did make it.
4587 if (!ins_rc
[0] && fileObj
[0]) {
4588 PyDict_DelItem(_PyPopenProcs
,
4591 if (!ins_rc
[1] && fileObj
[1]) {
4592 PyDict_DelItem(_PyPopenProcs
,
4595 if (!ins_rc
[2] && fileObj
[2]) {
4596 PyDict_DelItem(_PyPopenProcs
,
4603 * Clean up our localized references for the dictionary keys
4604 * and value since PyDict_SetItem will Py_INCREF any copies
4605 * that got placed in the dictionary.
4607 Py_XDECREF(procObj
);
4608 Py_XDECREF(fileObj
[0]);
4609 Py_XDECREF(fileObj
[1]);
4610 Py_XDECREF(fileObj
[2]);
4613 /* Child is launched. Close the parents copy of those pipe
4614 * handles that only the child should have open. You need to
4615 * make sure that no handles to the write end of the output pipe
4616 * are maintained in this process or else the pipe will not close
4617 * when the child process exits and the ReadFile will hang. */
4619 if (!CloseHandle(hChildStdinRd
))
4620 return win32_error("CloseHandle", NULL
);
4622 if (!CloseHandle(hChildStdoutWr
))
4623 return win32_error("CloseHandle", NULL
);
4625 if ((n
!= 4) && (!CloseHandle(hChildStderrWr
)))
4626 return win32_error("CloseHandle", NULL
);
4632 * Wrapper for fclose() to use for popen* files, so we can retrieve the
4633 * exit code for the child process and return as a result of the close.
4635 * This function uses the _PyPopenProcs dictionary in order to map the
4636 * input file pointer to information about the process that was
4637 * originally created by the popen* call that created the file pointer.
4638 * The dictionary uses the file pointer as a key (with one entry
4639 * inserted for each file returned by the original popen* call) and a
4640 * single list object as the value for all files from a single call.
4641 * The list object contains the Win32 process handle at [0], and a file
4642 * count at [1], which is initialized to the total number of file
4643 * handles using that list.
4645 * This function closes whichever handle it is passed, and decrements
4646 * the file count in the dictionary for the process handle pointed to
4647 * by this file. On the last close (when the file count reaches zero),
4648 * this function will wait for the child process and then return its
4649 * exit code as the result of the close() operation. This permits the
4650 * files to be closed in any order - it is always the close() of the
4651 * final handle that will return the exit code.
4653 * NOTE: This function is currently called with the GIL released.
4654 * hence we use the GILState API to manage our state.
4657 static int _PyPclose(FILE *file
)
4662 PyObject
*procObj
, *hProcessObj
, *intObj
, *fileObj
;
4665 PyGILState_STATE state
;
4668 /* Close the file handle first, to ensure it can't block the
4669 * child from exiting if it's the last handle.
4671 result
= fclose(file
);
4673 state
= PyGILState_Ensure();
4675 if (_PyPopenProcs
) {
4676 if ((fileObj
= PyLong_FromVoidPtr(file
)) != NULL
&&
4677 (procObj
= PyDict_GetItem(_PyPopenProcs
,
4678 fileObj
)) != NULL
&&
4679 (hProcessObj
= PyList_GetItem(procObj
,0)) != NULL
&&
4680 (intObj
= PyList_GetItem(procObj
,1)) != NULL
) {
4682 hProcess
= PyLong_AsVoidPtr(hProcessObj
);
4683 file_count
= PyInt_AsLong(intObj
);
4685 if (file_count
> 1) {
4686 /* Still other files referencing process */
4688 PyList_SetItem(procObj
,1,
4689 PyInt_FromLong(file_count
));
4691 /* Last file for this process */
4692 if (result
!= EOF
&&
4693 WaitForSingleObject(hProcess
, INFINITE
) != WAIT_FAILED
&&
4694 GetExitCodeProcess(hProcess
, &exit_code
)) {
4695 /* Possible truncation here in 16-bit environments, but
4696 * real exit codes are just the lower byte in any event.
4700 /* Indicate failure - this will cause the file object
4701 * to raise an I/O error and translate the last Win32
4702 * error code from errno. We do have a problem with
4703 * last errors that overlap the normal errno table,
4704 * but that's a consistent problem with the file object.
4706 if (result
!= EOF
) {
4707 /* If the error wasn't from the fclose(), then
4708 * set errno for the file object error handling.
4710 errno
= GetLastError();
4715 /* Free up the native handle at this point */
4716 CloseHandle(hProcess
);
4719 /* Remove this file pointer from dictionary */
4720 PyDict_DelItem(_PyPopenProcs
, fileObj
);
4722 if (PyDict_Size(_PyPopenProcs
) == 0) {
4723 Py_DECREF(_PyPopenProcs
);
4724 _PyPopenProcs
= NULL
;
4727 } /* if object retrieval ok */
4729 Py_XDECREF(fileObj
);
4730 } /* if _PyPopenProcs */
4733 PyGILState_Release(state
);
4738 #else /* which OS? */
4740 posix_popen(PyObject
*self
, PyObject
*args
)
4747 if (!PyArg_ParseTuple(args
, "s|si:popen", &name
, &mode
, &bufsize
))
4749 /* Strip mode of binary or text modifiers */
4750 if (strcmp(mode
, "rb") == 0 || strcmp(mode
, "rt") == 0)
4752 else if (strcmp(mode
, "wb") == 0 || strcmp(mode
, "wt") == 0)
4754 Py_BEGIN_ALLOW_THREADS
4755 fp
= popen(name
, mode
);
4756 Py_END_ALLOW_THREADS
4758 return posix_error();
4759 f
= PyFile_FromFile(fp
, name
, mode
, pclose
);
4761 PyFile_SetBufSize(f
, bufsize
);
4765 #endif /* PYOS_??? */
4766 #endif /* HAVE_POPEN */
4770 PyDoc_STRVAR(posix_setuid__doc__
,
4772 Set the current process's user id.");
4775 posix_setuid(PyObject
*self
, PyObject
*args
)
4778 if (!PyArg_ParseTuple(args
, "i:setuid", &uid
))
4780 if (setuid(uid
) < 0)
4781 return posix_error();
4785 #endif /* HAVE_SETUID */
4789 PyDoc_STRVAR(posix_seteuid__doc__
,
4791 Set the current process's effective user id.");
4794 posix_seteuid (PyObject
*self
, PyObject
*args
)
4797 if (!PyArg_ParseTuple(args
, "i", &euid
)) {
4799 } else if (seteuid(euid
) < 0) {
4800 return posix_error();
4806 #endif /* HAVE_SETEUID */
4809 PyDoc_STRVAR(posix_setegid__doc__
,
4811 Set the current process's effective group id.");
4814 posix_setegid (PyObject
*self
, PyObject
*args
)
4817 if (!PyArg_ParseTuple(args
, "i", &egid
)) {
4819 } else if (setegid(egid
) < 0) {
4820 return posix_error();
4826 #endif /* HAVE_SETEGID */
4828 #ifdef HAVE_SETREUID
4829 PyDoc_STRVAR(posix_setreuid__doc__
,
4830 "setreuid(ruid, euid)\n\n\
4831 Set the current process's real and effective user ids.");
4834 posix_setreuid (PyObject
*self
, PyObject
*args
)
4837 if (!PyArg_ParseTuple(args
, "ii", &ruid
, &euid
)) {
4839 } else if (setreuid(ruid
, euid
) < 0) {
4840 return posix_error();
4846 #endif /* HAVE_SETREUID */
4848 #ifdef HAVE_SETREGID
4849 PyDoc_STRVAR(posix_setregid__doc__
,
4850 "setregid(rgid, egid)\n\n\
4851 Set the current process's real and effective group ids.");
4854 posix_setregid (PyObject
*self
, PyObject
*args
)
4857 if (!PyArg_ParseTuple(args
, "ii", &rgid
, &egid
)) {
4859 } else if (setregid(rgid
, egid
) < 0) {
4860 return posix_error();
4866 #endif /* HAVE_SETREGID */
4869 PyDoc_STRVAR(posix_setgid__doc__
,
4871 Set the current process's group id.");
4874 posix_setgid(PyObject
*self
, PyObject
*args
)
4877 if (!PyArg_ParseTuple(args
, "i:setgid", &gid
))
4879 if (setgid(gid
) < 0)
4880 return posix_error();
4884 #endif /* HAVE_SETGID */
4886 #ifdef HAVE_SETGROUPS
4887 PyDoc_STRVAR(posix_setgroups__doc__
,
4888 "setgroups(list)\n\n\
4889 Set the groups of the current process to list.");
4892 posix_setgroups(PyObject
*self
, PyObject
*args
)
4896 gid_t grouplist
[MAX_GROUPS
];
4898 if (!PyArg_ParseTuple(args
, "O:setgid", &groups
))
4900 if (!PySequence_Check(groups
)) {
4901 PyErr_SetString(PyExc_TypeError
, "setgroups argument must be a sequence");
4904 len
= PySequence_Size(groups
);
4905 if (len
> MAX_GROUPS
) {
4906 PyErr_SetString(PyExc_ValueError
, "too many groups");
4909 for(i
= 0; i
< len
; i
++) {
4911 elem
= PySequence_GetItem(groups
, i
);
4914 if (!PyInt_Check(elem
)) {
4915 if (!PyLong_Check(elem
)) {
4916 PyErr_SetString(PyExc_TypeError
,
4917 "groups must be integers");
4921 unsigned long x
= PyLong_AsUnsignedLong(elem
);
4922 if (PyErr_Occurred()) {
4923 PyErr_SetString(PyExc_TypeError
,
4924 "group id too big");
4929 /* read back the value to see if it fitted in gid_t */
4930 if (grouplist
[i
] != x
) {
4931 PyErr_SetString(PyExc_TypeError
,
4932 "group id too big");
4938 long x
= PyInt_AsLong(elem
);
4940 if (grouplist
[i
] != x
) {
4941 PyErr_SetString(PyExc_TypeError
,
4942 "group id too big");
4950 if (setgroups(len
, grouplist
) < 0)
4951 return posix_error();
4955 #endif /* HAVE_SETGROUPS */
4958 PyDoc_STRVAR(posix_waitpid__doc__
,
4959 "waitpid(pid, options) -> (pid, status)\n\n\
4960 Wait for completion of a given child process.");
4963 posix_waitpid(PyObject
*self
, PyObject
*args
)
4968 #define status_i (status.w_status)
4971 #define status_i status
4975 if (!PyArg_ParseTuple(args
, "ii:waitpid", &pid
, &options
))
4977 Py_BEGIN_ALLOW_THREADS
4978 pid
= waitpid(pid
, &status
, options
);
4979 Py_END_ALLOW_THREADS
4981 return posix_error();
4983 return Py_BuildValue("ii", pid
, status_i
);
4986 #elif defined(HAVE_CWAIT)
4988 /* MS C has a variant of waitpid() that's usable for most purposes. */
4989 PyDoc_STRVAR(posix_waitpid__doc__
,
4990 "waitpid(pid, options) -> (pid, status << 8)\n\n"
4991 "Wait for completion of a given process. options is ignored on Windows.");
4994 posix_waitpid(PyObject
*self
, PyObject
*args
)
4999 if (!PyArg_ParseTuple(args
, "ii:waitpid", &pid
, &options
))
5001 Py_BEGIN_ALLOW_THREADS
5002 pid
= _cwait(&status
, pid
, options
);
5003 Py_END_ALLOW_THREADS
5005 return posix_error();
5007 /* shift the status left a byte so this is more like the
5009 return Py_BuildValue("ii", pid
, status
<< 8);
5011 #endif /* HAVE_WAITPID || HAVE_CWAIT */
5014 PyDoc_STRVAR(posix_wait__doc__
,
5015 "wait() -> (pid, status)\n\n\
5016 Wait for completion of a child process.");
5019 posix_wait(PyObject
*self
, PyObject
*noargs
)
5024 #define status_i (status.w_status)
5027 #define status_i status
5031 Py_BEGIN_ALLOW_THREADS
5032 pid
= wait(&status
);
5033 Py_END_ALLOW_THREADS
5035 return posix_error();
5037 return Py_BuildValue("ii", pid
, status_i
);
5043 PyDoc_STRVAR(posix_lstat__doc__
,
5044 "lstat(path) -> stat result\n\n\
5045 Like stat(path), but do not follow symbolic links.");
5048 posix_lstat(PyObject
*self
, PyObject
*args
)
5051 return posix_do_stat(self
, args
, "et:lstat", lstat
, NULL
, NULL
);
5052 #else /* !HAVE_LSTAT */
5054 return posix_do_stat(self
, args
, "et:lstat", STAT
, "U:lstat", _wstati64
);
5056 return posix_do_stat(self
, args
, "et:lstat", STAT
, NULL
, NULL
);
5058 #endif /* !HAVE_LSTAT */
5062 #ifdef HAVE_READLINK
5063 PyDoc_STRVAR(posix_readlink__doc__
,
5064 "readlink(path) -> path\n\n\
5065 Return a string representing the path to which the symbolic link points.");
5068 posix_readlink(PyObject
*self
, PyObject
*args
)
5070 char buf
[MAXPATHLEN
];
5073 if (!PyArg_ParseTuple(args
, "s:readlink", &path
))
5075 Py_BEGIN_ALLOW_THREADS
5076 n
= readlink(path
, buf
, (int) sizeof buf
);
5077 Py_END_ALLOW_THREADS
5079 return posix_error_with_filename(path
);
5080 return PyString_FromStringAndSize(buf
, n
);
5082 #endif /* HAVE_READLINK */
5086 PyDoc_STRVAR(posix_symlink__doc__
,
5087 "symlink(src, dst)\n\n\
5088 Create a symbolic link pointing to src named dst.");
5091 posix_symlink(PyObject
*self
, PyObject
*args
)
5093 return posix_2str(args
, "etet:symlink", symlink
, NULL
, NULL
);
5095 #endif /* HAVE_SYMLINK */
5100 #define HZ 60 /* Universal constant :-) */
5103 #if defined(PYCC_VACPP) && defined(PYOS_OS2)
5109 Py_BEGIN_ALLOW_THREADS
5110 DosQuerySysInfo(QSV_MS_COUNT
, QSV_MS_COUNT
, &value
, sizeof(value
));
5111 Py_END_ALLOW_THREADS
5117 posix_times(PyObject
*self
, PyObject
*noargs
)
5119 /* Currently Only Uptime is Provided -- Others Later */
5120 return Py_BuildValue("ddddd",
5121 (double)0 /* t.tms_utime / HZ */,
5122 (double)0 /* t.tms_stime / HZ */,
5123 (double)0 /* t.tms_cutime / HZ */,
5124 (double)0 /* t.tms_cstime / HZ */,
5125 (double)system_uptime() / 1000);
5129 posix_times(PyObject
*self
, PyObject
*noargs
)
5135 if (c
== (clock_t) -1)
5136 return posix_error();
5137 return Py_BuildValue("ddddd",
5138 (double)t
.tms_utime
/ HZ
,
5139 (double)t
.tms_stime
/ HZ
,
5140 (double)t
.tms_cutime
/ HZ
,
5141 (double)t
.tms_cstime
/ HZ
,
5144 #endif /* not OS2 */
5145 #endif /* HAVE_TIMES */
5149 #define HAVE_TIMES /* so the method table will pick it up */
5151 posix_times(PyObject
*self
, PyObject
*noargs
)
5153 FILETIME create
, exit
, kernel
, user
;
5155 hProc
= GetCurrentProcess();
5156 GetProcessTimes(hProc
, &create
, &exit
, &kernel
, &user
);
5157 /* The fields of a FILETIME structure are the hi and lo part
5158 of a 64-bit value expressed in 100 nanosecond units.
5159 1e7 is one second in such units; 1e-7 the inverse.
5160 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
5162 return Py_BuildValue(
5164 (double)(kernel
.dwHighDateTime
*429.4967296 +
5165 kernel
.dwLowDateTime
*1e-7),
5166 (double)(user
.dwHighDateTime
*429.4967296 +
5167 user
.dwLowDateTime
*1e-7),
5172 #endif /* MS_WINDOWS */
5175 PyDoc_STRVAR(posix_times__doc__
,
5176 "times() -> (utime, stime, cutime, cstime, elapsed_time)\n\n\
5177 Return a tuple of floating point numbers indicating process times.");
5182 PyDoc_STRVAR(posix_getsid__doc__
,
5183 "getsid(pid) -> sid\n\n\
5184 Call the system call getsid().");
5187 posix_getsid(PyObject
*self
, PyObject
*args
)
5190 if (!PyArg_ParseTuple(args
, "i:getsid", &pid
))
5194 return posix_error();
5195 return PyInt_FromLong((long)sid
);
5197 #endif /* HAVE_GETSID */
5201 PyDoc_STRVAR(posix_setsid__doc__
,
5203 Call the system call setsid().");
5206 posix_setsid(PyObject
*self
, PyObject
*noargs
)
5209 return posix_error();
5213 #endif /* HAVE_SETSID */
5216 PyDoc_STRVAR(posix_setpgid__doc__
,
5217 "setpgid(pid, pgrp)\n\n\
5218 Call the system call setpgid().");
5221 posix_setpgid(PyObject
*self
, PyObject
*args
)
5224 if (!PyArg_ParseTuple(args
, "ii:setpgid", &pid
, &pgrp
))
5226 if (setpgid(pid
, pgrp
) < 0)
5227 return posix_error();
5231 #endif /* HAVE_SETPGID */
5234 #ifdef HAVE_TCGETPGRP
5235 PyDoc_STRVAR(posix_tcgetpgrp__doc__
,
5236 "tcgetpgrp(fd) -> pgid\n\n\
5237 Return the process group associated with the terminal given by a fd.");
5240 posix_tcgetpgrp(PyObject
*self
, PyObject
*args
)
5243 if (!PyArg_ParseTuple(args
, "i:tcgetpgrp", &fd
))
5245 pgid
= tcgetpgrp(fd
);
5247 return posix_error();
5248 return PyInt_FromLong((long)pgid
);
5250 #endif /* HAVE_TCGETPGRP */
5253 #ifdef HAVE_TCSETPGRP
5254 PyDoc_STRVAR(posix_tcsetpgrp__doc__
,
5255 "tcsetpgrp(fd, pgid)\n\n\
5256 Set the process group associated with the terminal given by a fd.");
5259 posix_tcsetpgrp(PyObject
*self
, PyObject
*args
)
5262 if (!PyArg_ParseTuple(args
, "ii:tcsetpgrp", &fd
, &pgid
))
5264 if (tcsetpgrp(fd
, pgid
) < 0)
5265 return posix_error();
5269 #endif /* HAVE_TCSETPGRP */
5271 /* Functions acting on file descriptors */
5273 PyDoc_STRVAR(posix_open__doc__
,
5274 "open(filename, flag [, mode=0777]) -> fd\n\n\
5275 Open a file (for low level IO).");
5278 posix_open(PyObject
*self
, PyObject
*args
)
5286 if (unicode_file_names()) {
5287 PyUnicodeObject
*po
;
5288 if (PyArg_ParseTuple(args
, "Ui|i:mkdir", &po
, &flag
, &mode
)) {
5289 Py_BEGIN_ALLOW_THREADS
5290 /* PyUnicode_AS_UNICODE OK without thread
5291 lock as it is a simple dereference. */
5292 fd
= _wopen(PyUnicode_AS_UNICODE(po
), flag
, mode
);
5293 Py_END_ALLOW_THREADS
5295 return posix_error();
5296 return PyInt_FromLong((long)fd
);
5298 /* Drop the argument parsing error as narrow strings
5304 if (!PyArg_ParseTuple(args
, "eti|i",
5305 Py_FileSystemDefaultEncoding
, &file
,
5309 Py_BEGIN_ALLOW_THREADS
5310 fd
= open(file
, flag
, mode
);
5311 Py_END_ALLOW_THREADS
5313 return posix_error_with_allocated_filename(file
);
5315 return PyInt_FromLong((long)fd
);
5319 PyDoc_STRVAR(posix_close__doc__
,
5321 Close a file descriptor (for low level IO).");
5324 posix_close(PyObject
*self
, PyObject
*args
)
5327 if (!PyArg_ParseTuple(args
, "i:close", &fd
))
5329 Py_BEGIN_ALLOW_THREADS
5331 Py_END_ALLOW_THREADS
5333 return posix_error();
5339 PyDoc_STRVAR(posix_dup__doc__
,
5340 "dup(fd) -> fd2\n\n\
5341 Return a duplicate of a file descriptor.");
5344 posix_dup(PyObject
*self
, PyObject
*args
)
5347 if (!PyArg_ParseTuple(args
, "i:dup", &fd
))
5349 Py_BEGIN_ALLOW_THREADS
5351 Py_END_ALLOW_THREADS
5353 return posix_error();
5354 return PyInt_FromLong((long)fd
);
5358 PyDoc_STRVAR(posix_dup2__doc__
,
5359 "dup2(old_fd, new_fd)\n\n\
5360 Duplicate file descriptor.");
5363 posix_dup2(PyObject
*self
, PyObject
*args
)
5366 if (!PyArg_ParseTuple(args
, "ii:dup2", &fd
, &fd2
))
5368 Py_BEGIN_ALLOW_THREADS
5369 res
= dup2(fd
, fd2
);
5370 Py_END_ALLOW_THREADS
5372 return posix_error();
5378 PyDoc_STRVAR(posix_lseek__doc__
,
5379 "lseek(fd, pos, how) -> newpos\n\n\
5380 Set the current position of a file descriptor.");
5383 posix_lseek(PyObject
*self
, PyObject
*args
)
5386 #if defined(MS_WIN64) || defined(MS_WINDOWS)
5387 PY_LONG_LONG pos
, res
;
5392 if (!PyArg_ParseTuple(args
, "iOi:lseek", &fd
, &posobj
, &how
))
5395 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
5397 case 0: how
= SEEK_SET
; break;
5398 case 1: how
= SEEK_CUR
; break;
5399 case 2: how
= SEEK_END
; break;
5401 #endif /* SEEK_END */
5403 #if !defined(HAVE_LARGEFILE_SUPPORT)
5404 pos
= PyInt_AsLong(posobj
);
5406 pos
= PyLong_Check(posobj
) ?
5407 PyLong_AsLongLong(posobj
) : PyInt_AsLong(posobj
);
5409 if (PyErr_Occurred())
5412 Py_BEGIN_ALLOW_THREADS
5413 #if defined(MS_WIN64) || defined(MS_WINDOWS)
5414 res
= _lseeki64(fd
, pos
, how
);
5416 res
= lseek(fd
, pos
, how
);
5418 Py_END_ALLOW_THREADS
5420 return posix_error();
5422 #if !defined(HAVE_LARGEFILE_SUPPORT)
5423 return PyInt_FromLong(res
);
5425 return PyLong_FromLongLong(res
);
5430 PyDoc_STRVAR(posix_read__doc__
,
5431 "read(fd, buffersize) -> string\n\n\
5432 Read a file descriptor.");
5435 posix_read(PyObject
*self
, PyObject
*args
)
5439 if (!PyArg_ParseTuple(args
, "ii:read", &fd
, &size
))
5443 return posix_error();
5445 buffer
= PyString_FromStringAndSize((char *)NULL
, size
);
5448 Py_BEGIN_ALLOW_THREADS
5449 n
= read(fd
, PyString_AsString(buffer
), size
);
5450 Py_END_ALLOW_THREADS
5453 return posix_error();
5456 _PyString_Resize(&buffer
, n
);
5461 PyDoc_STRVAR(posix_write__doc__
,
5462 "write(fd, string) -> byteswritten\n\n\
5463 Write a string to a file descriptor.");
5466 posix_write(PyObject
*self
, PyObject
*args
)
5470 if (!PyArg_ParseTuple(args
, "is#:write", &fd
, &buffer
, &size
))
5472 Py_BEGIN_ALLOW_THREADS
5473 size
= write(fd
, buffer
, size
);
5474 Py_END_ALLOW_THREADS
5476 return posix_error();
5477 return PyInt_FromLong((long)size
);
5481 PyDoc_STRVAR(posix_fstat__doc__
,
5482 "fstat(fd) -> stat result\n\n\
5483 Like stat(), but for an open file descriptor.");
5486 posix_fstat(PyObject
*self
, PyObject
*args
)
5491 if (!PyArg_ParseTuple(args
, "i:fstat", &fd
))
5494 /* on OpenVMS we must ensure that all bytes are written to the file */
5497 Py_BEGIN_ALLOW_THREADS
5498 res
= FSTAT(fd
, &st
);
5499 Py_END_ALLOW_THREADS
5501 return posix_error();
5503 return _pystat_fromstructstat(st
);
5507 PyDoc_STRVAR(posix_fdopen__doc__
,
5508 "fdopen(fd [, mode='r' [, bufsize]]) -> file_object\n\n\
5509 Return an open file object connected to a file descriptor.");
5512 posix_fdopen(PyObject
*self
, PyObject
*args
)
5519 if (!PyArg_ParseTuple(args
, "i|si", &fd
, &mode
, &bufsize
))
5522 if (mode
[0] != 'r' && mode
[0] != 'w' && mode
[0] != 'a') {
5523 PyErr_Format(PyExc_ValueError
,
5524 "invalid file mode '%s'", mode
);
5528 Py_BEGIN_ALLOW_THREADS
5529 fp
= fdopen(fd
, mode
);
5530 Py_END_ALLOW_THREADS
5532 return posix_error();
5533 f
= PyFile_FromFile(fp
, "<fdopen>", mode
, fclose
);
5535 PyFile_SetBufSize(f
, bufsize
);
5539 PyDoc_STRVAR(posix_isatty__doc__
,
5540 "isatty(fd) -> bool\n\n\
5541 Return True if the file descriptor 'fd' is an open file descriptor\n\
5542 connected to the slave end of a terminal.");
5545 posix_isatty(PyObject
*self
, PyObject
*args
)
5548 if (!PyArg_ParseTuple(args
, "i:isatty", &fd
))
5550 return PyBool_FromLong(isatty(fd
));
5554 PyDoc_STRVAR(posix_pipe__doc__
,
5555 "pipe() -> (read_end, write_end)\n\n\
5559 posix_pipe(PyObject
*self
, PyObject
*noargs
)
5561 #if defined(PYOS_OS2)
5565 Py_BEGIN_ALLOW_THREADS
5566 rc
= DosCreatePipe( &read
, &write
, 4096);
5567 Py_END_ALLOW_THREADS
5569 return os2_error(rc
);
5571 return Py_BuildValue("(ii)", read
, write
);
5573 #if !defined(MS_WINDOWS)
5576 Py_BEGIN_ALLOW_THREADS
5578 Py_END_ALLOW_THREADS
5580 return posix_error();
5581 return Py_BuildValue("(ii)", fds
[0], fds
[1]);
5582 #else /* MS_WINDOWS */
5584 int read_fd
, write_fd
;
5586 Py_BEGIN_ALLOW_THREADS
5587 ok
= CreatePipe(&read
, &write
, NULL
, 0);
5588 Py_END_ALLOW_THREADS
5590 return win32_error("CreatePipe", NULL
);
5591 read_fd
= _open_osfhandle((Py_intptr_t
)read
, 0);
5592 write_fd
= _open_osfhandle((Py_intptr_t
)write
, 1);
5593 return Py_BuildValue("(ii)", read_fd
, write_fd
);
5594 #endif /* MS_WINDOWS */
5597 #endif /* HAVE_PIPE */
5601 PyDoc_STRVAR(posix_mkfifo__doc__
,
5602 "mkfifo(filename [, mode=0666])\n\n\
5603 Create a FIFO (a POSIX named pipe).");
5606 posix_mkfifo(PyObject
*self
, PyObject
*args
)
5611 if (!PyArg_ParseTuple(args
, "s|i:mkfifo", &filename
, &mode
))
5613 Py_BEGIN_ALLOW_THREADS
5614 res
= mkfifo(filename
, mode
);
5615 Py_END_ALLOW_THREADS
5617 return posix_error();
5624 #if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
5625 PyDoc_STRVAR(posix_mknod__doc__
,
5626 "mknod(filename [, mode=0600, device])\n\n\
5627 Create a filesystem node (file, device special file or named pipe)\n\
5628 named filename. mode specifies both the permissions to use and the\n\
5629 type of node to be created, being combined (bitwise OR) with one of\n\
5630 S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. For S_IFCHR and S_IFBLK,\n\
5631 device defines the newly created device special file (probably using\n\
5632 os.makedev()), otherwise it is ignored.");
5636 posix_mknod(PyObject
*self
, PyObject
*args
)
5642 if (!PyArg_ParseTuple(args
, "s|ii:mknod", &filename
, &mode
, &device
))
5644 Py_BEGIN_ALLOW_THREADS
5645 res
= mknod(filename
, mode
, device
);
5646 Py_END_ALLOW_THREADS
5648 return posix_error();
5654 #ifdef HAVE_DEVICE_MACROS
5655 PyDoc_STRVAR(posix_major__doc__
,
5656 "major(device) -> major number\n\
5657 Extracts a device major number from a raw device number.");
5660 posix_major(PyObject
*self
, PyObject
*args
)
5663 if (!PyArg_ParseTuple(args
, "i:major", &device
))
5665 return PyInt_FromLong((long)major(device
));
5668 PyDoc_STRVAR(posix_minor__doc__
,
5669 "minor(device) -> minor number\n\
5670 Extracts a device minor number from a raw device number.");
5673 posix_minor(PyObject
*self
, PyObject
*args
)
5676 if (!PyArg_ParseTuple(args
, "i:minor", &device
))
5678 return PyInt_FromLong((long)minor(device
));
5681 PyDoc_STRVAR(posix_makedev__doc__
,
5682 "makedev(major, minor) -> device number\n\
5683 Composes a raw device number from the major and minor device numbers.");
5686 posix_makedev(PyObject
*self
, PyObject
*args
)
5689 if (!PyArg_ParseTuple(args
, "ii:makedev", &major
, &minor
))
5691 return PyInt_FromLong((long)makedev(major
, minor
));
5693 #endif /* device macros */
5696 #ifdef HAVE_FTRUNCATE
5697 PyDoc_STRVAR(posix_ftruncate__doc__
,
5698 "ftruncate(fd, length)\n\n\
5699 Truncate a file to a specified length.");
5702 posix_ftruncate(PyObject
*self
, PyObject
*args
)
5709 if (!PyArg_ParseTuple(args
, "iO:ftruncate", &fd
, &lenobj
))
5712 #if !defined(HAVE_LARGEFILE_SUPPORT)
5713 length
= PyInt_AsLong(lenobj
);
5715 length
= PyLong_Check(lenobj
) ?
5716 PyLong_AsLongLong(lenobj
) : PyInt_AsLong(lenobj
);
5718 if (PyErr_Occurred())
5721 Py_BEGIN_ALLOW_THREADS
5722 res
= ftruncate(fd
, length
);
5723 Py_END_ALLOW_THREADS
5725 PyErr_SetFromErrno(PyExc_IOError
);
5734 PyDoc_STRVAR(posix_putenv__doc__
,
5735 "putenv(key, value)\n\n\
5736 Change or add an environment variable.");
5738 /* Save putenv() parameters as values here, so we can collect them when they
5739 * get re-set with another call for the same key. */
5740 static PyObject
*posix_putenv_garbage
;
5743 posix_putenv(PyObject
*self
, PyObject
*args
)
5750 if (!PyArg_ParseTuple(args
, "ss:putenv", &s1
, &s2
))
5753 #if defined(PYOS_OS2)
5754 if (stricmp(s1
, "BEGINLIBPATH") == 0) {
5757 rc
= DosSetExtLIBPATH(s2
, BEGIN_LIBPATH
);
5759 return os2_error(rc
);
5761 } else if (stricmp(s1
, "ENDLIBPATH") == 0) {
5764 rc
= DosSetExtLIBPATH(s2
, END_LIBPATH
);
5766 return os2_error(rc
);
5770 /* XXX This can leak memory -- not easy to fix :-( */
5771 len
= strlen(s1
) + strlen(s2
) + 2;
5772 /* len includes space for a trailing \0; the size arg to
5773 PyString_FromStringAndSize does not count that */
5774 newstr
= PyString_FromStringAndSize(NULL
, (int)len
- 1);
5776 return PyErr_NoMemory();
5777 new = PyString_AS_STRING(newstr
);
5778 PyOS_snprintf(new, len
, "%s=%s", s1
, s2
);
5784 /* Install the first arg and newstr in posix_putenv_garbage;
5785 * this will cause previous value to be collected. This has to
5786 * happen after the real putenv() call because the old value
5787 * was still accessible until then. */
5788 if (PyDict_SetItem(posix_putenv_garbage
,
5789 PyTuple_GET_ITEM(args
, 0), newstr
)) {
5790 /* really not much we can do; just leak */
5797 #if defined(PYOS_OS2)
5805 #ifdef HAVE_UNSETENV
5806 PyDoc_STRVAR(posix_unsetenv__doc__
,
5808 Delete an environment variable.");
5811 posix_unsetenv(PyObject
*self
, PyObject
*args
)
5815 if (!PyArg_ParseTuple(args
, "s:unsetenv", &s1
))
5820 /* Remove the key from posix_putenv_garbage;
5821 * this will cause it to be collected. This has to
5822 * happen after the real unsetenv() call because the
5823 * old value was still accessible until then.
5825 if (PyDict_DelItem(posix_putenv_garbage
,
5826 PyTuple_GET_ITEM(args
, 0))) {
5827 /* really not much we can do; just leak */
5834 #endif /* unsetenv */
5836 #ifdef HAVE_STRERROR
5837 PyDoc_STRVAR(posix_strerror__doc__
,
5838 "strerror(code) -> string\n\n\
5839 Translate an error code to a message string.");
5842 posix_strerror(PyObject
*self
, PyObject
*args
)
5846 if (!PyArg_ParseTuple(args
, "i:strerror", &code
))
5848 message
= strerror(code
);
5849 if (message
== NULL
) {
5850 PyErr_SetString(PyExc_ValueError
,
5851 "strerror() argument out of range");
5854 return PyString_FromString(message
);
5856 #endif /* strerror */
5859 #ifdef HAVE_SYS_WAIT_H
5862 PyDoc_STRVAR(posix_WCOREDUMP__doc__
,
5863 "WCOREDUMP(status) -> bool\n\n\
5864 Return True if the process returning 'status' was dumped to a core file.");
5867 posix_WCOREDUMP(PyObject
*self
, PyObject
*args
)
5871 #define status_i (status.w_status)
5874 #define status_i status
5878 if (!PyArg_ParseTuple(args
, "i:WCOREDUMP", &status_i
))
5883 return PyBool_FromLong(WCOREDUMP(status
));
5886 #endif /* WCOREDUMP */
5889 PyDoc_STRVAR(posix_WIFCONTINUED__doc__
,
5890 "WIFCONTINUED(status) -> bool\n\n\
5891 Return True if the process returning 'status' was continued from a\n\
5892 job control stop.");
5895 posix_WIFCONTINUED(PyObject
*self
, PyObject
*args
)
5899 #define status_i (status.w_status)
5902 #define status_i status
5906 if (!PyArg_ParseTuple(args
, "i:WCONTINUED", &status_i
))
5911 return PyBool_FromLong(WIFCONTINUED(status
));
5914 #endif /* WIFCONTINUED */
5917 PyDoc_STRVAR(posix_WIFSTOPPED__doc__
,
5918 "WIFSTOPPED(status) -> bool\n\n\
5919 Return True if the process returning 'status' was stopped.");
5922 posix_WIFSTOPPED(PyObject
*self
, PyObject
*args
)
5926 #define status_i (status.w_status)
5929 #define status_i status
5933 if (!PyArg_ParseTuple(args
, "i:WIFSTOPPED", &status_i
))
5938 return PyBool_FromLong(WIFSTOPPED(status
));
5941 #endif /* WIFSTOPPED */
5944 PyDoc_STRVAR(posix_WIFSIGNALED__doc__
,
5945 "WIFSIGNALED(status) -> bool\n\n\
5946 Return True if the process returning 'status' was terminated by a signal.");
5949 posix_WIFSIGNALED(PyObject
*self
, PyObject
*args
)
5953 #define status_i (status.w_status)
5956 #define status_i status
5960 if (!PyArg_ParseTuple(args
, "i:WIFSIGNALED", &status_i
))
5965 return PyBool_FromLong(WIFSIGNALED(status
));
5968 #endif /* WIFSIGNALED */
5971 PyDoc_STRVAR(posix_WIFEXITED__doc__
,
5972 "WIFEXITED(status) -> bool\n\n\
5973 Return true if the process returning 'status' exited using the exit()\n\
5977 posix_WIFEXITED(PyObject
*self
, PyObject
*args
)
5981 #define status_i (status.w_status)
5984 #define status_i status
5988 if (!PyArg_ParseTuple(args
, "i:WIFEXITED", &status_i
))
5993 return PyBool_FromLong(WIFEXITED(status
));
5996 #endif /* WIFEXITED */
5999 PyDoc_STRVAR(posix_WEXITSTATUS__doc__
,
6000 "WEXITSTATUS(status) -> integer\n\n\
6001 Return the process return code from 'status'.");
6004 posix_WEXITSTATUS(PyObject
*self
, PyObject
*args
)
6008 #define status_i (status.w_status)
6011 #define status_i status
6015 if (!PyArg_ParseTuple(args
, "i:WEXITSTATUS", &status_i
))
6020 return Py_BuildValue("i", WEXITSTATUS(status
));
6023 #endif /* WEXITSTATUS */
6026 PyDoc_STRVAR(posix_WTERMSIG__doc__
,
6027 "WTERMSIG(status) -> integer\n\n\
6028 Return the signal that terminated the process that provided the 'status'\n\
6032 posix_WTERMSIG(PyObject
*self
, PyObject
*args
)
6036 #define status_i (status.w_status)
6039 #define status_i status
6043 if (!PyArg_ParseTuple(args
, "i:WTERMSIG", &status_i
))
6048 return Py_BuildValue("i", WTERMSIG(status
));
6051 #endif /* WTERMSIG */
6054 PyDoc_STRVAR(posix_WSTOPSIG__doc__
,
6055 "WSTOPSIG(status) -> integer\n\n\
6056 Return the signal that stopped the process that provided\n\
6057 the 'status' value.");
6060 posix_WSTOPSIG(PyObject
*self
, PyObject
*args
)
6064 #define status_i (status.w_status)
6067 #define status_i status
6071 if (!PyArg_ParseTuple(args
, "i:WSTOPSIG", &status_i
))
6076 return Py_BuildValue("i", WSTOPSIG(status
));
6079 #endif /* WSTOPSIG */
6081 #endif /* HAVE_SYS_WAIT_H */
6084 #if defined(HAVE_FSTATVFS)
6086 /* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
6087 needed definitions in sys/statvfs.h */
6090 #include <sys/statvfs.h>
6093 _pystatvfs_fromstructstatvfs(struct statvfs st
) {
6094 PyObject
*v
= PyStructSequence_New(&StatVFSResultType
);
6098 #if !defined(HAVE_LARGEFILE_SUPPORT)
6099 PyStructSequence_SET_ITEM(v
, 0, PyInt_FromLong((long) st
.f_bsize
));
6100 PyStructSequence_SET_ITEM(v
, 1, PyInt_FromLong((long) st
.f_frsize
));
6101 PyStructSequence_SET_ITEM(v
, 2, PyInt_FromLong((long) st
.f_blocks
));
6102 PyStructSequence_SET_ITEM(v
, 3, PyInt_FromLong((long) st
.f_bfree
));
6103 PyStructSequence_SET_ITEM(v
, 4, PyInt_FromLong((long) st
.f_bavail
));
6104 PyStructSequence_SET_ITEM(v
, 5, PyInt_FromLong((long) st
.f_files
));
6105 PyStructSequence_SET_ITEM(v
, 6, PyInt_FromLong((long) st
.f_ffree
));
6106 PyStructSequence_SET_ITEM(v
, 7, PyInt_FromLong((long) st
.f_favail
));
6107 PyStructSequence_SET_ITEM(v
, 8, PyInt_FromLong((long) st
.f_flag
));
6108 PyStructSequence_SET_ITEM(v
, 9, PyInt_FromLong((long) st
.f_namemax
));
6110 PyStructSequence_SET_ITEM(v
, 0, PyInt_FromLong((long) st
.f_bsize
));
6111 PyStructSequence_SET_ITEM(v
, 1, PyInt_FromLong((long) st
.f_frsize
));
6112 PyStructSequence_SET_ITEM(v
, 2,
6113 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_blocks
));
6114 PyStructSequence_SET_ITEM(v
, 3,
6115 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_bfree
));
6116 PyStructSequence_SET_ITEM(v
, 4,
6117 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_bavail
));
6118 PyStructSequence_SET_ITEM(v
, 5,
6119 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_files
));
6120 PyStructSequence_SET_ITEM(v
, 6,
6121 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_ffree
));
6122 PyStructSequence_SET_ITEM(v
, 7,
6123 PyLong_FromLongLong((PY_LONG_LONG
) st
.f_favail
));
6124 PyStructSequence_SET_ITEM(v
, 8, PyInt_FromLong((long) st
.f_flag
));
6125 PyStructSequence_SET_ITEM(v
, 9, PyInt_FromLong((long) st
.f_namemax
));
6131 PyDoc_STRVAR(posix_fstatvfs__doc__
,
6132 "fstatvfs(fd) -> statvfs result\n\n\
6133 Perform an fstatvfs system call on the given fd.");
6136 posix_fstatvfs(PyObject
*self
, PyObject
*args
)
6141 if (!PyArg_ParseTuple(args
, "i:fstatvfs", &fd
))
6143 Py_BEGIN_ALLOW_THREADS
6144 res
= fstatvfs(fd
, &st
);
6145 Py_END_ALLOW_THREADS
6147 return posix_error();
6149 return _pystatvfs_fromstructstatvfs(st
);
6151 #endif /* HAVE_FSTATVFS */
6154 #if defined(HAVE_STATVFS)
6155 #include <sys/statvfs.h>
6157 PyDoc_STRVAR(posix_statvfs__doc__
,
6158 "statvfs(path) -> statvfs result\n\n\
6159 Perform a statvfs system call on the given path.");
6162 posix_statvfs(PyObject
*self
, PyObject
*args
)
6167 if (!PyArg_ParseTuple(args
, "s:statvfs", &path
))
6169 Py_BEGIN_ALLOW_THREADS
6170 res
= statvfs(path
, &st
);
6171 Py_END_ALLOW_THREADS
6173 return posix_error_with_filename(path
);
6175 return _pystatvfs_fromstructstatvfs(st
);
6177 #endif /* HAVE_STATVFS */
6181 PyDoc_STRVAR(posix_tempnam__doc__
,
6182 "tempnam([dir[, prefix]]) -> string\n\n\
6183 Return a unique name for a temporary file.\n\
6184 The directory and a prefix may be specified as strings; they may be omitted\n\
6185 or None if not needed.");
6188 posix_tempnam(PyObject
*self
, PyObject
*args
)
6190 PyObject
*result
= NULL
;
6195 if (!PyArg_ParseTuple(args
, "|zz:tempnam", &dir
, &pfx
))
6198 if (PyErr_Warn(PyExc_RuntimeWarning
,
6199 "tempnam is a potential security risk to your program") < 0)
6203 name
= _tempnam(dir
, pfx
);
6205 name
= tempnam(dir
, pfx
);
6208 return PyErr_NoMemory();
6209 result
= PyString_FromString(name
);
6217 PyDoc_STRVAR(posix_tmpfile__doc__
,
6218 "tmpfile() -> file object\n\n\
6219 Create a temporary file with no directory entries.");
6222 posix_tmpfile(PyObject
*self
, PyObject
*noargs
)
6228 return posix_error();
6229 return PyFile_FromFile(fp
, "<tmpfile>", "w+b", fclose
);
6235 PyDoc_STRVAR(posix_tmpnam__doc__
,
6236 "tmpnam() -> string\n\n\
6237 Return a unique name for a temporary file.");
6240 posix_tmpnam(PyObject
*self
, PyObject
*noargs
)
6242 char buffer
[L_tmpnam
];
6245 if (PyErr_Warn(PyExc_RuntimeWarning
,
6246 "tmpnam is a potential security risk to your program") < 0)
6250 name
= tmpnam_r(buffer
);
6252 name
= tmpnam(buffer
);
6255 PyErr_SetObject(PyExc_OSError
,
6256 Py_BuildValue("is", 0,
6258 "unexpected NULL from tmpnam_r"
6260 "unexpected NULL from tmpnam"
6265 return PyString_FromString(buffer
);
6270 /* This is used for fpathconf(), pathconf(), confstr() and sysconf().
6271 * It maps strings representing configuration variable names to
6272 * integer values, allowing those functions to be called with the
6273 * magic names instead of polluting the module's namespace with tons of
6274 * rarely-used constants. There are three separate tables that use
6275 * these definitions.
6277 * This code is always included, even if none of the interfaces that
6278 * need it are included. The #if hackery needed to avoid it would be
6279 * sufficiently pervasive that it's not worth the loss of readability.
6287 conv_confname(PyObject
*arg
, int *valuep
, struct constdef
*table
,
6290 if (PyInt_Check(arg
)) {
6291 *valuep
= PyInt_AS_LONG(arg
);
6294 if (PyString_Check(arg
)) {
6295 /* look up the value in the table using a binary search */
6298 size_t hi
= tablesize
;
6300 char *confname
= PyString_AS_STRING(arg
);
6302 mid
= (lo
+ hi
) / 2;
6303 cmp
= strcmp(confname
, table
[mid
].name
);
6309 *valuep
= table
[mid
].value
;
6313 PyErr_SetString(PyExc_ValueError
, "unrecognized configuration name");
6316 PyErr_SetString(PyExc_TypeError
,
6317 "configuration names must be strings or integers");
6322 #if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
6323 static struct constdef posix_constants_pathconf
[] = {
6324 #ifdef _PC_ABI_AIO_XFER_MAX
6325 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX
},
6327 #ifdef _PC_ABI_ASYNC_IO
6328 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO
},
6331 {"PC_ASYNC_IO", _PC_ASYNC_IO
},
6333 #ifdef _PC_CHOWN_RESTRICTED
6334 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED
},
6336 #ifdef _PC_FILESIZEBITS
6337 {"PC_FILESIZEBITS", _PC_FILESIZEBITS
},
6340 {"PC_LAST", _PC_LAST
},
6343 {"PC_LINK_MAX", _PC_LINK_MAX
},
6345 #ifdef _PC_MAX_CANON
6346 {"PC_MAX_CANON", _PC_MAX_CANON
},
6348 #ifdef _PC_MAX_INPUT
6349 {"PC_MAX_INPUT", _PC_MAX_INPUT
},
6352 {"PC_NAME_MAX", _PC_NAME_MAX
},
6355 {"PC_NO_TRUNC", _PC_NO_TRUNC
},
6358 {"PC_PATH_MAX", _PC_PATH_MAX
},
6361 {"PC_PIPE_BUF", _PC_PIPE_BUF
},
6364 {"PC_PRIO_IO", _PC_PRIO_IO
},
6366 #ifdef _PC_SOCK_MAXBUF
6367 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF
},
6370 {"PC_SYNC_IO", _PC_SYNC_IO
},
6373 {"PC_VDISABLE", _PC_VDISABLE
},
6378 conv_path_confname(PyObject
*arg
, int *valuep
)
6380 return conv_confname(arg
, valuep
, posix_constants_pathconf
,
6381 sizeof(posix_constants_pathconf
)
6382 / sizeof(struct constdef
));
6386 #ifdef HAVE_FPATHCONF
6387 PyDoc_STRVAR(posix_fpathconf__doc__
,
6388 "fpathconf(fd, name) -> integer\n\n\
6389 Return the configuration limit name for the file descriptor fd.\n\
6390 If there is no limit, return -1.");
6393 posix_fpathconf(PyObject
*self
, PyObject
*args
)
6395 PyObject
*result
= NULL
;
6398 if (PyArg_ParseTuple(args
, "iO&:fpathconf", &fd
,
6399 conv_path_confname
, &name
)) {
6403 limit
= fpathconf(fd
, name
);
6404 if (limit
== -1 && errno
!= 0)
6407 result
= PyInt_FromLong(limit
);
6414 #ifdef HAVE_PATHCONF
6415 PyDoc_STRVAR(posix_pathconf__doc__
,
6416 "pathconf(path, name) -> integer\n\n\
6417 Return the configuration limit name for the file or directory path.\n\
6418 If there is no limit, return -1.");
6421 posix_pathconf(PyObject
*self
, PyObject
*args
)
6423 PyObject
*result
= NULL
;
6427 if (PyArg_ParseTuple(args
, "sO&:pathconf", &path
,
6428 conv_path_confname
, &name
)) {
6432 limit
= pathconf(path
, name
);
6433 if (limit
== -1 && errno
!= 0) {
6434 if (errno
== EINVAL
)
6435 /* could be a path or name problem */
6438 posix_error_with_filename(path
);
6441 result
= PyInt_FromLong(limit
);
6448 static struct constdef posix_constants_confstr
[] = {
6449 #ifdef _CS_ARCHITECTURE
6450 {"CS_ARCHITECTURE", _CS_ARCHITECTURE
},
6453 {"CS_HOSTNAME", _CS_HOSTNAME
},
6455 #ifdef _CS_HW_PROVIDER
6456 {"CS_HW_PROVIDER", _CS_HW_PROVIDER
},
6458 #ifdef _CS_HW_SERIAL
6459 {"CS_HW_SERIAL", _CS_HW_SERIAL
},
6461 #ifdef _CS_INITTAB_NAME
6462 {"CS_INITTAB_NAME", _CS_INITTAB_NAME
},
6464 #ifdef _CS_LFS64_CFLAGS
6465 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS
},
6467 #ifdef _CS_LFS64_LDFLAGS
6468 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS
},
6470 #ifdef _CS_LFS64_LIBS
6471 {"CS_LFS64_LIBS", _CS_LFS64_LIBS
},
6473 #ifdef _CS_LFS64_LINTFLAGS
6474 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS
},
6476 #ifdef _CS_LFS_CFLAGS
6477 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS
},
6479 #ifdef _CS_LFS_LDFLAGS
6480 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS
},
6483 {"CS_LFS_LIBS", _CS_LFS_LIBS
},
6485 #ifdef _CS_LFS_LINTFLAGS
6486 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS
},
6489 {"CS_MACHINE", _CS_MACHINE
},
6492 {"CS_PATH", _CS_PATH
},
6495 {"CS_RELEASE", _CS_RELEASE
},
6497 #ifdef _CS_SRPC_DOMAIN
6498 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN
},
6501 {"CS_SYSNAME", _CS_SYSNAME
},
6504 {"CS_VERSION", _CS_VERSION
},
6506 #ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
6507 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS
},
6509 #ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
6510 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS
},
6512 #ifdef _CS_XBS5_ILP32_OFF32_LIBS
6513 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS
},
6515 #ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
6516 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS
},
6518 #ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
6519 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS
},
6521 #ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
6522 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS
},
6524 #ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
6525 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS
},
6527 #ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
6528 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
},
6530 #ifdef _CS_XBS5_LP64_OFF64_CFLAGS
6531 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS
},
6533 #ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
6534 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS
},
6536 #ifdef _CS_XBS5_LP64_OFF64_LIBS
6537 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS
},
6539 #ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
6540 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS
},
6542 #ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
6543 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS
},
6545 #ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
6546 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
},
6548 #ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
6549 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS
},
6551 #ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
6552 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
},
6554 #ifdef _MIPS_CS_AVAIL_PROCESSORS
6555 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS
},
6557 #ifdef _MIPS_CS_BASE
6558 {"MIPS_CS_BASE", _MIPS_CS_BASE
},
6560 #ifdef _MIPS_CS_HOSTID
6561 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID
},
6563 #ifdef _MIPS_CS_HW_NAME
6564 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME
},
6566 #ifdef _MIPS_CS_NUM_PROCESSORS
6567 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS
},
6569 #ifdef _MIPS_CS_OSREL_MAJ
6570 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ
},
6572 #ifdef _MIPS_CS_OSREL_MIN
6573 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN
},
6575 #ifdef _MIPS_CS_OSREL_PATCH
6576 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH
},
6578 #ifdef _MIPS_CS_OS_NAME
6579 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME
},
6581 #ifdef _MIPS_CS_OS_PROVIDER
6582 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER
},
6584 #ifdef _MIPS_CS_PROCESSORS
6585 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS
},
6587 #ifdef _MIPS_CS_SERIAL
6588 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL
},
6590 #ifdef _MIPS_CS_VENDOR
6591 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR
},
6596 conv_confstr_confname(PyObject
*arg
, int *valuep
)
6598 return conv_confname(arg
, valuep
, posix_constants_confstr
,
6599 sizeof(posix_constants_confstr
)
6600 / sizeof(struct constdef
));
6603 PyDoc_STRVAR(posix_confstr__doc__
,
6604 "confstr(name) -> string\n\n\
6605 Return a string-valued system configuration variable.");
6608 posix_confstr(PyObject
*self
, PyObject
*args
)
6610 PyObject
*result
= NULL
;
6614 if (PyArg_ParseTuple(args
, "O&:confstr", conv_confstr_confname
, &name
)) {
6615 int len
= confstr(name
, buffer
, sizeof(buffer
));
6622 result
= PyString_FromString("");
6625 if (len
>= sizeof(buffer
)) {
6626 result
= PyString_FromStringAndSize(NULL
, len
);
6628 confstr(name
, PyString_AS_STRING(result
), len
+1);
6631 result
= PyString_FromString(buffer
);
6640 static struct constdef posix_constants_sysconf
[] = {
6641 #ifdef _SC_2_CHAR_TERM
6642 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM
},
6645 {"SC_2_C_BIND", _SC_2_C_BIND
},
6648 {"SC_2_C_DEV", _SC_2_C_DEV
},
6650 #ifdef _SC_2_C_VERSION
6651 {"SC_2_C_VERSION", _SC_2_C_VERSION
},
6653 #ifdef _SC_2_FORT_DEV
6654 {"SC_2_FORT_DEV", _SC_2_FORT_DEV
},
6656 #ifdef _SC_2_FORT_RUN
6657 {"SC_2_FORT_RUN", _SC_2_FORT_RUN
},
6659 #ifdef _SC_2_LOCALEDEF
6660 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF
},
6663 {"SC_2_SW_DEV", _SC_2_SW_DEV
},
6666 {"SC_2_UPE", _SC_2_UPE
},
6668 #ifdef _SC_2_VERSION
6669 {"SC_2_VERSION", _SC_2_VERSION
},
6671 #ifdef _SC_ABI_ASYNCHRONOUS_IO
6672 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO
},
6675 {"SC_ACL", _SC_ACL
},
6677 #ifdef _SC_AIO_LISTIO_MAX
6678 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX
},
6681 {"SC_AIO_MAX", _SC_AIO_MAX
},
6683 #ifdef _SC_AIO_PRIO_DELTA_MAX
6684 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX
},
6687 {"SC_ARG_MAX", _SC_ARG_MAX
},
6689 #ifdef _SC_ASYNCHRONOUS_IO
6690 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO
},
6692 #ifdef _SC_ATEXIT_MAX
6693 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX
},
6696 {"SC_AUDIT", _SC_AUDIT
},
6698 #ifdef _SC_AVPHYS_PAGES
6699 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES
},
6701 #ifdef _SC_BC_BASE_MAX
6702 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX
},
6704 #ifdef _SC_BC_DIM_MAX
6705 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX
},
6707 #ifdef _SC_BC_SCALE_MAX
6708 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX
},
6710 #ifdef _SC_BC_STRING_MAX
6711 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX
},
6714 {"SC_CAP", _SC_CAP
},
6716 #ifdef _SC_CHARCLASS_NAME_MAX
6717 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX
},
6720 {"SC_CHAR_BIT", _SC_CHAR_BIT
},
6723 {"SC_CHAR_MAX", _SC_CHAR_MAX
},
6726 {"SC_CHAR_MIN", _SC_CHAR_MIN
},
6728 #ifdef _SC_CHILD_MAX
6729 {"SC_CHILD_MAX", _SC_CHILD_MAX
},
6732 {"SC_CLK_TCK", _SC_CLK_TCK
},
6734 #ifdef _SC_COHER_BLKSZ
6735 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ
},
6737 #ifdef _SC_COLL_WEIGHTS_MAX
6738 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX
},
6740 #ifdef _SC_DCACHE_ASSOC
6741 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC
},
6743 #ifdef _SC_DCACHE_BLKSZ
6744 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ
},
6746 #ifdef _SC_DCACHE_LINESZ
6747 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ
},
6749 #ifdef _SC_DCACHE_SZ
6750 {"SC_DCACHE_SZ", _SC_DCACHE_SZ
},
6752 #ifdef _SC_DCACHE_TBLKSZ
6753 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ
},
6755 #ifdef _SC_DELAYTIMER_MAX
6756 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX
},
6758 #ifdef _SC_EQUIV_CLASS_MAX
6759 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX
},
6761 #ifdef _SC_EXPR_NEST_MAX
6762 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX
},
6765 {"SC_FSYNC", _SC_FSYNC
},
6767 #ifdef _SC_GETGR_R_SIZE_MAX
6768 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX
},
6770 #ifdef _SC_GETPW_R_SIZE_MAX
6771 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX
},
6773 #ifdef _SC_ICACHE_ASSOC
6774 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC
},
6776 #ifdef _SC_ICACHE_BLKSZ
6777 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ
},
6779 #ifdef _SC_ICACHE_LINESZ
6780 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ
},
6782 #ifdef _SC_ICACHE_SZ
6783 {"SC_ICACHE_SZ", _SC_ICACHE_SZ
},
6786 {"SC_INF", _SC_INF
},
6789 {"SC_INT_MAX", _SC_INT_MAX
},
6792 {"SC_INT_MIN", _SC_INT_MIN
},
6795 {"SC_IOV_MAX", _SC_IOV_MAX
},
6797 #ifdef _SC_IP_SECOPTS
6798 {"SC_IP_SECOPTS", _SC_IP_SECOPTS
},
6800 #ifdef _SC_JOB_CONTROL
6801 {"SC_JOB_CONTROL", _SC_JOB_CONTROL
},
6803 #ifdef _SC_KERN_POINTERS
6804 {"SC_KERN_POINTERS", _SC_KERN_POINTERS
},
6807 {"SC_KERN_SIM", _SC_KERN_SIM
},
6810 {"SC_LINE_MAX", _SC_LINE_MAX
},
6812 #ifdef _SC_LOGIN_NAME_MAX
6813 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX
},
6815 #ifdef _SC_LOGNAME_MAX
6816 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX
},
6819 {"SC_LONG_BIT", _SC_LONG_BIT
},
6822 {"SC_MAC", _SC_MAC
},
6824 #ifdef _SC_MAPPED_FILES
6825 {"SC_MAPPED_FILES", _SC_MAPPED_FILES
},
6828 {"SC_MAXPID", _SC_MAXPID
},
6830 #ifdef _SC_MB_LEN_MAX
6831 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX
},
6834 {"SC_MEMLOCK", _SC_MEMLOCK
},
6836 #ifdef _SC_MEMLOCK_RANGE
6837 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE
},
6839 #ifdef _SC_MEMORY_PROTECTION
6840 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION
},
6842 #ifdef _SC_MESSAGE_PASSING
6843 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING
},
6845 #ifdef _SC_MMAP_FIXED_ALIGNMENT
6846 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT
},
6848 #ifdef _SC_MQ_OPEN_MAX
6849 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX
},
6851 #ifdef _SC_MQ_PRIO_MAX
6852 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX
},
6854 #ifdef _SC_NACLS_MAX
6855 {"SC_NACLS_MAX", _SC_NACLS_MAX
},
6857 #ifdef _SC_NGROUPS_MAX
6858 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX
},
6860 #ifdef _SC_NL_ARGMAX
6861 {"SC_NL_ARGMAX", _SC_NL_ARGMAX
},
6863 #ifdef _SC_NL_LANGMAX
6864 {"SC_NL_LANGMAX", _SC_NL_LANGMAX
},
6866 #ifdef _SC_NL_MSGMAX
6867 {"SC_NL_MSGMAX", _SC_NL_MSGMAX
},
6870 {"SC_NL_NMAX", _SC_NL_NMAX
},
6872 #ifdef _SC_NL_SETMAX
6873 {"SC_NL_SETMAX", _SC_NL_SETMAX
},
6875 #ifdef _SC_NL_TEXTMAX
6876 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX
},
6878 #ifdef _SC_NPROCESSORS_CONF
6879 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF
},
6881 #ifdef _SC_NPROCESSORS_ONLN
6882 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN
},
6884 #ifdef _SC_NPROC_CONF
6885 {"SC_NPROC_CONF", _SC_NPROC_CONF
},
6887 #ifdef _SC_NPROC_ONLN
6888 {"SC_NPROC_ONLN", _SC_NPROC_ONLN
},
6891 {"SC_NZERO", _SC_NZERO
},
6894 {"SC_OPEN_MAX", _SC_OPEN_MAX
},
6897 {"SC_PAGESIZE", _SC_PAGESIZE
},
6899 #ifdef _SC_PAGE_SIZE
6900 {"SC_PAGE_SIZE", _SC_PAGE_SIZE
},
6903 {"SC_PASS_MAX", _SC_PASS_MAX
},
6905 #ifdef _SC_PHYS_PAGES
6906 {"SC_PHYS_PAGES", _SC_PHYS_PAGES
},
6909 {"SC_PII", _SC_PII
},
6911 #ifdef _SC_PII_INTERNET
6912 {"SC_PII_INTERNET", _SC_PII_INTERNET
},
6914 #ifdef _SC_PII_INTERNET_DGRAM
6915 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM
},
6917 #ifdef _SC_PII_INTERNET_STREAM
6918 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM
},
6921 {"SC_PII_OSI", _SC_PII_OSI
},
6923 #ifdef _SC_PII_OSI_CLTS
6924 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS
},
6926 #ifdef _SC_PII_OSI_COTS
6927 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS
},
6929 #ifdef _SC_PII_OSI_M
6930 {"SC_PII_OSI_M", _SC_PII_OSI_M
},
6932 #ifdef _SC_PII_SOCKET
6933 {"SC_PII_SOCKET", _SC_PII_SOCKET
},
6936 {"SC_PII_XTI", _SC_PII_XTI
},
6939 {"SC_POLL", _SC_POLL
},
6941 #ifdef _SC_PRIORITIZED_IO
6942 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO
},
6944 #ifdef _SC_PRIORITY_SCHEDULING
6945 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING
},
6947 #ifdef _SC_REALTIME_SIGNALS
6948 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS
},
6950 #ifdef _SC_RE_DUP_MAX
6951 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX
},
6953 #ifdef _SC_RTSIG_MAX
6954 {"SC_RTSIG_MAX", _SC_RTSIG_MAX
},
6956 #ifdef _SC_SAVED_IDS
6957 {"SC_SAVED_IDS", _SC_SAVED_IDS
},
6959 #ifdef _SC_SCHAR_MAX
6960 {"SC_SCHAR_MAX", _SC_SCHAR_MAX
},
6962 #ifdef _SC_SCHAR_MIN
6963 {"SC_SCHAR_MIN", _SC_SCHAR_MIN
},
6966 {"SC_SELECT", _SC_SELECT
},
6968 #ifdef _SC_SEMAPHORES
6969 {"SC_SEMAPHORES", _SC_SEMAPHORES
},
6971 #ifdef _SC_SEM_NSEMS_MAX
6972 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX
},
6974 #ifdef _SC_SEM_VALUE_MAX
6975 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX
},
6977 #ifdef _SC_SHARED_MEMORY_OBJECTS
6978 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS
},
6981 {"SC_SHRT_MAX", _SC_SHRT_MAX
},
6984 {"SC_SHRT_MIN", _SC_SHRT_MIN
},
6986 #ifdef _SC_SIGQUEUE_MAX
6987 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX
},
6989 #ifdef _SC_SIGRT_MAX
6990 {"SC_SIGRT_MAX", _SC_SIGRT_MAX
},
6992 #ifdef _SC_SIGRT_MIN
6993 {"SC_SIGRT_MIN", _SC_SIGRT_MIN
},
6995 #ifdef _SC_SOFTPOWER
6996 {"SC_SOFTPOWER", _SC_SOFTPOWER
},
6998 #ifdef _SC_SPLIT_CACHE
6999 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE
},
7001 #ifdef _SC_SSIZE_MAX
7002 {"SC_SSIZE_MAX", _SC_SSIZE_MAX
},
7004 #ifdef _SC_STACK_PROT
7005 {"SC_STACK_PROT", _SC_STACK_PROT
},
7007 #ifdef _SC_STREAM_MAX
7008 {"SC_STREAM_MAX", _SC_STREAM_MAX
},
7010 #ifdef _SC_SYNCHRONIZED_IO
7011 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO
},
7014 {"SC_THREADS", _SC_THREADS
},
7016 #ifdef _SC_THREAD_ATTR_STACKADDR
7017 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR
},
7019 #ifdef _SC_THREAD_ATTR_STACKSIZE
7020 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE
},
7022 #ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
7023 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS
},
7025 #ifdef _SC_THREAD_KEYS_MAX
7026 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX
},
7028 #ifdef _SC_THREAD_PRIORITY_SCHEDULING
7029 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING
},
7031 #ifdef _SC_THREAD_PRIO_INHERIT
7032 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT
},
7034 #ifdef _SC_THREAD_PRIO_PROTECT
7035 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT
},
7037 #ifdef _SC_THREAD_PROCESS_SHARED
7038 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED
},
7040 #ifdef _SC_THREAD_SAFE_FUNCTIONS
7041 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS
},
7043 #ifdef _SC_THREAD_STACK_MIN
7044 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN
},
7046 #ifdef _SC_THREAD_THREADS_MAX
7047 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX
},
7050 {"SC_TIMERS", _SC_TIMERS
},
7052 #ifdef _SC_TIMER_MAX
7053 {"SC_TIMER_MAX", _SC_TIMER_MAX
},
7055 #ifdef _SC_TTY_NAME_MAX
7056 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX
},
7058 #ifdef _SC_TZNAME_MAX
7059 {"SC_TZNAME_MAX", _SC_TZNAME_MAX
},
7061 #ifdef _SC_T_IOV_MAX
7062 {"SC_T_IOV_MAX", _SC_T_IOV_MAX
},
7064 #ifdef _SC_UCHAR_MAX
7065 {"SC_UCHAR_MAX", _SC_UCHAR_MAX
},
7068 {"SC_UINT_MAX", _SC_UINT_MAX
},
7070 #ifdef _SC_UIO_MAXIOV
7071 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV
},
7073 #ifdef _SC_ULONG_MAX
7074 {"SC_ULONG_MAX", _SC_ULONG_MAX
},
7076 #ifdef _SC_USHRT_MAX
7077 {"SC_USHRT_MAX", _SC_USHRT_MAX
},
7080 {"SC_VERSION", _SC_VERSION
},
7083 {"SC_WORD_BIT", _SC_WORD_BIT
},
7085 #ifdef _SC_XBS5_ILP32_OFF32
7086 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32
},
7088 #ifdef _SC_XBS5_ILP32_OFFBIG
7089 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG
},
7091 #ifdef _SC_XBS5_LP64_OFF64
7092 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64
},
7094 #ifdef _SC_XBS5_LPBIG_OFFBIG
7095 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG
},
7097 #ifdef _SC_XOPEN_CRYPT
7098 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT
},
7100 #ifdef _SC_XOPEN_ENH_I18N
7101 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N
},
7103 #ifdef _SC_XOPEN_LEGACY
7104 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY
},
7106 #ifdef _SC_XOPEN_REALTIME
7107 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME
},
7109 #ifdef _SC_XOPEN_REALTIME_THREADS
7110 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS
},
7112 #ifdef _SC_XOPEN_SHM
7113 {"SC_XOPEN_SHM", _SC_XOPEN_SHM
},
7115 #ifdef _SC_XOPEN_UNIX
7116 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX
},
7118 #ifdef _SC_XOPEN_VERSION
7119 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION
},
7121 #ifdef _SC_XOPEN_XCU_VERSION
7122 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION
},
7124 #ifdef _SC_XOPEN_XPG2
7125 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2
},
7127 #ifdef _SC_XOPEN_XPG3
7128 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3
},
7130 #ifdef _SC_XOPEN_XPG4
7131 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4
},
7136 conv_sysconf_confname(PyObject
*arg
, int *valuep
)
7138 return conv_confname(arg
, valuep
, posix_constants_sysconf
,
7139 sizeof(posix_constants_sysconf
)
7140 / sizeof(struct constdef
));
7143 PyDoc_STRVAR(posix_sysconf__doc__
,
7144 "sysconf(name) -> integer\n\n\
7145 Return an integer-valued system configuration variable.");
7148 posix_sysconf(PyObject
*self
, PyObject
*args
)
7150 PyObject
*result
= NULL
;
7153 if (PyArg_ParseTuple(args
, "O&:sysconf", conv_sysconf_confname
, &name
)) {
7157 value
= sysconf(name
);
7158 if (value
== -1 && errno
!= 0)
7161 result
= PyInt_FromLong(value
);
7168 /* This code is used to ensure that the tables of configuration value names
7169 * are in sorted order as required by conv_confname(), and also to build the
7170 * the exported dictionaries that are used to publish information about the
7171 * names available on the host platform.
7173 * Sorting the table at runtime ensures that the table is properly ordered
7174 * when used, even for platforms we're not able to test on. It also makes
7175 * it easier to add additional entries to the tables.
7179 cmp_constdefs(const void *v1
, const void *v2
)
7181 const struct constdef
*c1
=
7182 (const struct constdef
*) v1
;
7183 const struct constdef
*c2
=
7184 (const struct constdef
*) v2
;
7186 return strcmp(c1
->name
, c2
->name
);
7190 setup_confname_table(struct constdef
*table
, size_t tablesize
,
7191 char *tablename
, PyObject
*module
)
7196 qsort(table
, tablesize
, sizeof(struct constdef
), cmp_constdefs
);
7201 for (i
=0; i
< tablesize
; ++i
) {
7202 PyObject
*o
= PyInt_FromLong(table
[i
].value
);
7203 if (o
== NULL
|| PyDict_SetItemString(d
, table
[i
].name
, o
) == -1) {
7210 return PyModule_AddObject(module
, tablename
, d
);
7213 /* Return -1 on failure, 0 on success. */
7215 setup_confname_tables(PyObject
*module
)
7217 #if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
7218 if (setup_confname_table(posix_constants_pathconf
,
7219 sizeof(posix_constants_pathconf
)
7220 / sizeof(struct constdef
),
7221 "pathconf_names", module
))
7225 if (setup_confname_table(posix_constants_confstr
,
7226 sizeof(posix_constants_confstr
)
7227 / sizeof(struct constdef
),
7228 "confstr_names", module
))
7232 if (setup_confname_table(posix_constants_sysconf
,
7233 sizeof(posix_constants_sysconf
)
7234 / sizeof(struct constdef
),
7235 "sysconf_names", module
))
7242 PyDoc_STRVAR(posix_abort__doc__
,
7243 "abort() -> does not return!\n\n\
7244 Abort the interpreter immediately. This 'dumps core' or otherwise fails\n\
7245 in the hardest way possible on the hosting operating system.");
7248 posix_abort(PyObject
*self
, PyObject
*noargs
)
7252 Py_FatalError("abort() called from Python code didn't abort!");
7257 PyDoc_STRVAR(win32_startfile__doc__
,
7258 "startfile(filepath) - Start a file with its associated application.\n\
7260 This acts like double-clicking the file in Explorer, or giving the file\n\
7261 name as an argument to the DOS \"start\" command: the file is opened\n\
7262 with whatever application (if any) its extension is associated.\n\
7264 startfile returns as soon as the associated application is launched.\n\
7265 There is no option to wait for the application to close, and no way\n\
7266 to retrieve the application's exit status.\n\
7268 The filepath is relative to the current directory. If you want to use\n\
7269 an absolute path, make sure the first character is not a slash (\"/\");\n\
7270 the underlying Win32 ShellExecute function doesn't work if it is.");
7273 win32_startfile(PyObject
*self
, PyObject
*args
)
7277 if (!PyArg_ParseTuple(args
, "et:startfile",
7278 Py_FileSystemDefaultEncoding
, &filepath
))
7280 Py_BEGIN_ALLOW_THREADS
7281 rc
= ShellExecute((HWND
)0, NULL
, filepath
, NULL
, NULL
, SW_SHOWNORMAL
);
7282 Py_END_ALLOW_THREADS
7283 if (rc
<= (HINSTANCE
)32) {
7284 PyObject
*errval
= win32_error("startfile", filepath
);
7285 PyMem_Free(filepath
);
7288 PyMem_Free(filepath
);
7294 #ifdef HAVE_GETLOADAVG
7295 PyDoc_STRVAR(posix_getloadavg__doc__
,
7296 "getloadavg() -> (float, float, float)\n\n\
7297 Return the number of processes in the system run queue averaged over\n\
7298 the last 1, 5, and 15 minutes or raises OSError if the load average\n\
7302 posix_getloadavg(PyObject
*self
, PyObject
*noargs
)
7305 if (getloadavg(loadavg
, 3)!=3) {
7306 PyErr_SetString(PyExc_OSError
, "Load averages are unobtainable");
7309 return Py_BuildValue("ddd", loadavg
[0], loadavg
[1], loadavg
[2]);
7315 PyDoc_STRVAR(win32_urandom__doc__
,
7316 "urandom(n) -> str\n\n\
7317 Return a string of n random bytes suitable for cryptographic use.");
7319 typedef BOOL (WINAPI
*CRYPTACQUIRECONTEXTA
)(HCRYPTPROV
*phProv
,\
7320 LPCSTR pszContainer
, LPCSTR pszProvider
, DWORD dwProvType
,\
7322 typedef BOOL (WINAPI
*CRYPTGENRANDOM
)(HCRYPTPROV hProv
, DWORD dwLen
,\
7325 static CRYPTGENRANDOM pCryptGenRandom
= NULL
;
7326 static HCRYPTPROV hCryptProv
= 0;
7329 win32_urandom(PyObject
*self
, PyObject
*args
)
7334 /* Read arguments */
7335 if (! PyArg_ParseTuple(args
, "i:urandom", &howMany
))
7338 return PyErr_Format(PyExc_ValueError
,
7339 "negative argument not allowed");
7341 if (hCryptProv
== 0) {
7342 HINSTANCE hAdvAPI32
= NULL
;
7343 CRYPTACQUIRECONTEXTA pCryptAcquireContext
= NULL
;
7345 /* Obtain handle to the DLL containing CryptoAPI
7346 This should not fail */
7347 hAdvAPI32
= GetModuleHandle("advapi32.dll");
7348 if(hAdvAPI32
== NULL
)
7349 return win32_error("GetModuleHandle", NULL
);
7351 /* Obtain pointers to the CryptoAPI functions
7352 This will fail on some early versions of Win95 */
7353 pCryptAcquireContext
= (CRYPTACQUIRECONTEXTA
)GetProcAddress(
7355 "CryptAcquireContextA");
7356 if (pCryptAcquireContext
== NULL
)
7357 return PyErr_Format(PyExc_NotImplementedError
,
7358 "CryptAcquireContextA not found");
7360 pCryptGenRandom
= (CRYPTGENRANDOM
)GetProcAddress(
7361 hAdvAPI32
, "CryptGenRandom");
7362 if (pCryptAcquireContext
== NULL
)
7363 return PyErr_Format(PyExc_NotImplementedError
,
7364 "CryptGenRandom not found");
7366 /* Acquire context */
7367 if (! pCryptAcquireContext(&hCryptProv
, NULL
, NULL
,
7368 PROV_RSA_FULL
, CRYPT_VERIFYCONTEXT
))
7369 return win32_error("CryptAcquireContext", NULL
);
7372 /* Allocate bytes */
7373 result
= PyString_FromStringAndSize(NULL
, howMany
);
7374 if (result
!= NULL
) {
7375 /* Get random data */
7376 if (! pCryptGenRandom(hCryptProv
, howMany
, (unsigned char*)
7377 PyString_AS_STRING(result
))) {
7379 return win32_error("CryptGenRandom", NULL
);
7386 static PyMethodDef posix_methods
[] = {
7387 {"access", posix_access
, METH_VARARGS
, posix_access__doc__
},
7389 {"ttyname", posix_ttyname
, METH_VARARGS
, posix_ttyname__doc__
},
7391 {"chdir", posix_chdir
, METH_VARARGS
, posix_chdir__doc__
},
7392 {"chmod", posix_chmod
, METH_VARARGS
, posix_chmod__doc__
},
7394 {"chown", posix_chown
, METH_VARARGS
, posix_chown__doc__
},
7395 #endif /* HAVE_CHOWN */
7397 {"lchown", posix_lchown
, METH_VARARGS
, posix_lchown__doc__
},
7398 #endif /* HAVE_LCHOWN */
7400 {"chroot", posix_chroot
, METH_VARARGS
, posix_chroot__doc__
},
7403 {"ctermid", posix_ctermid
, METH_NOARGS
, posix_ctermid__doc__
},
7406 {"getcwd", posix_getcwd
, METH_NOARGS
, posix_getcwd__doc__
},
7407 #ifdef Py_USING_UNICODE
7408 {"getcwdu", posix_getcwdu
, METH_NOARGS
, posix_getcwdu__doc__
},
7412 {"link", posix_link
, METH_VARARGS
, posix_link__doc__
},
7413 #endif /* HAVE_LINK */
7414 {"listdir", posix_listdir
, METH_VARARGS
, posix_listdir__doc__
},
7415 {"lstat", posix_lstat
, METH_VARARGS
, posix_lstat__doc__
},
7416 {"mkdir", posix_mkdir
, METH_VARARGS
, posix_mkdir__doc__
},
7418 {"nice", posix_nice
, METH_VARARGS
, posix_nice__doc__
},
7419 #endif /* HAVE_NICE */
7420 #ifdef HAVE_READLINK
7421 {"readlink", posix_readlink
, METH_VARARGS
, posix_readlink__doc__
},
7422 #endif /* HAVE_READLINK */
7423 {"rename", posix_rename
, METH_VARARGS
, posix_rename__doc__
},
7424 {"rmdir", posix_rmdir
, METH_VARARGS
, posix_rmdir__doc__
},
7425 {"stat", posix_stat
, METH_VARARGS
, posix_stat__doc__
},
7426 {"stat_float_times", stat_float_times
, METH_VARARGS
, stat_float_times__doc__
},
7428 {"symlink", posix_symlink
, METH_VARARGS
, posix_symlink__doc__
},
7429 #endif /* HAVE_SYMLINK */
7431 {"system", posix_system
, METH_VARARGS
, posix_system__doc__
},
7433 {"umask", posix_umask
, METH_VARARGS
, posix_umask__doc__
},
7435 {"uname", posix_uname
, METH_NOARGS
, posix_uname__doc__
},
7436 #endif /* HAVE_UNAME */
7437 {"unlink", posix_unlink
, METH_VARARGS
, posix_unlink__doc__
},
7438 {"remove", posix_unlink
, METH_VARARGS
, posix_remove__doc__
},
7439 {"utime", posix_utime
, METH_VARARGS
, posix_utime__doc__
},
7441 {"times", posix_times
, METH_NOARGS
, posix_times__doc__
},
7442 #endif /* HAVE_TIMES */
7443 {"_exit", posix__exit
, METH_VARARGS
, posix__exit__doc__
},
7445 {"execv", posix_execv
, METH_VARARGS
, posix_execv__doc__
},
7446 {"execve", posix_execve
, METH_VARARGS
, posix_execve__doc__
},
7447 #endif /* HAVE_EXECV */
7449 {"spawnv", posix_spawnv
, METH_VARARGS
, posix_spawnv__doc__
},
7450 {"spawnve", posix_spawnve
, METH_VARARGS
, posix_spawnve__doc__
},
7451 #if defined(PYOS_OS2)
7452 {"spawnvp", posix_spawnvp
, METH_VARARGS
, posix_spawnvp__doc__
},
7453 {"spawnvpe", posix_spawnvpe
, METH_VARARGS
, posix_spawnvpe__doc__
},
7454 #endif /* PYOS_OS2 */
7455 #endif /* HAVE_SPAWNV */
7457 {"fork1", posix_fork1
, METH_NOARGS
, posix_fork1__doc__
},
7458 #endif /* HAVE_FORK1 */
7460 {"fork", posix_fork
, METH_NOARGS
, posix_fork__doc__
},
7461 #endif /* HAVE_FORK */
7462 #if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
7463 {"openpty", posix_openpty
, METH_NOARGS
, posix_openpty__doc__
},
7464 #endif /* HAVE_OPENPTY || HAVE__GETPTY || HAVE_DEV_PTMX */
7466 {"forkpty", posix_forkpty
, METH_NOARGS
, posix_forkpty__doc__
},
7467 #endif /* HAVE_FORKPTY */
7469 {"getegid", posix_getegid
, METH_NOARGS
, posix_getegid__doc__
},
7470 #endif /* HAVE_GETEGID */
7472 {"geteuid", posix_geteuid
, METH_NOARGS
, posix_geteuid__doc__
},
7473 #endif /* HAVE_GETEUID */
7475 {"getgid", posix_getgid
, METH_NOARGS
, posix_getgid__doc__
},
7476 #endif /* HAVE_GETGID */
7477 #ifdef HAVE_GETGROUPS
7478 {"getgroups", posix_getgroups
, METH_NOARGS
, posix_getgroups__doc__
},
7480 {"getpid", posix_getpid
, METH_NOARGS
, posix_getpid__doc__
},
7482 {"getpgrp", posix_getpgrp
, METH_NOARGS
, posix_getpgrp__doc__
},
7483 #endif /* HAVE_GETPGRP */
7485 {"getppid", posix_getppid
, METH_NOARGS
, posix_getppid__doc__
},
7486 #endif /* HAVE_GETPPID */
7488 {"getuid", posix_getuid
, METH_NOARGS
, posix_getuid__doc__
},
7489 #endif /* HAVE_GETUID */
7490 #ifdef HAVE_GETLOGIN
7491 {"getlogin", posix_getlogin
, METH_NOARGS
, posix_getlogin__doc__
},
7494 {"kill", posix_kill
, METH_VARARGS
, posix_kill__doc__
},
7495 #endif /* HAVE_KILL */
7497 {"killpg", posix_killpg
, METH_VARARGS
, posix_killpg__doc__
},
7498 #endif /* HAVE_KILLPG */
7500 {"plock", posix_plock
, METH_VARARGS
, posix_plock__doc__
},
7501 #endif /* HAVE_PLOCK */
7503 {"popen", posix_popen
, METH_VARARGS
, posix_popen__doc__
},
7505 {"popen2", win32_popen2
, METH_VARARGS
},
7506 {"popen3", win32_popen3
, METH_VARARGS
},
7507 {"popen4", win32_popen4
, METH_VARARGS
},
7508 {"startfile", win32_startfile
, METH_VARARGS
, win32_startfile__doc__
},
7510 #if defined(PYOS_OS2) && defined(PYCC_GCC)
7511 {"popen2", os2emx_popen2
, METH_VARARGS
},
7512 {"popen3", os2emx_popen3
, METH_VARARGS
},
7513 {"popen4", os2emx_popen4
, METH_VARARGS
},
7516 #endif /* HAVE_POPEN */
7518 {"setuid", posix_setuid
, METH_VARARGS
, posix_setuid__doc__
},
7519 #endif /* HAVE_SETUID */
7521 {"seteuid", posix_seteuid
, METH_VARARGS
, posix_seteuid__doc__
},
7522 #endif /* HAVE_SETEUID */
7524 {"setegid", posix_setegid
, METH_VARARGS
, posix_setegid__doc__
},
7525 #endif /* HAVE_SETEGID */
7526 #ifdef HAVE_SETREUID
7527 {"setreuid", posix_setreuid
, METH_VARARGS
, posix_setreuid__doc__
},
7528 #endif /* HAVE_SETREUID */
7529 #ifdef HAVE_SETREGID
7530 {"setregid", posix_setregid
, METH_VARARGS
, posix_setregid__doc__
},
7531 #endif /* HAVE_SETREGID */
7533 {"setgid", posix_setgid
, METH_VARARGS
, posix_setgid__doc__
},
7534 #endif /* HAVE_SETGID */
7535 #ifdef HAVE_SETGROUPS
7536 {"setgroups", posix_setgroups
, METH_VARARGS
, posix_setgroups__doc__
},
7537 #endif /* HAVE_SETGROUPS */
7539 {"getpgid", posix_getpgid
, METH_VARARGS
, posix_getpgid__doc__
},
7540 #endif /* HAVE_GETPGID */
7542 {"setpgrp", posix_setpgrp
, METH_NOARGS
, posix_setpgrp__doc__
},
7543 #endif /* HAVE_SETPGRP */
7545 {"wait", posix_wait
, METH_NOARGS
, posix_wait__doc__
},
7546 #endif /* HAVE_WAIT */
7547 #if defined(HAVE_WAITPID) || defined(HAVE_CWAIT)
7548 {"waitpid", posix_waitpid
, METH_VARARGS
, posix_waitpid__doc__
},
7549 #endif /* HAVE_WAITPID */
7551 {"getsid", posix_getsid
, METH_VARARGS
, posix_getsid__doc__
},
7552 #endif /* HAVE_GETSID */
7554 {"setsid", posix_setsid
, METH_NOARGS
, posix_setsid__doc__
},
7555 #endif /* HAVE_SETSID */
7557 {"setpgid", posix_setpgid
, METH_VARARGS
, posix_setpgid__doc__
},
7558 #endif /* HAVE_SETPGID */
7559 #ifdef HAVE_TCGETPGRP
7560 {"tcgetpgrp", posix_tcgetpgrp
, METH_VARARGS
, posix_tcgetpgrp__doc__
},
7561 #endif /* HAVE_TCGETPGRP */
7562 #ifdef HAVE_TCSETPGRP
7563 {"tcsetpgrp", posix_tcsetpgrp
, METH_VARARGS
, posix_tcsetpgrp__doc__
},
7564 #endif /* HAVE_TCSETPGRP */
7565 {"open", posix_open
, METH_VARARGS
, posix_open__doc__
},
7566 {"close", posix_close
, METH_VARARGS
, posix_close__doc__
},
7567 {"dup", posix_dup
, METH_VARARGS
, posix_dup__doc__
},
7568 {"dup2", posix_dup2
, METH_VARARGS
, posix_dup2__doc__
},
7569 {"lseek", posix_lseek
, METH_VARARGS
, posix_lseek__doc__
},
7570 {"read", posix_read
, METH_VARARGS
, posix_read__doc__
},
7571 {"write", posix_write
, METH_VARARGS
, posix_write__doc__
},
7572 {"fstat", posix_fstat
, METH_VARARGS
, posix_fstat__doc__
},
7573 {"fdopen", posix_fdopen
, METH_VARARGS
, posix_fdopen__doc__
},
7574 {"isatty", posix_isatty
, METH_VARARGS
, posix_isatty__doc__
},
7576 {"pipe", posix_pipe
, METH_NOARGS
, posix_pipe__doc__
},
7579 {"mkfifo", posix_mkfifo
, METH_VARARGS
, posix_mkfifo__doc__
},
7581 #if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
7582 {"mknod", posix_mknod
, METH_VARARGS
, posix_mknod__doc__
},
7584 #ifdef HAVE_DEVICE_MACROS
7585 {"major", posix_major
, METH_VARARGS
, posix_major__doc__
},
7586 {"minor", posix_minor
, METH_VARARGS
, posix_minor__doc__
},
7587 {"makedev", posix_makedev
, METH_VARARGS
, posix_makedev__doc__
},
7589 #ifdef HAVE_FTRUNCATE
7590 {"ftruncate", posix_ftruncate
, METH_VARARGS
, posix_ftruncate__doc__
},
7593 {"putenv", posix_putenv
, METH_VARARGS
, posix_putenv__doc__
},
7595 #ifdef HAVE_UNSETENV
7596 {"unsetenv", posix_unsetenv
, METH_VARARGS
, posix_unsetenv__doc__
},
7598 #ifdef HAVE_STRERROR
7599 {"strerror", posix_strerror
, METH_VARARGS
, posix_strerror__doc__
},
7602 {"fchdir", posix_fchdir
, METH_O
, posix_fchdir__doc__
},
7605 {"fsync", posix_fsync
, METH_O
, posix_fsync__doc__
},
7607 #ifdef HAVE_FDATASYNC
7608 {"fdatasync", posix_fdatasync
, METH_O
, posix_fdatasync__doc__
},
7610 #ifdef HAVE_SYS_WAIT_H
7612 {"WCOREDUMP", posix_WCOREDUMP
, METH_VARARGS
, posix_WCOREDUMP__doc__
},
7613 #endif /* WCOREDUMP */
7615 {"WIFCONTINUED",posix_WIFCONTINUED
, METH_VARARGS
, posix_WIFCONTINUED__doc__
},
7616 #endif /* WIFCONTINUED */
7618 {"WIFSTOPPED", posix_WIFSTOPPED
, METH_VARARGS
, posix_WIFSTOPPED__doc__
},
7619 #endif /* WIFSTOPPED */
7621 {"WIFSIGNALED", posix_WIFSIGNALED
, METH_VARARGS
, posix_WIFSIGNALED__doc__
},
7622 #endif /* WIFSIGNALED */
7624 {"WIFEXITED", posix_WIFEXITED
, METH_VARARGS
, posix_WIFEXITED__doc__
},
7625 #endif /* WIFEXITED */
7627 {"WEXITSTATUS", posix_WEXITSTATUS
, METH_VARARGS
, posix_WEXITSTATUS__doc__
},
7628 #endif /* WEXITSTATUS */
7630 {"WTERMSIG", posix_WTERMSIG
, METH_VARARGS
, posix_WTERMSIG__doc__
},
7631 #endif /* WTERMSIG */
7633 {"WSTOPSIG", posix_WSTOPSIG
, METH_VARARGS
, posix_WSTOPSIG__doc__
},
7634 #endif /* WSTOPSIG */
7635 #endif /* HAVE_SYS_WAIT_H */
7636 #ifdef HAVE_FSTATVFS
7637 {"fstatvfs", posix_fstatvfs
, METH_VARARGS
, posix_fstatvfs__doc__
},
7640 {"statvfs", posix_statvfs
, METH_VARARGS
, posix_statvfs__doc__
},
7643 {"tmpfile", posix_tmpfile
, METH_NOARGS
, posix_tmpfile__doc__
},
7646 {"tempnam", posix_tempnam
, METH_VARARGS
, posix_tempnam__doc__
},
7649 {"tmpnam", posix_tmpnam
, METH_NOARGS
, posix_tmpnam__doc__
},
7652 {"confstr", posix_confstr
, METH_VARARGS
, posix_confstr__doc__
},
7655 {"sysconf", posix_sysconf
, METH_VARARGS
, posix_sysconf__doc__
},
7657 #ifdef HAVE_FPATHCONF
7658 {"fpathconf", posix_fpathconf
, METH_VARARGS
, posix_fpathconf__doc__
},
7660 #ifdef HAVE_PATHCONF
7661 {"pathconf", posix_pathconf
, METH_VARARGS
, posix_pathconf__doc__
},
7663 {"abort", posix_abort
, METH_NOARGS
, posix_abort__doc__
},
7665 {"_getfullpathname", posix__getfullpathname
, METH_VARARGS
, NULL
},
7667 #ifdef HAVE_GETLOADAVG
7668 {"getloadavg", posix_getloadavg
, METH_NOARGS
, posix_getloadavg__doc__
},
7671 {"urandom", win32_urandom
, METH_VARARGS
, win32_urandom__doc__
},
7673 {NULL
, NULL
} /* Sentinel */
7678 ins(PyObject
*module
, char *symbol
, long value
)
7680 return PyModule_AddIntConstant(module
, symbol
, value
);
7683 #if defined(PYOS_OS2)
7684 /* Insert Platform-Specific Constant Values (Strings & Numbers) of Common Use */
7685 static int insertvalues(PyObject
*module
)
7688 ULONG values
[QSV_MAX
+1];
7692 Py_BEGIN_ALLOW_THREADS
7693 rc
= DosQuerySysInfo(1L, QSV_MAX
, &values
[1], sizeof(ULONG
) * QSV_MAX
);
7694 Py_END_ALLOW_THREADS
7696 if (rc
!= NO_ERROR
) {
7701 if (ins(module
, "meminstalled", values
[QSV_TOTPHYSMEM
])) return -1;
7702 if (ins(module
, "memkernel", values
[QSV_TOTRESMEM
])) return -1;
7703 if (ins(module
, "memvirtual", values
[QSV_TOTAVAILMEM
])) return -1;
7704 if (ins(module
, "maxpathlen", values
[QSV_MAX_PATH_LENGTH
])) return -1;
7705 if (ins(module
, "maxnamelen", values
[QSV_MAX_COMP_LENGTH
])) return -1;
7706 if (ins(module
, "revision", values
[QSV_VERSION_REVISION
])) return -1;
7707 if (ins(module
, "timeslice", values
[QSV_MIN_SLICE
])) return -1;
7709 switch (values
[QSV_VERSION_MINOR
]) {
7710 case 0: ver
= "2.00"; break;
7711 case 10: ver
= "2.10"; break;
7712 case 11: ver
= "2.11"; break;
7713 case 30: ver
= "3.00"; break;
7714 case 40: ver
= "4.00"; break;
7715 case 50: ver
= "5.00"; break;
7717 PyOS_snprintf(tmp
, sizeof(tmp
),
7718 "%d-%d", values
[QSV_VERSION_MAJOR
],
7719 values
[QSV_VERSION_MINOR
]);
7723 /* Add Indicator of the Version of the Operating System */
7724 if (PyModule_AddStringConstant(module
, "version", tmp
) < 0)
7727 /* Add Indicator of Which Drive was Used to Boot the System */
7728 tmp
[0] = 'A' + values
[QSV_BOOT_DRIVE
] - 1;
7732 return PyModule_AddStringConstant(module
, "bootdrive", tmp
);
7737 all_ins(PyObject
*d
)
7740 if (ins(d
, "F_OK", (long)F_OK
)) return -1;
7743 if (ins(d
, "R_OK", (long)R_OK
)) return -1;
7746 if (ins(d
, "W_OK", (long)W_OK
)) return -1;
7749 if (ins(d
, "X_OK", (long)X_OK
)) return -1;
7752 if (ins(d
, "NGROUPS_MAX", (long)NGROUPS_MAX
)) return -1;
7755 if (ins(d
, "TMP_MAX", (long)TMP_MAX
)) return -1;
7758 if (ins(d
, "WCONTINUED", (long)WCONTINUED
)) return -1;
7761 if (ins(d
, "WNOHANG", (long)WNOHANG
)) return -1;
7764 if (ins(d
, "WUNTRACED", (long)WUNTRACED
)) return -1;
7767 if (ins(d
, "O_RDONLY", (long)O_RDONLY
)) return -1;
7770 if (ins(d
, "O_WRONLY", (long)O_WRONLY
)) return -1;
7773 if (ins(d
, "O_RDWR", (long)O_RDWR
)) return -1;
7776 if (ins(d
, "O_NDELAY", (long)O_NDELAY
)) return -1;
7779 if (ins(d
, "O_NONBLOCK", (long)O_NONBLOCK
)) return -1;
7782 if (ins(d
, "O_APPEND", (long)O_APPEND
)) return -1;
7785 if (ins(d
, "O_DSYNC", (long)O_DSYNC
)) return -1;
7788 if (ins(d
, "O_RSYNC", (long)O_RSYNC
)) return -1;
7791 if (ins(d
, "O_SYNC", (long)O_SYNC
)) return -1;
7794 if (ins(d
, "O_NOCTTY", (long)O_NOCTTY
)) return -1;
7797 if (ins(d
, "O_CREAT", (long)O_CREAT
)) return -1;
7800 if (ins(d
, "O_EXCL", (long)O_EXCL
)) return -1;
7803 if (ins(d
, "O_TRUNC", (long)O_TRUNC
)) return -1;
7806 if (ins(d
, "O_BINARY", (long)O_BINARY
)) return -1;
7809 if (ins(d
, "O_TEXT", (long)O_TEXT
)) return -1;
7812 if (ins(d
, "O_LARGEFILE", (long)O_LARGEFILE
)) return -1;
7815 if (ins(d
, "O_SHLOCK", (long)O_SHLOCK
)) return -1;
7818 if (ins(d
, "O_EXLOCK", (long)O_EXLOCK
)) return -1;
7823 /* Don't inherit in child processes. */
7824 if (ins(d
, "O_NOINHERIT", (long)O_NOINHERIT
)) return -1;
7826 #ifdef _O_SHORT_LIVED
7827 /* Optimize for short life (keep in memory). */
7828 /* MS forgot to define this one with a non-underscore form too. */
7829 if (ins(d
, "O_SHORT_LIVED", (long)_O_SHORT_LIVED
)) return -1;
7832 /* Automatically delete when last handle is closed. */
7833 if (ins(d
, "O_TEMPORARY", (long)O_TEMPORARY
)) return -1;
7836 /* Optimize for random access. */
7837 if (ins(d
, "O_RANDOM", (long)O_RANDOM
)) return -1;
7840 /* Optimize for sequential access. */
7841 if (ins(d
, "O_SEQUENTIAL", (long)O_SEQUENTIAL
)) return -1;
7844 /* GNU extensions. */
7846 /* Direct disk access. */
7847 if (ins(d
, "O_DIRECT", (long)O_DIRECT
)) return -1;
7850 /* Must be a directory. */
7851 if (ins(d
, "O_DIRECTORY", (long)O_DIRECTORY
)) return -1;
7854 /* Do not follow links. */
7855 if (ins(d
, "O_NOFOLLOW", (long)O_NOFOLLOW
)) return -1;
7858 /* These come from sysexits.h */
7860 if (ins(d
, "EX_OK", (long)EX_OK
)) return -1;
7863 if (ins(d
, "EX_USAGE", (long)EX_USAGE
)) return -1;
7864 #endif /* EX_USAGE */
7866 if (ins(d
, "EX_DATAERR", (long)EX_DATAERR
)) return -1;
7867 #endif /* EX_DATAERR */
7869 if (ins(d
, "EX_NOINPUT", (long)EX_NOINPUT
)) return -1;
7870 #endif /* EX_NOINPUT */
7872 if (ins(d
, "EX_NOUSER", (long)EX_NOUSER
)) return -1;
7873 #endif /* EX_NOUSER */
7875 if (ins(d
, "EX_NOHOST", (long)EX_NOHOST
)) return -1;
7876 #endif /* EX_NOHOST */
7877 #ifdef EX_UNAVAILABLE
7878 if (ins(d
, "EX_UNAVAILABLE", (long)EX_UNAVAILABLE
)) return -1;
7879 #endif /* EX_UNAVAILABLE */
7881 if (ins(d
, "EX_SOFTWARE", (long)EX_SOFTWARE
)) return -1;
7882 #endif /* EX_SOFTWARE */
7884 if (ins(d
, "EX_OSERR", (long)EX_OSERR
)) return -1;
7885 #endif /* EX_OSERR */
7887 if (ins(d
, "EX_OSFILE", (long)EX_OSFILE
)) return -1;
7888 #endif /* EX_OSFILE */
7890 if (ins(d
, "EX_CANTCREAT", (long)EX_CANTCREAT
)) return -1;
7891 #endif /* EX_CANTCREAT */
7893 if (ins(d
, "EX_IOERR", (long)EX_IOERR
)) return -1;
7894 #endif /* EX_IOERR */
7896 if (ins(d
, "EX_TEMPFAIL", (long)EX_TEMPFAIL
)) return -1;
7897 #endif /* EX_TEMPFAIL */
7899 if (ins(d
, "EX_PROTOCOL", (long)EX_PROTOCOL
)) return -1;
7900 #endif /* EX_PROTOCOL */
7902 if (ins(d
, "EX_NOPERM", (long)EX_NOPERM
)) return -1;
7903 #endif /* EX_NOPERM */
7905 if (ins(d
, "EX_CONFIG", (long)EX_CONFIG
)) return -1;
7906 #endif /* EX_CONFIG */
7908 if (ins(d
, "EX_NOTFOUND", (long)EX_NOTFOUND
)) return -1;
7909 #endif /* EX_NOTFOUND */
7912 #if defined(PYOS_OS2) && defined(PYCC_GCC)
7913 if (ins(d
, "P_WAIT", (long)P_WAIT
)) return -1;
7914 if (ins(d
, "P_NOWAIT", (long)P_NOWAIT
)) return -1;
7915 if (ins(d
, "P_OVERLAY", (long)P_OVERLAY
)) return -1;
7916 if (ins(d
, "P_DEBUG", (long)P_DEBUG
)) return -1;
7917 if (ins(d
, "P_SESSION", (long)P_SESSION
)) return -1;
7918 if (ins(d
, "P_DETACH", (long)P_DETACH
)) return -1;
7919 if (ins(d
, "P_PM", (long)P_PM
)) return -1;
7920 if (ins(d
, "P_DEFAULT", (long)P_DEFAULT
)) return -1;
7921 if (ins(d
, "P_MINIMIZE", (long)P_MINIMIZE
)) return -1;
7922 if (ins(d
, "P_MAXIMIZE", (long)P_MAXIMIZE
)) return -1;
7923 if (ins(d
, "P_FULLSCREEN", (long)P_FULLSCREEN
)) return -1;
7924 if (ins(d
, "P_WINDOWED", (long)P_WINDOWED
)) return -1;
7925 if (ins(d
, "P_FOREGROUND", (long)P_FOREGROUND
)) return -1;
7926 if (ins(d
, "P_BACKGROUND", (long)P_BACKGROUND
)) return -1;
7927 if (ins(d
, "P_NOCLOSE", (long)P_NOCLOSE
)) return -1;
7928 if (ins(d
, "P_NOSESSION", (long)P_NOSESSION
)) return -1;
7929 if (ins(d
, "P_QUOTE", (long)P_QUOTE
)) return -1;
7930 if (ins(d
, "P_TILDE", (long)P_TILDE
)) return -1;
7931 if (ins(d
, "P_UNRELATED", (long)P_UNRELATED
)) return -1;
7932 if (ins(d
, "P_DEBUGDESC", (long)P_DEBUGDESC
)) return -1;
7934 if (ins(d
, "P_WAIT", (long)_P_WAIT
)) return -1;
7935 if (ins(d
, "P_NOWAIT", (long)_P_NOWAIT
)) return -1;
7936 if (ins(d
, "P_OVERLAY", (long)_OLD_P_OVERLAY
)) return -1;
7937 if (ins(d
, "P_NOWAITO", (long)_P_NOWAITO
)) return -1;
7938 if (ins(d
, "P_DETACH", (long)_P_DETACH
)) return -1;
7942 #if defined(PYOS_OS2)
7943 if (insertvalues(d
)) return -1;
7949 #if (defined(_MSC_VER) || defined(__WATCOMC__) || defined(__BORLANDC__)) && !defined(__QNX__)
7950 #define INITFUNC initnt
7951 #define MODNAME "nt"
7953 #elif defined(PYOS_OS2)
7954 #define INITFUNC initos2
7955 #define MODNAME "os2"
7958 #define INITFUNC initposix
7959 #define MODNAME "posix"
7967 m
= Py_InitModule3(MODNAME
,
7971 /* Initialize environ dictionary */
7972 v
= convertenviron();
7974 if (v
== NULL
|| PyModule_AddObject(m
, "environ", v
) != 0)
7981 if (setup_confname_tables(m
))
7984 Py_INCREF(PyExc_OSError
);
7985 PyModule_AddObject(m
, "error", PyExc_OSError
);
7988 if (posix_putenv_garbage
== NULL
)
7989 posix_putenv_garbage
= PyDict_New();
7992 stat_result_desc
.name
= MODNAME
".stat_result";
7993 stat_result_desc
.fields
[7].name
= PyStructSequence_UnnamedField
;
7994 stat_result_desc
.fields
[8].name
= PyStructSequence_UnnamedField
;
7995 stat_result_desc
.fields
[9].name
= PyStructSequence_UnnamedField
;
7996 PyStructSequence_InitType(&StatResultType
, &stat_result_desc
);
7997 structseq_new
= StatResultType
.tp_new
;
7998 StatResultType
.tp_new
= statresult_new
;
7999 Py_INCREF((PyObject
*) &StatResultType
);
8000 PyModule_AddObject(m
, "stat_result", (PyObject
*) &StatResultType
);
8002 statvfs_result_desc
.name
= MODNAME
".statvfs_result";
8003 PyStructSequence_InitType(&StatVFSResultType
, &statvfs_result_desc
);
8004 Py_INCREF((PyObject
*) &StatVFSResultType
);
8005 PyModule_AddObject(m
, "statvfs_result",
8006 (PyObject
*) &StatVFSResultType
);