blob: 473fefaa344735c1dd6ebe8bd065656e8bf22f61 [file] [log] [blame]
Guido van Rossumf70e43a1991-02-19 12:39:46 +00001
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002/* POSIX module implementation */
3
Jesus Ceaab70e2a2012-10-05 01:48:08 +02004/* This file is also used for Windows NT/MS-Win. In that case the
5 module actually calls itself 'nt', not 'posix', and a few
Andrew MacIntyre6c73af22002-03-03 03:07:07 +00006 functions are either unimplemented or implemented differently. The source
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00007 assumes that for Windows NT, the macro 'MS_WINDOWS' is defined independent
Guido van Rossumad0ee831995-03-01 10:34:45 +00008 of the compiler used. Different compilers define their own feature
Jesus Ceaab70e2a2012-10-05 01:48:08 +02009 test macro, e.g. '__BORLANDC__' or '_MSC_VER'. */
Guido van Rossumad0ee831995-03-01 10:34:45 +000010
Larry Hastings31826802013-10-19 00:09:25 -070011
12
Thomas Wouters477c8d52006-05-27 19:21:47 +000013#ifdef __APPLE__
14 /*
Victor Stinner8c62be82010-05-06 00:08:46 +000015 * Step 1 of support for weak-linking a number of symbols existing on
Thomas Wouters477c8d52006-05-27 19:21:47 +000016 * OSX 10.4 and later, see the comment in the #ifdef __APPLE__ block
17 * at the end of this file for more information.
18 */
19# pragma weak lchown
20# pragma weak statvfs
21# pragma weak fstatvfs
22
23#endif /* __APPLE__ */
24
Thomas Wouters68bc4f92006-03-01 01:05:10 +000025#define PY_SSIZE_T_CLEAN
26
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000027#include "Python.h"
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020028#ifndef MS_WINDOWS
29#include "posixmodule.h"
Tim Golden0321cf22014-05-05 19:46:17 +010030#else
31#include "winreparse.h"
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020032#endif
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000033
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000034#ifdef __cplusplus
35extern "C" {
36#endif
37
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000038PyDoc_STRVAR(posix__doc__,
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000039"This module provides access to operating system functionality that is\n\
40standardized by the C Standard and the POSIX standard (a thinly\n\
41disguised Unix interface). Refer to the library manual and\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000042corresponding Unix manual entries for more information on calls.");
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000043
Martin v. Löwis0073f2e2002-11-21 23:52:35 +000044
Ross Lagerwall4d076da2011-03-18 06:56:53 +020045#ifdef HAVE_SYS_UIO_H
46#include <sys/uio.h>
47#endif
48
Thomas Wouters0e3f5912006-08-11 14:57:12 +000049#ifdef HAVE_SYS_TYPES_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000050#include <sys/types.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000051#endif /* HAVE_SYS_TYPES_H */
52
53#ifdef HAVE_SYS_STAT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000054#include <sys/stat.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000055#endif /* HAVE_SYS_STAT_H */
Guido van Rossuma6535fd2001-10-18 19:44:10 +000056
Guido van Rossum36bc6801995-06-14 22:54:23 +000057#ifdef HAVE_SYS_WAIT_H
Victor Stinner8c62be82010-05-06 00:08:46 +000058#include <sys/wait.h> /* For WNOHANG */
Guido van Rossum36bc6801995-06-14 22:54:23 +000059#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +000060
Thomas Wouters0e3f5912006-08-11 14:57:12 +000061#ifdef HAVE_SIGNAL_H
Guido van Rossuma376cc51996-12-05 23:43:35 +000062#include <signal.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000063#endif
Guido van Rossuma376cc51996-12-05 23:43:35 +000064
Guido van Rossumb6775db1994-08-01 11:34:53 +000065#ifdef HAVE_FCNTL_H
66#include <fcntl.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000067#endif /* HAVE_FCNTL_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000068
Guido van Rossuma6535fd2001-10-18 19:44:10 +000069#ifdef HAVE_GRP_H
70#include <grp.h>
71#endif
72
Barry Warsaw5676bd12003-01-07 20:57:09 +000073#ifdef HAVE_SYSEXITS_H
74#include <sysexits.h>
75#endif /* HAVE_SYSEXITS_H */
76
Anthony Baxter8a560de2004-10-13 15:30:56 +000077#ifdef HAVE_SYS_LOADAVG_H
78#include <sys/loadavg.h>
79#endif
80
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000081#ifdef HAVE_LANGINFO_H
82#include <langinfo.h>
83#endif
84
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000085#ifdef HAVE_SYS_SENDFILE_H
86#include <sys/sendfile.h>
87#endif
88
Benjamin Peterson94b580d2011-08-02 17:30:04 -050089#ifdef HAVE_SCHED_H
90#include <sched.h>
91#endif
92
Benjamin Peterson2dbda072012-03-16 10:12:55 -050093#if !defined(CPU_ALLOC) && defined(HAVE_SCHED_SETAFFINITY)
Benjamin Peterson7b51b8d2012-03-14 22:28:25 -050094#undef HAVE_SCHED_SETAFFINITY
95#endif
96
doko@ubuntu.com4a173bc2014-04-17 19:47:16 +020097#if defined(HAVE_SYS_XATTR_H) && defined(__GLIBC__) && !defined(__FreeBSD_kernel__) && !defined(__GNU__)
Benjamin Peterson9428d532011-09-14 11:45:52 -040098#define USE_XATTRS
99#endif
100
101#ifdef USE_XATTRS
Benjamin Petersonb77fe172011-09-13 17:20:47 -0400102#include <sys/xattr.h>
Benjamin Peterson799bd802011-08-31 22:15:17 -0400103#endif
104
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000105#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
106#ifdef HAVE_SYS_SOCKET_H
107#include <sys/socket.h>
108#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000109#endif
110
Victor Stinner8b905bd2011-10-25 13:34:04 +0200111#ifdef HAVE_DLFCN_H
112#include <dlfcn.h>
113#endif
114
Charles-Francois Natali44feda32013-05-20 14:40:46 +0200115#ifdef __hpux
116#include <sys/mpctl.h>
117#endif
118
119#if defined(__DragonFly__) || \
120 defined(__OpenBSD__) || \
121 defined(__FreeBSD__) || \
122 defined(__NetBSD__) || \
123 defined(__APPLE__)
124#include <sys/sysctl.h>
125#endif
126
Antoine Pitroubcf2b592012-02-08 23:28:36 +0100127#if defined(MS_WINDOWS)
128# define TERMSIZE_USE_CONIO
129#elif defined(HAVE_SYS_IOCTL_H)
130# include <sys/ioctl.h>
131# if defined(HAVE_TERMIOS_H)
132# include <termios.h>
133# endif
134# if defined(TIOCGWINSZ)
135# define TERMSIZE_USE_IOCTL
136# endif
137#endif /* MS_WINDOWS */
138
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000139/* Various compilers have only certain posix functions */
Martin v. Löwis4f1cd8b2001-07-26 13:41:06 +0000140/* XXX Gosh I wish these were all moved into pyconfig.h */
Victor Stinner8c62be82010-05-06 00:08:46 +0000141#if defined(__WATCOMC__) && !defined(__QNX__) /* Watcom compiler */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000142#define HAVE_OPENDIR 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000143#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000144#include <process.h>
145#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000146#ifdef __BORLANDC__ /* Borland compiler */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000147#define HAVE_EXECV 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000148#define HAVE_OPENDIR 1
149#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000150#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000151#define HAVE_WAIT 1
152#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000153#ifdef _MSC_VER /* Microsoft compiler */
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +0000154#define HAVE_GETPPID 1
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000155#define HAVE_GETLOGIN 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000156#define HAVE_SPAWNV 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000157#define HAVE_EXECV 1
158#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000159#define HAVE_SYSTEM 1
160#define HAVE_CWAIT 1
161#define HAVE_FSYNC 1
Tim Peters11b23062003-04-23 02:39:17 +0000162#define fsync _commit
Andrew MacIntyre6c73af22002-03-03 03:07:07 +0000163#else
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000164/* Unix functions that the configure script doesn't check for */
165#define HAVE_EXECV 1
166#define HAVE_FORK 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000167#if defined(__USLC__) && defined(__SCO_VERSION__) /* SCO UDK Compiler */
Guido van Rossum2242f2f2001-04-11 20:58:20 +0000168#define HAVE_FORK1 1
169#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000170#define HAVE_GETEGID 1
171#define HAVE_GETEUID 1
172#define HAVE_GETGID 1
173#define HAVE_GETPPID 1
174#define HAVE_GETUID 1
175#define HAVE_KILL 1
176#define HAVE_OPENDIR 1
177#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000178#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000179#define HAVE_WAIT 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000180#define HAVE_TTYNAME 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000181#endif /* _MSC_VER */
182#endif /* __BORLANDC__ */
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000183#endif /* ! __WATCOMC__ || __QNX__ */
Guido van Rossumad0ee831995-03-01 10:34:45 +0000184
Victor Stinnera2f7c002012-02-08 03:36:25 +0100185
Larry Hastings61272b72014-01-07 12:41:53 -0800186/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +1000187# one of the few times we lie about this name!
Larry Hastings44e2eaa2013-11-23 15:37:55 -0800188module os
Larry Hastings61272b72014-01-07 12:41:53 -0800189[clinic start generated code]*/
Larry Hastings2f936352014-08-05 14:04:04 +1000190/*[clinic end generated code: output=da39a3ee5e6b4b0d input=94a0f0f978acae17]*/
Victor Stinnera2f7c002012-02-08 03:36:25 +0100191
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000192#ifndef _MSC_VER
Guido van Rossum36bc6801995-06-14 22:54:23 +0000193
Martin v. Löwis8eb92a02002-09-19 08:03:21 +0000194#if defined(__sgi)&&_COMPILER_VERSION>=700
195/* declare ctermid_r if compiling with MIPSPro 7.x in ANSI C mode
196 (default) */
197extern char *ctermid_r(char *);
198#endif
199
Thomas Wouters1e0c2f42000-07-24 16:06:23 +0000200#ifndef HAVE_UNISTD_H
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000201#if defined(PYCC_VACPP)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000202extern int mkdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000203#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000204#if ( defined(__WATCOMC__) || defined(_MSC_VER) ) && !defined(__QNX__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000205extern int mkdir(const char *);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000206#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000207extern int mkdir(const char *, mode_t);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000208#endif
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000209#endif
210#if defined(__IBMC__) || defined(__IBMCPP__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000211extern int chdir(char *);
212extern int rmdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000213#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000214extern int chdir(const char *);
215extern int rmdir(const char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000216#endif
Tim Peters58e0a8c2001-05-14 22:32:33 +0000217#ifdef __BORLANDC__
218extern int chmod(const char *, int);
219#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000220extern int chmod(const char *, mode_t);
Tim Peters58e0a8c2001-05-14 22:32:33 +0000221#endif
Christian Heimes4e30a842007-11-30 22:12:06 +0000222/*#ifdef HAVE_FCHMOD
223extern int fchmod(int, mode_t);
224#endif*/
225/*#ifdef HAVE_LCHMOD
226extern int lchmod(const char *, mode_t);
227#endif*/
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000228extern int chown(const char *, uid_t, gid_t);
229extern char *getcwd(char *, int);
230extern char *strerror(int);
231extern int link(const char *, const char *);
232extern int rename(const char *, const char *);
233extern int stat(const char *, struct stat *);
234extern int unlink(const char *);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000235#ifdef HAVE_SYMLINK
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000236extern int symlink(const char *, const char *);
Guido van Rossuma38a5031995-02-17 15:11:36 +0000237#endif /* HAVE_SYMLINK */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000238#ifdef HAVE_LSTAT
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000239extern int lstat(const char *, struct stat *);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000240#endif /* HAVE_LSTAT */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000241#endif /* !HAVE_UNISTD_H */
Guido van Rossum36bc6801995-06-14 22:54:23 +0000242
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000243#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000244
Guido van Rossumb6775db1994-08-01 11:34:53 +0000245#ifdef HAVE_UTIME_H
246#include <utime.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000247#endif /* HAVE_UTIME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000248
Guido van Rossum14ed0b21994-09-29 09:50:09 +0000249#ifdef HAVE_SYS_UTIME_H
250#include <sys/utime.h>
251#define HAVE_UTIME_H /* pretend we do for the rest of this file */
252#endif /* HAVE_SYS_UTIME_H */
253
Guido van Rossumb6775db1994-08-01 11:34:53 +0000254#ifdef HAVE_SYS_TIMES_H
255#include <sys/times.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000256#endif /* HAVE_SYS_TIMES_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000257
258#ifdef HAVE_SYS_PARAM_H
259#include <sys/param.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000260#endif /* HAVE_SYS_PARAM_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000261
262#ifdef HAVE_SYS_UTSNAME_H
263#include <sys/utsname.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000264#endif /* HAVE_SYS_UTSNAME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000265
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000266#ifdef HAVE_DIRENT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000267#include <dirent.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000268#define NAMLEN(dirent) strlen((dirent)->d_name)
269#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000270#if defined(__WATCOMC__) && !defined(__QNX__)
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000271#include <direct.h>
272#define NAMLEN(dirent) strlen((dirent)->d_name)
273#else
Guido van Rossumb6775db1994-08-01 11:34:53 +0000274#define dirent direct
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000275#define NAMLEN(dirent) (dirent)->d_namlen
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000276#endif
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000277#ifdef HAVE_SYS_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000278#include <sys/ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000279#endif
280#ifdef HAVE_SYS_DIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000281#include <sys/dir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000282#endif
283#ifdef HAVE_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000284#include <ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000285#endif
286#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +0000287
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000288#ifdef _MSC_VER
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000289#ifdef HAVE_DIRECT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000290#include <direct.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000291#endif
292#ifdef HAVE_IO_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000293#include <io.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000294#endif
295#ifdef HAVE_PROCESS_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000296#include <process.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000297#endif
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000298#ifndef VOLUME_NAME_DOS
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000299#define VOLUME_NAME_DOS 0x0
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000300#endif
301#ifndef VOLUME_NAME_NT
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000302#define VOLUME_NAME_NT 0x2
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000303#endif
304#ifndef IO_REPARSE_TAG_SYMLINK
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000305#define IO_REPARSE_TAG_SYMLINK (0xA000000CL)
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000306#endif
Tim Golden0321cf22014-05-05 19:46:17 +0100307#ifndef IO_REPARSE_TAG_MOUNT_POINT
308#define IO_REPARSE_TAG_MOUNT_POINT (0xA0000003L)
309#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000310#include "osdefs.h"
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +0000311#include <malloc.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +0000312#include <windows.h>
Victor Stinner8c62be82010-05-06 00:08:46 +0000313#include <shellapi.h> /* for ShellExecute() */
Brian Curtine8e4b3b2010-09-23 20:04:14 +0000314#include <lmcons.h> /* for UNLEN */
Brian Curtin52173d42010-12-02 18:29:18 +0000315#ifdef SE_CREATE_SYMBOLIC_LINK_NAME /* Available starting with Vista */
316#define HAVE_SYMLINK
Brian Curtin3b4499c2010-12-28 14:31:47 +0000317static int win32_can_symlink = 0;
Brian Curtin52173d42010-12-02 18:29:18 +0000318#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000319#endif /* _MSC_VER */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000320
Tim Petersbc2e10e2002-03-03 23:17:02 +0000321#ifndef MAXPATHLEN
Thomas Wouters477c8d52006-05-27 19:21:47 +0000322#if defined(PATH_MAX) && PATH_MAX > 1024
323#define MAXPATHLEN PATH_MAX
324#else
Tim Petersbc2e10e2002-03-03 23:17:02 +0000325#define MAXPATHLEN 1024
Thomas Wouters477c8d52006-05-27 19:21:47 +0000326#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000327#endif /* MAXPATHLEN */
328
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000329#ifdef UNION_WAIT
330/* Emulate some macros on systems that have a union instead of macros */
331
332#ifndef WIFEXITED
333#define WIFEXITED(u_wait) (!(u_wait).w_termsig && !(u_wait).w_coredump)
334#endif
335
336#ifndef WEXITSTATUS
337#define WEXITSTATUS(u_wait) (WIFEXITED(u_wait)?((u_wait).w_retcode):-1)
338#endif
339
340#ifndef WTERMSIG
341#define WTERMSIG(u_wait) ((u_wait).w_termsig)
342#endif
343
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000344#define WAIT_TYPE union wait
345#define WAIT_STATUS_INT(s) (s.w_status)
346
347#else /* !UNION_WAIT */
348#define WAIT_TYPE int
349#define WAIT_STATUS_INT(s) (s)
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000350#endif /* UNION_WAIT */
351
Greg Wardb48bc172000-03-01 21:51:56 +0000352/* Don't use the "_r" form if we don't need it (also, won't have a
353 prototype for it, at least on Solaris -- maybe others as well?). */
354#if defined(HAVE_CTERMID_R) && defined(WITH_THREAD)
355#define USE_CTERMID_R
356#endif
357
Fred Drake699f3522000-06-29 21:12:41 +0000358/* choose the appropriate stat and fstat functions and return structs */
Guido van Rossum64529cd2000-06-30 22:45:12 +0000359#undef STAT
Antoine Pitroue47e0932011-01-19 15:21:35 +0000360#undef FSTAT
361#undef STRUCT_STAT
Victor Stinner14b9b112013-06-25 00:37:25 +0200362#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +0000363# define STAT win32_stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700364# define LSTAT win32_lstat
Victor Stinner8c62be82010-05-06 00:08:46 +0000365# define FSTAT win32_fstat
366# define STRUCT_STAT struct win32_stat
Fred Drake699f3522000-06-29 21:12:41 +0000367#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000368# define STAT stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700369# define LSTAT lstat
Victor Stinner8c62be82010-05-06 00:08:46 +0000370# define FSTAT fstat
371# define STRUCT_STAT struct stat
Fred Drake699f3522000-06-29 21:12:41 +0000372#endif
373
Tim Peters11b23062003-04-23 02:39:17 +0000374#if defined(MAJOR_IN_MKDEV)
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000375#include <sys/mkdev.h>
376#else
377#if defined(MAJOR_IN_SYSMACROS)
378#include <sys/sysmacros.h>
379#endif
Neal Norwitz3d949422002-04-20 13:46:43 +0000380#if defined(HAVE_MKNOD) && defined(HAVE_SYS_MKDEV_H)
381#include <sys/mkdev.h>
382#endif
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000383#endif
Fred Drake699f3522000-06-29 21:12:41 +0000384
Victor Stinner6edddfa2013-11-24 19:22:57 +0100385#define DWORD_MAX 4294967295U
386
Larry Hastings9cf065c2012-06-22 16:30:09 -0700387
388#ifdef MS_WINDOWS
389static int
390win32_warn_bytes_api()
391{
392 return PyErr_WarnEx(PyExc_DeprecationWarning,
393 "The Windows bytes API has been deprecated, "
394 "use Unicode filenames instead",
395 1);
396}
397#endif
398
399
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200400#ifndef MS_WINDOWS
401PyObject *
402_PyLong_FromUid(uid_t uid)
403{
404 if (uid == (uid_t)-1)
405 return PyLong_FromLong(-1);
406 return PyLong_FromUnsignedLong(uid);
407}
408
409PyObject *
410_PyLong_FromGid(gid_t gid)
411{
412 if (gid == (gid_t)-1)
413 return PyLong_FromLong(-1);
414 return PyLong_FromUnsignedLong(gid);
415}
416
417int
418_Py_Uid_Converter(PyObject *obj, void *p)
419{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700420 uid_t uid;
421 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200422 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200423 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700424 unsigned long uresult;
425
426 index = PyNumber_Index(obj);
427 if (index == NULL) {
428 PyErr_Format(PyExc_TypeError,
429 "uid should be integer, not %.200s",
430 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200431 return 0;
432 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700433
434 /*
435 * Handling uid_t is complicated for two reasons:
436 * * Although uid_t is (always?) unsigned, it still
437 * accepts -1.
438 * * We don't know its size in advance--it may be
439 * bigger than an int, or it may be smaller than
440 * a long.
441 *
442 * So a bit of defensive programming is in order.
443 * Start with interpreting the value passed
444 * in as a signed long and see if it works.
445 */
446
447 result = PyLong_AsLongAndOverflow(index, &overflow);
448
449 if (!overflow) {
450 uid = (uid_t)result;
451
452 if (result == -1) {
453 if (PyErr_Occurred())
454 goto fail;
455 /* It's a legitimate -1, we're done. */
456 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200457 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700458
459 /* Any other negative number is disallowed. */
460 if (result < 0)
461 goto underflow;
462
463 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200464 if (sizeof(uid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700465 (long)uid != result)
466 goto underflow;
467 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200468 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700469
470 if (overflow < 0)
471 goto underflow;
472
473 /*
474 * Okay, the value overflowed a signed long. If it
475 * fits in an *unsigned* long, it may still be okay,
476 * as uid_t may be unsigned long on this platform.
477 */
478 uresult = PyLong_AsUnsignedLong(index);
479 if (PyErr_Occurred()) {
480 if (PyErr_ExceptionMatches(PyExc_OverflowError))
481 goto overflow;
482 goto fail;
483 }
484
485 uid = (uid_t)uresult;
486
487 /*
488 * If uid == (uid_t)-1, the user actually passed in ULONG_MAX,
489 * but this value would get interpreted as (uid_t)-1 by chown
490 * and its siblings. That's not what the user meant! So we
491 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100492 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700493 */
494 if (uid == (uid_t)-1)
495 goto overflow;
496
497 /* Ensure the value wasn't truncated. */
498 if (sizeof(uid_t) < sizeof(long) &&
499 (unsigned long)uid != uresult)
500 goto overflow;
501 /* fallthrough */
502
503success:
504 Py_DECREF(index);
505 *(uid_t *)p = uid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200506 return 1;
507
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700508underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200509 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700510 "uid is less than minimum");
511 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200512
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700513overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200514 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700515 "uid is greater than maximum");
516 /* fallthrough */
517
518fail:
519 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200520 return 0;
521}
522
523int
524_Py_Gid_Converter(PyObject *obj, void *p)
525{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700526 gid_t gid;
527 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200528 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200529 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700530 unsigned long uresult;
531
532 index = PyNumber_Index(obj);
533 if (index == NULL) {
534 PyErr_Format(PyExc_TypeError,
535 "gid should be integer, not %.200s",
536 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200537 return 0;
538 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700539
540 /*
541 * Handling gid_t is complicated for two reasons:
542 * * Although gid_t is (always?) unsigned, it still
543 * accepts -1.
544 * * We don't know its size in advance--it may be
545 * bigger than an int, or it may be smaller than
546 * a long.
547 *
548 * So a bit of defensive programming is in order.
549 * Start with interpreting the value passed
550 * in as a signed long and see if it works.
551 */
552
553 result = PyLong_AsLongAndOverflow(index, &overflow);
554
555 if (!overflow) {
556 gid = (gid_t)result;
557
558 if (result == -1) {
559 if (PyErr_Occurred())
560 goto fail;
561 /* It's a legitimate -1, we're done. */
562 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200563 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700564
565 /* Any other negative number is disallowed. */
566 if (result < 0) {
567 goto underflow;
568 }
569
570 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200571 if (sizeof(gid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700572 (long)gid != result)
573 goto underflow;
574 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200575 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700576
577 if (overflow < 0)
578 goto underflow;
579
580 /*
581 * Okay, the value overflowed a signed long. If it
582 * fits in an *unsigned* long, it may still be okay,
583 * as gid_t may be unsigned long on this platform.
584 */
585 uresult = PyLong_AsUnsignedLong(index);
586 if (PyErr_Occurred()) {
587 if (PyErr_ExceptionMatches(PyExc_OverflowError))
588 goto overflow;
589 goto fail;
590 }
591
592 gid = (gid_t)uresult;
593
594 /*
595 * If gid == (gid_t)-1, the user actually passed in ULONG_MAX,
596 * but this value would get interpreted as (gid_t)-1 by chown
597 * and its siblings. That's not what the user meant! So we
598 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100599 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700600 */
601 if (gid == (gid_t)-1)
602 goto overflow;
603
604 /* Ensure the value wasn't truncated. */
605 if (sizeof(gid_t) < sizeof(long) &&
606 (unsigned long)gid != uresult)
607 goto overflow;
608 /* fallthrough */
609
610success:
611 Py_DECREF(index);
612 *(gid_t *)p = gid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200613 return 1;
614
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700615underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200616 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700617 "gid is less than minimum");
618 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200619
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700620overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200621 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700622 "gid is greater than maximum");
623 /* fallthrough */
624
625fail:
626 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200627 return 0;
628}
629#endif /* MS_WINDOWS */
630
631
Larry Hastings9cf065c2012-06-22 16:30:09 -0700632#ifdef AT_FDCWD
Trent Nelson9a461052012-09-18 21:50:06 -0400633/*
634 * Why the (int) cast? Solaris 10 defines AT_FDCWD as 0xffd19553 (-3041965);
635 * without the int cast, the value gets interpreted as uint (4291925331),
636 * which doesn't play nicely with all the initializer lines in this file that
637 * look like this:
638 * int dir_fd = DEFAULT_DIR_FD;
639 */
640#define DEFAULT_DIR_FD (int)AT_FDCWD
Larry Hastings9cf065c2012-06-22 16:30:09 -0700641#else
642#define DEFAULT_DIR_FD (-100)
643#endif
644
645static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200646_fd_converter(PyObject *o, int *p, const char *allowed)
647{
648 int overflow;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700649 long long_value;
650
651 PyObject *index = PyNumber_Index(o);
652 if (index == NULL) {
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200653 PyErr_Format(PyExc_TypeError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700654 "argument should be %s, not %.200s",
655 allowed, Py_TYPE(o)->tp_name);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700656 return 0;
657 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700658
659 long_value = PyLong_AsLongAndOverflow(index, &overflow);
660 Py_DECREF(index);
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200661 if (overflow > 0 || long_value > INT_MAX) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700662 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700663 "fd is greater than maximum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700664 return 0;
665 }
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200666 if (overflow < 0 || long_value < INT_MIN) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700667 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700668 "fd is less than minimum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700669 return 0;
670 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700671
Larry Hastings9cf065c2012-06-22 16:30:09 -0700672 *p = (int)long_value;
673 return 1;
674}
675
676static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200677dir_fd_converter(PyObject *o, void *p)
678{
679 if (o == Py_None) {
680 *(int *)p = DEFAULT_DIR_FD;
681 return 1;
682 }
683 return _fd_converter(o, (int *)p, "integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700684}
685
686
Larry Hastings9cf065c2012-06-22 16:30:09 -0700687/*
688 * A PyArg_ParseTuple "converter" function
689 * that handles filesystem paths in the manner
690 * preferred by the os module.
691 *
692 * path_converter accepts (Unicode) strings and their
693 * subclasses, and bytes and their subclasses. What
694 * it does with the argument depends on the platform:
695 *
696 * * On Windows, if we get a (Unicode) string we
697 * extract the wchar_t * and return it; if we get
698 * bytes we extract the char * and return that.
699 *
700 * * On all other platforms, strings are encoded
701 * to bytes using PyUnicode_FSConverter, then we
702 * extract the char * from the bytes object and
703 * return that.
704 *
705 * path_converter also optionally accepts signed
706 * integers (representing open file descriptors) instead
707 * of path strings.
708 *
709 * Input fields:
710 * path.nullable
711 * If nonzero, the path is permitted to be None.
712 * path.allow_fd
713 * If nonzero, the path is permitted to be a file handle
714 * (a signed int) instead of a string.
715 * path.function_name
716 * If non-NULL, path_converter will use that as the name
717 * of the function in error messages.
Larry Hastings31826802013-10-19 00:09:25 -0700718 * (If path.function_name is NULL it omits the function name.)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700719 * path.argument_name
720 * If non-NULL, path_converter will use that as the name
721 * of the parameter in error messages.
722 * (If path.argument_name is NULL it uses "path".)
723 *
724 * Output fields:
725 * path.wide
726 * Points to the path if it was expressed as Unicode
727 * and was not encoded. (Only used on Windows.)
728 * path.narrow
729 * Points to the path if it was expressed as bytes,
730 * or it was Unicode and was encoded to bytes.
731 * path.fd
732 * Contains a file descriptor if path.accept_fd was true
733 * and the caller provided a signed integer instead of any
734 * sort of string.
735 *
736 * WARNING: if your "path" parameter is optional, and is
737 * unspecified, path_converter will never get called.
738 * So if you set allow_fd, you *MUST* initialize path.fd = -1
739 * yourself!
740 * path.length
741 * The length of the path in characters, if specified as
742 * a string.
743 * path.object
744 * The original object passed in.
745 * path.cleanup
746 * For internal use only. May point to a temporary object.
747 * (Pay no attention to the man behind the curtain.)
748 *
749 * At most one of path.wide or path.narrow will be non-NULL.
750 * If path was None and path.nullable was set,
751 * or if path was an integer and path.allow_fd was set,
752 * both path.wide and path.narrow will be NULL
753 * and path.length will be 0.
Georg Brandlf7875592012-06-24 13:58:31 +0200754 *
Larry Hastings9cf065c2012-06-22 16:30:09 -0700755 * path_converter takes care to not write to the path_t
756 * unless it's successful. However it must reset the
757 * "cleanup" field each time it's called.
758 *
759 * Use as follows:
760 * path_t path;
761 * memset(&path, 0, sizeof(path));
762 * PyArg_ParseTuple(args, "O&", path_converter, &path);
763 * // ... use values from path ...
764 * path_cleanup(&path);
765 *
766 * (Note that if PyArg_Parse fails you don't need to call
767 * path_cleanup(). However it is safe to do so.)
768 */
769typedef struct {
Victor Stinner292c8352012-10-30 02:17:38 +0100770 const char *function_name;
771 const char *argument_name;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700772 int nullable;
773 int allow_fd;
774 wchar_t *wide;
775 char *narrow;
776 int fd;
777 Py_ssize_t length;
778 PyObject *object;
779 PyObject *cleanup;
780} path_t;
781
Larry Hastings2f936352014-08-05 14:04:04 +1000782#define PATH_T_INITIALIZE(function_name, argument_name, nullable, allow_fd) \
783 {function_name, argument_name, nullable, allow_fd, NULL, NULL, -1, 0, NULL, NULL}
Larry Hastings31826802013-10-19 00:09:25 -0700784
Larry Hastings9cf065c2012-06-22 16:30:09 -0700785static void
786path_cleanup(path_t *path) {
787 if (path->cleanup) {
Serhiy Storchaka505ff752014-02-09 13:33:53 +0200788 Py_CLEAR(path->cleanup);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700789 }
790}
791
792static int
793path_converter(PyObject *o, void *p) {
794 path_t *path = (path_t *)p;
795 PyObject *unicode, *bytes;
796 Py_ssize_t length;
797 char *narrow;
798
799#define FORMAT_EXCEPTION(exc, fmt) \
800 PyErr_Format(exc, "%s%s" fmt, \
801 path->function_name ? path->function_name : "", \
802 path->function_name ? ": " : "", \
803 path->argument_name ? path->argument_name : "path")
804
805 /* Py_CLEANUP_SUPPORTED support */
806 if (o == NULL) {
807 path_cleanup(path);
808 return 1;
809 }
810
811 /* ensure it's always safe to call path_cleanup() */
812 path->cleanup = NULL;
813
814 if (o == Py_None) {
815 if (!path->nullable) {
816 FORMAT_EXCEPTION(PyExc_TypeError,
817 "can't specify None for %s argument");
818 return 0;
819 }
820 path->wide = NULL;
821 path->narrow = NULL;
822 path->length = 0;
823 path->object = o;
824 path->fd = -1;
825 return 1;
826 }
827
828 unicode = PyUnicode_FromObject(o);
829 if (unicode) {
830#ifdef MS_WINDOWS
831 wchar_t *wide;
Victor Stinner59799a82013-11-13 14:17:30 +0100832
833 wide = PyUnicode_AsUnicodeAndSize(unicode, &length);
834 if (!wide) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700835 Py_DECREF(unicode);
836 return 0;
837 }
Victor Stinner59799a82013-11-13 14:17:30 +0100838 if (length > 32767) {
839 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700840 Py_DECREF(unicode);
841 return 0;
842 }
843
844 path->wide = wide;
845 path->narrow = NULL;
846 path->length = length;
847 path->object = o;
848 path->fd = -1;
849 path->cleanup = unicode;
850 return Py_CLEANUP_SUPPORTED;
851#else
852 int converted = PyUnicode_FSConverter(unicode, &bytes);
853 Py_DECREF(unicode);
854 if (!converted)
855 bytes = NULL;
856#endif
857 }
858 else {
859 PyErr_Clear();
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200860 if (PyObject_CheckBuffer(o))
861 bytes = PyBytes_FromObject(o);
862 else
863 bytes = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700864 if (!bytes) {
865 PyErr_Clear();
866 if (path->allow_fd) {
867 int fd;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200868 int result = _fd_converter(o, &fd,
869 "string, bytes or integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700870 if (result) {
871 path->wide = NULL;
872 path->narrow = NULL;
873 path->length = 0;
874 path->object = o;
875 path->fd = fd;
876 return result;
877 }
878 }
879 }
880 }
881
882 if (!bytes) {
883 if (!PyErr_Occurred())
884 FORMAT_EXCEPTION(PyExc_TypeError, "illegal type for %s parameter");
885 return 0;
886 }
887
888#ifdef MS_WINDOWS
889 if (win32_warn_bytes_api()) {
890 Py_DECREF(bytes);
891 return 0;
892 }
893#endif
894
895 length = PyBytes_GET_SIZE(bytes);
896#ifdef MS_WINDOWS
Victor Stinner75875072013-11-24 19:23:25 +0100897 if (length > MAX_PATH-1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700898 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
899 Py_DECREF(bytes);
900 return 0;
901 }
902#endif
903
904 narrow = PyBytes_AS_STRING(bytes);
Victor Stinner706768c2014-08-16 01:03:39 +0200905 if ((size_t)length != strlen(narrow)) {
Serhiy Storchakad8a14472014-09-06 20:07:17 +0300906 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700907 Py_DECREF(bytes);
908 return 0;
909 }
910
911 path->wide = NULL;
912 path->narrow = narrow;
913 path->length = length;
914 path->object = o;
915 path->fd = -1;
916 path->cleanup = bytes;
917 return Py_CLEANUP_SUPPORTED;
918}
919
920static void
921argument_unavailable_error(char *function_name, char *argument_name) {
922 PyErr_Format(PyExc_NotImplementedError,
923 "%s%s%s unavailable on this platform",
924 (function_name != NULL) ? function_name : "",
925 (function_name != NULL) ? ": ": "",
926 argument_name);
927}
928
929static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200930dir_fd_unavailable(PyObject *o, void *p)
931{
932 int dir_fd;
933 if (!dir_fd_converter(o, &dir_fd))
Larry Hastings9cf065c2012-06-22 16:30:09 -0700934 return 0;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200935 if (dir_fd != DEFAULT_DIR_FD) {
936 argument_unavailable_error(NULL, "dir_fd");
937 return 0;
938 }
939 *(int *)p = dir_fd;
940 return 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700941}
942
943static int
944fd_specified(char *function_name, int fd) {
945 if (fd == -1)
946 return 0;
947
948 argument_unavailable_error(function_name, "fd");
949 return 1;
950}
951
952static int
953follow_symlinks_specified(char *function_name, int follow_symlinks) {
954 if (follow_symlinks)
955 return 0;
956
957 argument_unavailable_error(function_name, "follow_symlinks");
958 return 1;
959}
960
961static int
962path_and_dir_fd_invalid(char *function_name, path_t *path, int dir_fd) {
963 if (!path->narrow && !path->wide && (dir_fd != DEFAULT_DIR_FD)) {
964 PyErr_Format(PyExc_ValueError,
965 "%s: can't specify dir_fd without matching path",
966 function_name);
967 return 1;
968 }
969 return 0;
970}
971
972static int
973dir_fd_and_fd_invalid(char *function_name, int dir_fd, int fd) {
974 if ((dir_fd != DEFAULT_DIR_FD) && (fd != -1)) {
975 PyErr_Format(PyExc_ValueError,
976 "%s: can't specify both dir_fd and fd",
977 function_name);
978 return 1;
979 }
980 return 0;
981}
982
983static int
984fd_and_follow_symlinks_invalid(char *function_name, int fd,
985 int follow_symlinks) {
986 if ((fd > 0) && (!follow_symlinks)) {
987 PyErr_Format(PyExc_ValueError,
988 "%s: cannot use fd and follow_symlinks together",
989 function_name);
990 return 1;
991 }
992 return 0;
993}
994
995static int
996dir_fd_and_follow_symlinks_invalid(char *function_name, int dir_fd,
997 int follow_symlinks) {
998 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
999 PyErr_Format(PyExc_ValueError,
1000 "%s: cannot use dir_fd and follow_symlinks together",
1001 function_name);
1002 return 1;
1003 }
1004 return 0;
1005}
1006
Larry Hastings2f936352014-08-05 14:04:04 +10001007#ifdef MS_WINDOWS
1008 typedef PY_LONG_LONG Py_off_t;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001009#else
Larry Hastings2f936352014-08-05 14:04:04 +10001010 typedef off_t Py_off_t;
1011#endif
1012
1013static int
1014Py_off_t_converter(PyObject *arg, void *addr)
1015{
1016#ifdef HAVE_LARGEFILE_SUPPORT
1017 *((Py_off_t *)addr) = PyLong_AsLongLong(arg);
1018#else
1019 *((Py_off_t *)addr) = PyLong_AsLong(arg);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001020#endif
1021 if (PyErr_Occurred())
1022 return 0;
1023 return 1;
1024}
Larry Hastings2f936352014-08-05 14:04:04 +10001025
1026static PyObject *
1027PyLong_FromPy_off_t(Py_off_t offset)
1028{
1029#ifdef HAVE_LARGEFILE_SUPPORT
1030 return PyLong_FromLongLong(offset);
1031#else
1032 return PyLong_FromLong(offset);
Ross Lagerwallb1e5d592011-09-19 08:30:43 +02001033#endif
Larry Hastings2f936352014-08-05 14:04:04 +10001034}
1035
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001036
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001037#if defined _MSC_VER && _MSC_VER >= 1400
1038/* Microsoft CRT in VS2005 and higher will verify that a filehandle is
Andrew Svetlov737fb892012-12-18 21:14:22 +02001039 * valid and raise an assertion if it isn't.
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001040 * Normally, an invalid fd is likely to be a C program error and therefore
1041 * an assertion can be useful, but it does contradict the POSIX standard
1042 * which for write(2) states:
1043 * "Otherwise, -1 shall be returned and errno set to indicate the error."
1044 * "[EBADF] The fildes argument is not a valid file descriptor open for
1045 * writing."
1046 * Furthermore, python allows the user to enter any old integer
1047 * as a fd and should merely raise a python exception on error.
1048 * The Microsoft CRT doesn't provide an official way to check for the
1049 * validity of a file descriptor, but we can emulate its internal behaviour
Victor Stinner8c62be82010-05-06 00:08:46 +00001050 * by using the exported __pinfo data member and knowledge of the
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001051 * internal structures involved.
1052 * The structures below must be updated for each version of visual studio
1053 * according to the file internal.h in the CRT source, until MS comes
1054 * up with a less hacky way to do this.
1055 * (all of this is to avoid globally modifying the CRT behaviour using
1056 * _set_invalid_parameter_handler() and _CrtSetReportMode())
1057 */
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001058/* The actual size of the structure is determined at runtime.
1059 * Only the first items must be present.
1060 */
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001061typedef struct {
Victor Stinner8c62be82010-05-06 00:08:46 +00001062 intptr_t osfhnd;
1063 char osfile;
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001064} my_ioinfo;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001065
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001066extern __declspec(dllimport) char * __pioinfo[];
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001067#define IOINFO_L2E 5
1068#define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
1069#define IOINFO_ARRAYS 64
1070#define _NHANDLE_ (IOINFO_ARRAYS * IOINFO_ARRAY_ELTS)
1071#define FOPEN 0x01
1072#define _NO_CONSOLE_FILENO (intptr_t)-2
1073
1074/* This function emulates what the windows CRT does to validate file handles */
1075int
1076_PyVerify_fd(int fd)
1077{
Victor Stinner8c62be82010-05-06 00:08:46 +00001078 const int i1 = fd >> IOINFO_L2E;
1079 const int i2 = fd & ((1 << IOINFO_L2E) - 1);
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001080
Antoine Pitrou22e41552010-08-15 18:07:50 +00001081 static size_t sizeof_ioinfo = 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001082
Victor Stinner8c62be82010-05-06 00:08:46 +00001083 /* Determine the actual size of the ioinfo structure,
1084 * as used by the CRT loaded in memory
1085 */
1086 if (sizeof_ioinfo == 0 && __pioinfo[0] != NULL) {
1087 sizeof_ioinfo = _msize(__pioinfo[0]) / IOINFO_ARRAY_ELTS;
1088 }
1089 if (sizeof_ioinfo == 0) {
1090 /* This should not happen... */
1091 goto fail;
1092 }
1093
1094 /* See that it isn't a special CLEAR fileno */
1095 if (fd != _NO_CONSOLE_FILENO) {
1096 /* Microsoft CRT would check that 0<=fd<_nhandle but we can't do that. Instead
1097 * we check pointer validity and other info
1098 */
1099 if (0 <= i1 && i1 < IOINFO_ARRAYS && __pioinfo[i1] != NULL) {
1100 /* finally, check that the file is open */
1101 my_ioinfo* info = (my_ioinfo*)(__pioinfo[i1] + i2 * sizeof_ioinfo);
1102 if (info->osfile & FOPEN) {
1103 return 1;
1104 }
1105 }
1106 }
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001107 fail:
Victor Stinner8c62be82010-05-06 00:08:46 +00001108 errno = EBADF;
1109 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001110}
1111
1112/* the special case of checking dup2. The target fd must be in a sensible range */
1113static int
1114_PyVerify_fd_dup2(int fd1, int fd2)
1115{
Victor Stinner8c62be82010-05-06 00:08:46 +00001116 if (!_PyVerify_fd(fd1))
1117 return 0;
1118 if (fd2 == _NO_CONSOLE_FILENO)
1119 return 0;
1120 if ((unsigned)fd2 < _NHANDLE_)
1121 return 1;
1122 else
1123 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001124}
1125#else
1126/* dummy version. _PyVerify_fd() is already defined in fileobject.h */
1127#define _PyVerify_fd_dup2(A, B) (1)
1128#endif
1129
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001130#ifdef MS_WINDOWS
Brian Curtinf5e76d02010-11-24 13:14:05 +00001131
1132static int
Brian Curtind25aef52011-06-13 15:16:04 -05001133win32_get_reparse_tag(HANDLE reparse_point_handle, ULONG *reparse_tag)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001134{
1135 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
1136 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
1137 DWORD n_bytes_returned;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001138
1139 if (0 == DeviceIoControl(
1140 reparse_point_handle,
1141 FSCTL_GET_REPARSE_POINT,
1142 NULL, 0, /* in buffer */
1143 target_buffer, sizeof(target_buffer),
1144 &n_bytes_returned,
1145 NULL)) /* we're not using OVERLAPPED_IO */
Brian Curtind25aef52011-06-13 15:16:04 -05001146 return FALSE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001147
1148 if (reparse_tag)
1149 *reparse_tag = rdb->ReparseTag;
1150
Brian Curtind25aef52011-06-13 15:16:04 -05001151 return TRUE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001152}
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001153
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001154#endif /* MS_WINDOWS */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001155
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001156/* Return a dictionary corresponding to the POSIX environment table */
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001157#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Jack Jansenea0c3822002-08-01 21:57:49 +00001158/* On Darwin/MacOSX a shared library or framework has no access to
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001159** environ directly, we must obtain it with _NSGetEnviron(). See also
1160** man environ(7).
Jack Jansenea0c3822002-08-01 21:57:49 +00001161*/
1162#include <crt_externs.h>
1163static char **environ;
1164#elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001165extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001166#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001167
Barry Warsaw53699e91996-12-10 23:23:01 +00001168static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001169convertenviron(void)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001170{
Victor Stinner8c62be82010-05-06 00:08:46 +00001171 PyObject *d;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001172#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00001173 wchar_t **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001174#else
Victor Stinner8c62be82010-05-06 00:08:46 +00001175 char **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001176#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00001177
Victor Stinner8c62be82010-05-06 00:08:46 +00001178 d = PyDict_New();
1179 if (d == NULL)
1180 return NULL;
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001181#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Victor Stinner8c62be82010-05-06 00:08:46 +00001182 if (environ == NULL)
1183 environ = *_NSGetEnviron();
1184#endif
1185#ifdef MS_WINDOWS
1186 /* _wenviron must be initialized in this way if the program is started
1187 through main() instead of wmain(). */
1188 _wgetenv(L"");
1189 if (_wenviron == NULL)
1190 return d;
1191 /* This part ignores errors */
1192 for (e = _wenviron; *e != NULL; e++) {
1193 PyObject *k;
1194 PyObject *v;
1195 wchar_t *p = wcschr(*e, L'=');
1196 if (p == NULL)
1197 continue;
1198 k = PyUnicode_FromWideChar(*e, (Py_ssize_t)(p-*e));
1199 if (k == NULL) {
1200 PyErr_Clear();
1201 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001202 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001203 v = PyUnicode_FromWideChar(p+1, wcslen(p+1));
1204 if (v == NULL) {
1205 PyErr_Clear();
1206 Py_DECREF(k);
1207 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001208 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001209 if (PyDict_GetItem(d, k) == NULL) {
1210 if (PyDict_SetItem(d, k, v) != 0)
1211 PyErr_Clear();
1212 }
1213 Py_DECREF(k);
1214 Py_DECREF(v);
1215 }
1216#else
1217 if (environ == NULL)
1218 return d;
1219 /* This part ignores errors */
1220 for (e = environ; *e != NULL; e++) {
1221 PyObject *k;
1222 PyObject *v;
1223 char *p = strchr(*e, '=');
1224 if (p == NULL)
1225 continue;
Victor Stinner84ae1182010-05-06 22:05:07 +00001226 k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
Victor Stinner8c62be82010-05-06 00:08:46 +00001227 if (k == NULL) {
1228 PyErr_Clear();
1229 continue;
1230 }
Victor Stinner84ae1182010-05-06 22:05:07 +00001231 v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
Victor Stinner8c62be82010-05-06 00:08:46 +00001232 if (v == NULL) {
1233 PyErr_Clear();
1234 Py_DECREF(k);
1235 continue;
1236 }
1237 if (PyDict_GetItem(d, k) == NULL) {
1238 if (PyDict_SetItem(d, k, v) != 0)
1239 PyErr_Clear();
1240 }
1241 Py_DECREF(k);
1242 Py_DECREF(v);
Guido van Rossumd48f2521997-12-05 22:19:34 +00001243 }
1244#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001245 return d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001246}
1247
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001248/* Set a POSIX-specific error from errno, and return NULL */
1249
Barry Warsawd58d7641998-07-23 16:14:40 +00001250static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001251posix_error(void)
Guido van Rossumad0ee831995-03-01 10:34:45 +00001252{
Victor Stinner8c62be82010-05-06 00:08:46 +00001253 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001254}
Mark Hammondef8b6542001-05-13 08:04:26 +00001255
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00001256#ifdef MS_WINDOWS
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001257static PyObject *
Brian Curtind40e6f72010-07-08 21:39:08 +00001258win32_error(char* function, const char* filename)
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001259{
Victor Stinner8c62be82010-05-06 00:08:46 +00001260 /* XXX We should pass the function name along in the future.
1261 (winreg.c also wants to pass the function name.)
1262 This would however require an additional param to the
1263 Windows error object, which is non-trivial.
1264 */
1265 errno = GetLastError();
1266 if (filename)
1267 return PyErr_SetFromWindowsErrWithFilename(errno, filename);
1268 else
1269 return PyErr_SetFromWindowsErr(errno);
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001270}
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001271
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001272static PyObject *
Victor Stinnereb5657a2011-09-30 01:44:27 +02001273win32_error_object(char* function, PyObject* filename)
1274{
1275 /* XXX - see win32_error for comments on 'function' */
1276 errno = GetLastError();
1277 if (filename)
1278 return PyErr_SetExcFromWindowsErrWithFilenameObject(
Andrew Svetlov2606a6f2012-12-19 14:33:35 +02001279 PyExc_OSError,
Victor Stinnereb5657a2011-09-30 01:44:27 +02001280 errno,
1281 filename);
1282 else
1283 return PyErr_SetFromWindowsErr(errno);
1284}
1285
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001286#endif /* MS_WINDOWS */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001287
Larry Hastings9cf065c2012-06-22 16:30:09 -07001288static PyObject *
Victor Stinner292c8352012-10-30 02:17:38 +01001289path_error(path_t *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001290{
1291#ifdef MS_WINDOWS
Victor Stinner292c8352012-10-30 02:17:38 +01001292 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
1293 0, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001294#else
Victor Stinner292c8352012-10-30 02:17:38 +01001295 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001296#endif
1297}
1298
Larry Hastings31826802013-10-19 00:09:25 -07001299
Larry Hastingsb0827312014-02-09 22:05:19 -08001300static PyObject *
1301path_error2(path_t *path, path_t *path2)
1302{
1303#ifdef MS_WINDOWS
1304 return PyErr_SetExcFromWindowsErrWithFilenameObjects(PyExc_OSError,
1305 0, path->object, path2->object);
1306#else
1307 return PyErr_SetFromErrnoWithFilenameObjects(PyExc_OSError,
1308 path->object, path2->object);
1309#endif
1310}
1311
1312
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001313/* POSIX generic methods */
1314
Larry Hastings2f936352014-08-05 14:04:04 +10001315static int
1316fildes_converter(PyObject *o, void *p)
Fred Drake4d1e64b2002-04-15 19:40:07 +00001317{
Victor Stinner8c62be82010-05-06 00:08:46 +00001318 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +10001319 int *pointer = (int *)p;
1320 fd = PyObject_AsFileDescriptor(o);
Victor Stinner8c62be82010-05-06 00:08:46 +00001321 if (fd < 0)
Larry Hastings2f936352014-08-05 14:04:04 +10001322 return 0;
1323 if (!_PyVerify_fd(fd)) {
1324 posix_error();
1325 return 0;
1326 }
1327 *pointer = fd;
1328 return 1;
1329}
1330
1331static PyObject *
1332posix_fildes_fd(int fd, int (*func)(int))
1333{
1334 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00001335 Py_BEGIN_ALLOW_THREADS
1336 res = (*func)(fd);
1337 Py_END_ALLOW_THREADS
1338 if (res < 0)
1339 return posix_error();
1340 Py_INCREF(Py_None);
1341 return Py_None;
Fred Drake4d1e64b2002-04-15 19:40:07 +00001342}
Guido van Rossum21142a01999-01-08 21:05:37 +00001343
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001344
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001345#ifdef MS_WINDOWS
Thomas Wouters477c8d52006-05-27 19:21:47 +00001346/* This is a reimplementation of the C library's chdir function,
1347 but one that produces Win32 errors instead of DOS error codes.
1348 chdir is essentially a wrapper around SetCurrentDirectory; however,
1349 it also needs to set "magic" environment variables indicating
1350 the per-drive current directory, which are of the form =<drive>: */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001351static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001352win32_chdir(LPCSTR path)
1353{
Victor Stinner75875072013-11-24 19:23:25 +01001354 char new_path[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00001355 int result;
1356 char env[4] = "=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001357
Victor Stinner8c62be82010-05-06 00:08:46 +00001358 if(!SetCurrentDirectoryA(path))
1359 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001360 result = GetCurrentDirectoryA(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001361 if (!result)
1362 return FALSE;
1363 /* In the ANSI API, there should not be any paths longer
Victor Stinner75875072013-11-24 19:23:25 +01001364 than MAX_PATH-1 (not including the final null character). */
1365 assert(result < Py_ARRAY_LENGTH(new_path));
Victor Stinner8c62be82010-05-06 00:08:46 +00001366 if (strncmp(new_path, "\\\\", 2) == 0 ||
1367 strncmp(new_path, "//", 2) == 0)
1368 /* UNC path, nothing to do. */
1369 return TRUE;
1370 env[1] = new_path[0];
1371 return SetEnvironmentVariableA(env, new_path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001372}
1373
1374/* The Unicode version differs from the ANSI version
1375 since the current directory might exceed MAX_PATH characters */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001376static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001377win32_wchdir(LPCWSTR path)
1378{
Victor Stinner75875072013-11-24 19:23:25 +01001379 wchar_t _new_path[MAX_PATH], *new_path = _new_path;
Victor Stinner8c62be82010-05-06 00:08:46 +00001380 int result;
1381 wchar_t env[4] = L"=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001382
Victor Stinner8c62be82010-05-06 00:08:46 +00001383 if(!SetCurrentDirectoryW(path))
1384 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001385 result = GetCurrentDirectoryW(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001386 if (!result)
1387 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001388 if (result > Py_ARRAY_LENGTH(new_path)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001389 new_path = PyMem_RawMalloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00001390 if (!new_path) {
1391 SetLastError(ERROR_OUTOFMEMORY);
1392 return FALSE;
1393 }
1394 result = GetCurrentDirectoryW(result, new_path);
1395 if (!result) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001396 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001397 return FALSE;
1398 }
1399 }
1400 if (wcsncmp(new_path, L"\\\\", 2) == 0 ||
1401 wcsncmp(new_path, L"//", 2) == 0)
1402 /* UNC path, nothing to do. */
1403 return TRUE;
1404 env[1] = new_path[0];
1405 result = SetEnvironmentVariableW(env, new_path);
1406 if (new_path != _new_path)
Victor Stinnerb6404912013-07-07 16:21:41 +02001407 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001408 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001409}
1410#endif
1411
Martin v. Löwis14694662006-02-03 12:54:16 +00001412#ifdef MS_WINDOWS
1413/* The CRT of Windows has a number of flaws wrt. its stat() implementation:
1414 - time stamps are restricted to second resolution
1415 - file modification times suffer from forth-and-back conversions between
1416 UTC and local time
1417 Therefore, we implement our own stat, based on the Win32 API directly.
1418*/
Victor Stinner8c62be82010-05-06 00:08:46 +00001419#define HAVE_STAT_NSEC 1
Zachary Ware63f277b2014-06-19 09:46:37 -05001420#define HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES 1
Martin v. Löwis14694662006-02-03 12:54:16 +00001421
1422struct win32_stat{
Brian Curtin87e63a22012-12-31 11:59:48 -06001423 unsigned long st_dev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001424 __int64 st_ino;
1425 unsigned short st_mode;
1426 int st_nlink;
1427 int st_uid;
1428 int st_gid;
Brian Curtin87e63a22012-12-31 11:59:48 -06001429 unsigned long st_rdev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001430 __int64 st_size;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001431 time_t st_atime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001432 int st_atime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001433 time_t st_mtime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001434 int st_mtime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001435 time_t st_ctime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001436 int st_ctime_nsec;
Zachary Ware63f277b2014-06-19 09:46:37 -05001437 unsigned long st_file_attributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001438};
1439
1440static __int64 secs_between_epochs = 11644473600; /* Seconds between 1.1.1601 and 1.1.1970 */
1441
1442static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001443FILE_TIME_to_time_t_nsec(FILETIME *in_ptr, time_t *time_out, int* nsec_out)
Martin v. Löwis14694662006-02-03 12:54:16 +00001444{
Victor Stinner8c62be82010-05-06 00:08:46 +00001445 /* XXX endianness. Shouldn't matter, as all Windows implementations are little-endian */
1446 /* Cannot simply cast and dereference in_ptr,
1447 since it might not be aligned properly */
1448 __int64 in;
1449 memcpy(&in, in_ptr, sizeof(in));
1450 *nsec_out = (int)(in % 10000000) * 100; /* FILETIME is in units of 100 nsec. */
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001451 *time_out = Py_SAFE_DOWNCAST((in / 10000000) - secs_between_epochs, __int64, time_t);
Martin v. Löwis14694662006-02-03 12:54:16 +00001452}
1453
Thomas Wouters477c8d52006-05-27 19:21:47 +00001454static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001455time_t_to_FILE_TIME(time_t time_in, int nsec_in, FILETIME *out_ptr)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001456{
Victor Stinner8c62be82010-05-06 00:08:46 +00001457 /* XXX endianness */
1458 __int64 out;
1459 out = time_in + secs_between_epochs;
1460 out = out * 10000000 + nsec_in / 100;
1461 memcpy(out_ptr, &out, sizeof(out));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001462}
1463
Martin v. Löwis14694662006-02-03 12:54:16 +00001464/* Below, we *know* that ugo+r is 0444 */
1465#if _S_IREAD != 0400
1466#error Unsupported C library
1467#endif
1468static int
1469attributes_to_mode(DWORD attr)
1470{
Victor Stinner8c62be82010-05-06 00:08:46 +00001471 int m = 0;
1472 if (attr & FILE_ATTRIBUTE_DIRECTORY)
1473 m |= _S_IFDIR | 0111; /* IFEXEC for user,group,other */
1474 else
1475 m |= _S_IFREG;
1476 if (attr & FILE_ATTRIBUTE_READONLY)
1477 m |= 0444;
1478 else
1479 m |= 0666;
1480 return m;
Martin v. Löwis14694662006-02-03 12:54:16 +00001481}
1482
1483static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001484attribute_data_to_stat(BY_HANDLE_FILE_INFORMATION *info, ULONG reparse_tag, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001485{
Victor Stinner8c62be82010-05-06 00:08:46 +00001486 memset(result, 0, sizeof(*result));
1487 result->st_mode = attributes_to_mode(info->dwFileAttributes);
1488 result->st_size = (((__int64)info->nFileSizeHigh)<<32) + info->nFileSizeLow;
Brian Curtin490b32a2012-12-26 07:03:03 -06001489 result->st_dev = info->dwVolumeSerialNumber;
1490 result->st_rdev = result->st_dev;
Victor Stinner8c62be82010-05-06 00:08:46 +00001491 FILE_TIME_to_time_t_nsec(&info->ftCreationTime, &result->st_ctime, &result->st_ctime_nsec);
1492 FILE_TIME_to_time_t_nsec(&info->ftLastWriteTime, &result->st_mtime, &result->st_mtime_nsec);
1493 FILE_TIME_to_time_t_nsec(&info->ftLastAccessTime, &result->st_atime, &result->st_atime_nsec);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001494 result->st_nlink = info->nNumberOfLinks;
Brian Curtin1b9df392010-11-24 20:24:31 +00001495 result->st_ino = (((__int64)info->nFileIndexHigh)<<32) + info->nFileIndexLow;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001496 if (reparse_tag == IO_REPARSE_TAG_SYMLINK) {
1497 /* first clear the S_IFMT bits */
Christian Heimes99d61352013-06-23 23:56:05 +02001498 result->st_mode ^= (result->st_mode & S_IFMT);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001499 /* now set the bits that make this a symlink */
Christian Heimes99d61352013-06-23 23:56:05 +02001500 result->st_mode |= S_IFLNK;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001501 }
Zachary Ware63f277b2014-06-19 09:46:37 -05001502 result->st_file_attributes = info->dwFileAttributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001503
Victor Stinner8c62be82010-05-06 00:08:46 +00001504 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001505}
1506
Guido van Rossumd8faa362007-04-27 19:54:29 +00001507static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001508attributes_from_dir(LPCSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001509{
Victor Stinner8c62be82010-05-06 00:08:46 +00001510 HANDLE hFindFile;
1511 WIN32_FIND_DATAA FileData;
1512 hFindFile = FindFirstFileA(pszFile, &FileData);
1513 if (hFindFile == INVALID_HANDLE_VALUE)
1514 return FALSE;
1515 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001516 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001517 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001518 info->dwFileAttributes = FileData.dwFileAttributes;
1519 info->ftCreationTime = FileData.ftCreationTime;
1520 info->ftLastAccessTime = FileData.ftLastAccessTime;
1521 info->ftLastWriteTime = FileData.ftLastWriteTime;
1522 info->nFileSizeHigh = FileData.nFileSizeHigh;
1523 info->nFileSizeLow = FileData.nFileSizeLow;
1524/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001525 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1526 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001527 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001528}
1529
1530static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001531attributes_from_dir_w(LPCWSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001532{
Victor Stinner8c62be82010-05-06 00:08:46 +00001533 HANDLE hFindFile;
1534 WIN32_FIND_DATAW FileData;
1535 hFindFile = FindFirstFileW(pszFile, &FileData);
1536 if (hFindFile == INVALID_HANDLE_VALUE)
1537 return FALSE;
1538 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001539 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001540 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001541 info->dwFileAttributes = FileData.dwFileAttributes;
1542 info->ftCreationTime = FileData.ftCreationTime;
1543 info->ftLastAccessTime = FileData.ftLastAccessTime;
1544 info->ftLastWriteTime = FileData.ftLastWriteTime;
1545 info->nFileSizeHigh = FileData.nFileSizeHigh;
1546 info->nFileSizeLow = FileData.nFileSizeLow;
1547/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001548 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1549 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001550 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001551}
1552
Brian Curtind25aef52011-06-13 15:16:04 -05001553/* Grab GetFinalPathNameByHandle dynamically from kernel32 */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001554static int has_GetFinalPathNameByHandle = -1;
Brian Curtind25aef52011-06-13 15:16:04 -05001555static DWORD (CALLBACK *Py_GetFinalPathNameByHandleW)(HANDLE, LPWSTR, DWORD,
1556 DWORD);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001557static int
Brian Curtind25aef52011-06-13 15:16:04 -05001558check_GetFinalPathNameByHandle()
Brian Curtinf5e76d02010-11-24 13:14:05 +00001559{
Brian Curtind25aef52011-06-13 15:16:04 -05001560 HINSTANCE hKernel32;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001561 DWORD (CALLBACK *Py_GetFinalPathNameByHandleA)(HANDLE, LPSTR, DWORD,
1562 DWORD);
1563
Brian Curtind25aef52011-06-13 15:16:04 -05001564 /* only recheck */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001565 if (-1 == has_GetFinalPathNameByHandle)
Brian Curtind25aef52011-06-13 15:16:04 -05001566 {
Martin v. Löwis50590f12012-01-14 17:54:09 +01001567 hKernel32 = GetModuleHandleW(L"KERNEL32");
Brian Curtind25aef52011-06-13 15:16:04 -05001568 *(FARPROC*)&Py_GetFinalPathNameByHandleA = GetProcAddress(hKernel32,
1569 "GetFinalPathNameByHandleA");
1570 *(FARPROC*)&Py_GetFinalPathNameByHandleW = GetProcAddress(hKernel32,
1571 "GetFinalPathNameByHandleW");
1572 has_GetFinalPathNameByHandle = Py_GetFinalPathNameByHandleA &&
1573 Py_GetFinalPathNameByHandleW;
1574 }
1575 return has_GetFinalPathNameByHandle;
1576}
1577
1578static BOOL
1579get_target_path(HANDLE hdl, wchar_t **target_path)
1580{
1581 int buf_size, result_length;
1582 wchar_t *buf;
1583
1584 /* We have a good handle to the target, use it to determine
1585 the target path name (then we'll call lstat on it). */
1586 buf_size = Py_GetFinalPathNameByHandleW(hdl, 0, 0,
1587 VOLUME_NAME_DOS);
1588 if(!buf_size)
1589 return FALSE;
1590
Victor Stinnerb6404912013-07-07 16:21:41 +02001591 buf = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtinc8be8402011-06-14 09:52:50 -05001592 if (!buf) {
1593 SetLastError(ERROR_OUTOFMEMORY);
1594 return FALSE;
1595 }
1596
Brian Curtind25aef52011-06-13 15:16:04 -05001597 result_length = Py_GetFinalPathNameByHandleW(hdl,
1598 buf, buf_size, VOLUME_NAME_DOS);
1599
1600 if(!result_length) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001601 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001602 return FALSE;
1603 }
1604
1605 if(!CloseHandle(hdl)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001606 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001607 return FALSE;
1608 }
1609
1610 buf[result_length] = 0;
1611
1612 *target_path = buf;
1613 return TRUE;
1614}
1615
1616static int
1617win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1618 BOOL traverse);
1619static int
1620win32_xstat_impl(const char *path, struct win32_stat *result,
1621 BOOL traverse)
1622{
Victor Stinner26de69d2011-06-17 15:15:38 +02001623 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001624 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001625 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001626 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001627 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001628 const char *dot;
1629
Brian Curtind25aef52011-06-13 15:16:04 -05001630 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001631 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1632 traverse reparse point. */
1633 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001634 }
1635
Brian Curtinf5e76d02010-11-24 13:14:05 +00001636 hFile = CreateFileA(
1637 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001638 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001639 0, /* share mode */
1640 NULL, /* security attributes */
1641 OPEN_EXISTING,
1642 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001643 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1644 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001645 the symlink path again and not the actual final path. */
Brian Curtind25aef52011-06-13 15:16:04 -05001646 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
1647 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001648 NULL);
1649
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001650 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001651 /* Either the target doesn't exist, or we don't have access to
1652 get a handle to it. If the former, we need to return an error.
1653 If the latter, we can use attributes_from_dir. */
1654 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001655 return -1;
1656 /* Could not get attributes on open file. Fall back to
1657 reading the directory. */
1658 if (!attributes_from_dir(path, &info, &reparse_tag))
1659 /* Very strange. This should not fail now */
1660 return -1;
1661 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1662 if (traverse) {
1663 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001664 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001665 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001666 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001667 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001668 } else {
1669 if (!GetFileInformationByHandle(hFile, &info)) {
1670 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001671 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001672 }
1673 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001674 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1675 return -1;
1676
1677 /* Close the outer open file handle now that we're about to
1678 reopen it with different flags. */
1679 if (!CloseHandle(hFile))
1680 return -1;
1681
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001682 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001683 /* In order to call GetFinalPathNameByHandle we need to open
1684 the file without the reparse handling flag set. */
1685 hFile2 = CreateFileA(
1686 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1687 NULL, OPEN_EXISTING,
1688 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1689 NULL);
1690 if (hFile2 == INVALID_HANDLE_VALUE)
1691 return -1;
1692
1693 if (!get_target_path(hFile2, &target_path))
1694 return -1;
1695
1696 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001697 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001698 return code;
1699 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001700 } else
1701 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001702 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001703 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001704
1705 /* Set S_IEXEC if it is an .exe, .bat, ... */
1706 dot = strrchr(path, '.');
1707 if (dot) {
1708 if (stricmp(dot, ".bat") == 0 || stricmp(dot, ".cmd") == 0 ||
1709 stricmp(dot, ".exe") == 0 || stricmp(dot, ".com") == 0)
1710 result->st_mode |= 0111;
1711 }
1712 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001713}
1714
1715static int
Brian Curtind25aef52011-06-13 15:16:04 -05001716win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1717 BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001718{
1719 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001720 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001721 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001722 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001723 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001724 const wchar_t *dot;
1725
Brian Curtind25aef52011-06-13 15:16:04 -05001726 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001727 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1728 traverse reparse point. */
1729 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001730 }
1731
Brian Curtinf5e76d02010-11-24 13:14:05 +00001732 hFile = CreateFileW(
1733 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001734 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001735 0, /* share mode */
1736 NULL, /* security attributes */
1737 OPEN_EXISTING,
1738 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001739 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1740 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001741 the symlink path again and not the actual final path. */
Victor Stinner26de69d2011-06-17 15:15:38 +02001742 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
Brian Curtind25aef52011-06-13 15:16:04 -05001743 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001744 NULL);
1745
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001746 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001747 /* Either the target doesn't exist, or we don't have access to
1748 get a handle to it. If the former, we need to return an error.
1749 If the latter, we can use attributes_from_dir. */
1750 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001751 return -1;
1752 /* Could not get attributes on open file. Fall back to
1753 reading the directory. */
1754 if (!attributes_from_dir_w(path, &info, &reparse_tag))
1755 /* Very strange. This should not fail now */
1756 return -1;
1757 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1758 if (traverse) {
1759 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001760 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001761 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001762 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001763 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001764 } else {
1765 if (!GetFileInformationByHandle(hFile, &info)) {
1766 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001767 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001768 }
1769 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001770 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1771 return -1;
1772
1773 /* Close the outer open file handle now that we're about to
1774 reopen it with different flags. */
1775 if (!CloseHandle(hFile))
1776 return -1;
1777
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001778 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001779 /* In order to call GetFinalPathNameByHandle we need to open
1780 the file without the reparse handling flag set. */
1781 hFile2 = CreateFileW(
1782 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1783 NULL, OPEN_EXISTING,
1784 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1785 NULL);
1786 if (hFile2 == INVALID_HANDLE_VALUE)
1787 return -1;
1788
1789 if (!get_target_path(hFile2, &target_path))
1790 return -1;
1791
1792 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001793 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001794 return code;
1795 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001796 } else
1797 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001798 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001799 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001800
1801 /* Set S_IEXEC if it is an .exe, .bat, ... */
1802 dot = wcsrchr(path, '.');
1803 if (dot) {
1804 if (_wcsicmp(dot, L".bat") == 0 || _wcsicmp(dot, L".cmd") == 0 ||
1805 _wcsicmp(dot, L".exe") == 0 || _wcsicmp(dot, L".com") == 0)
1806 result->st_mode |= 0111;
1807 }
1808 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001809}
1810
1811static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001812win32_xstat(const char *path, struct win32_stat *result, BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001813{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001814 /* Protocol violation: we explicitly clear errno, instead of
1815 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001816 int code = win32_xstat_impl(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001817 errno = 0;
1818 return code;
1819}
Brian Curtinf5e76d02010-11-24 13:14:05 +00001820
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001821static int
1822win32_xstat_w(const wchar_t *path, struct win32_stat *result, BOOL traverse)
1823{
1824 /* Protocol violation: we explicitly clear errno, instead of
1825 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001826 int code = win32_xstat_impl_w(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001827 errno = 0;
1828 return code;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001829}
Brian Curtind25aef52011-06-13 15:16:04 -05001830/* About the following functions: win32_lstat_w, win32_stat, win32_stat_w
Brian Curtind40e6f72010-07-08 21:39:08 +00001831
1832 In Posix, stat automatically traverses symlinks and returns the stat
1833 structure for the target. In Windows, the equivalent GetFileAttributes by
1834 default does not traverse symlinks and instead returns attributes for
1835 the symlink.
1836
1837 Therefore, win32_lstat will get the attributes traditionally, and
1838 win32_stat will first explicitly resolve the symlink target and then will
1839 call win32_lstat on that result.
1840
Ezio Melotti4969f702011-03-15 05:59:46 +02001841 The _w represent Unicode equivalents of the aforementioned ANSI functions. */
Brian Curtind40e6f72010-07-08 21:39:08 +00001842
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001843static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001844win32_lstat(const char* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001845{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001846 return win32_xstat(path, result, FALSE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001847}
1848
Victor Stinner8c62be82010-05-06 00:08:46 +00001849static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001850win32_lstat_w(const wchar_t* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001851{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001852 return win32_xstat_w(path, result, FALSE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001853}
1854
1855static int
1856win32_stat(const char* path, struct win32_stat *result)
1857{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001858 return win32_xstat(path, result, TRUE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001859}
1860
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001861static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001862win32_stat_w(const wchar_t* path, struct win32_stat *result)
1863{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001864 return win32_xstat_w(path, result, TRUE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001865}
1866
1867static int
1868win32_fstat(int file_number, struct win32_stat *result)
1869{
Victor Stinner8c62be82010-05-06 00:08:46 +00001870 BY_HANDLE_FILE_INFORMATION info;
1871 HANDLE h;
1872 int type;
Martin v. Löwis14694662006-02-03 12:54:16 +00001873
Richard Oudkerk2240ac12012-07-06 12:05:32 +01001874 if (!_PyVerify_fd(file_number))
1875 h = INVALID_HANDLE_VALUE;
1876 else
1877 h = (HANDLE)_get_osfhandle(file_number);
Martin v. Löwis14694662006-02-03 12:54:16 +00001878
Victor Stinner8c62be82010-05-06 00:08:46 +00001879 /* Protocol violation: we explicitly clear errno, instead of
1880 setting it to a POSIX error. Callers should use GetLastError. */
1881 errno = 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001882
Victor Stinner8c62be82010-05-06 00:08:46 +00001883 if (h == INVALID_HANDLE_VALUE) {
1884 /* This is really a C library error (invalid file handle).
1885 We set the Win32 error to the closes one matching. */
1886 SetLastError(ERROR_INVALID_HANDLE);
1887 return -1;
1888 }
1889 memset(result, 0, sizeof(*result));
Martin v. Löwis14694662006-02-03 12:54:16 +00001890
Victor Stinner8c62be82010-05-06 00:08:46 +00001891 type = GetFileType(h);
1892 if (type == FILE_TYPE_UNKNOWN) {
1893 DWORD error = GetLastError();
1894 if (error != 0) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001895 return -1;
Victor Stinner8c62be82010-05-06 00:08:46 +00001896 }
1897 /* else: valid but unknown file */
1898 }
Martin v. Löwis14694662006-02-03 12:54:16 +00001899
Victor Stinner8c62be82010-05-06 00:08:46 +00001900 if (type != FILE_TYPE_DISK) {
1901 if (type == FILE_TYPE_CHAR)
1902 result->st_mode = _S_IFCHR;
1903 else if (type == FILE_TYPE_PIPE)
1904 result->st_mode = _S_IFIFO;
1905 return 0;
1906 }
1907
1908 if (!GetFileInformationByHandle(h, &info)) {
1909 return -1;
1910 }
1911
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001912 attribute_data_to_stat(&info, 0, result);
Victor Stinner8c62be82010-05-06 00:08:46 +00001913 /* specific to fstat() */
Victor Stinner8c62be82010-05-06 00:08:46 +00001914 result->st_ino = (((__int64)info.nFileIndexHigh)<<32) + info.nFileIndexLow;
1915 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001916}
1917
1918#endif /* MS_WINDOWS */
1919
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001920PyDoc_STRVAR(stat_result__doc__,
Larry Hastings9cf065c2012-06-22 16:30:09 -07001921"stat_result: Result from stat, fstat, or lstat.\n\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001922This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001923 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001924or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
1925\n\
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001926Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
1927or st_flags, they are available as attributes only.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001928\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001929See os.stat for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001930
1931static PyStructSequence_Field stat_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001932 {"st_mode", "protection bits"},
1933 {"st_ino", "inode"},
1934 {"st_dev", "device"},
1935 {"st_nlink", "number of hard links"},
1936 {"st_uid", "user ID of owner"},
1937 {"st_gid", "group ID of owner"},
1938 {"st_size", "total size, in bytes"},
1939 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
1940 {NULL, "integer time of last access"},
1941 {NULL, "integer time of last modification"},
1942 {NULL, "integer time of last change"},
1943 {"st_atime", "time of last access"},
1944 {"st_mtime", "time of last modification"},
1945 {"st_ctime", "time of last change"},
Larry Hastings6fe20b32012-04-19 15:07:49 -07001946 {"st_atime_ns", "time of last access in nanoseconds"},
1947 {"st_mtime_ns", "time of last modification in nanoseconds"},
1948 {"st_ctime_ns", "time of last change in nanoseconds"},
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001949#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00001950 {"st_blksize", "blocksize for filesystem I/O"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001951#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001952#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00001953 {"st_blocks", "number of blocks allocated"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001954#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001955#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00001956 {"st_rdev", "device type (if inode device)"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001957#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001958#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00001959 {"st_flags", "user defined flags for file"},
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001960#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001961#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00001962 {"st_gen", "generation number"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001963#endif
1964#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00001965 {"st_birthtime", "time of creation"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001966#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05001967#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1968 {"st_file_attributes", "Windows file attribute bits"},
1969#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001970 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001971};
1972
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001973#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Larry Hastings6fe20b32012-04-19 15:07:49 -07001974#define ST_BLKSIZE_IDX 16
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001975#else
Larry Hastings6fe20b32012-04-19 15:07:49 -07001976#define ST_BLKSIZE_IDX 15
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001977#endif
1978
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001979#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001980#define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
1981#else
1982#define ST_BLOCKS_IDX ST_BLKSIZE_IDX
1983#endif
1984
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001985#ifdef HAVE_STRUCT_STAT_ST_RDEV
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001986#define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
1987#else
1988#define ST_RDEV_IDX ST_BLOCKS_IDX
1989#endif
1990
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001991#ifdef HAVE_STRUCT_STAT_ST_FLAGS
1992#define ST_FLAGS_IDX (ST_RDEV_IDX+1)
1993#else
1994#define ST_FLAGS_IDX ST_RDEV_IDX
1995#endif
1996
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001997#ifdef HAVE_STRUCT_STAT_ST_GEN
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001998#define ST_GEN_IDX (ST_FLAGS_IDX+1)
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001999#else
Martin v. Löwisf09582e2005-08-14 21:42:34 +00002000#define ST_GEN_IDX ST_FLAGS_IDX
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002001#endif
2002
2003#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
2004#define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
2005#else
2006#define ST_BIRTHTIME_IDX ST_GEN_IDX
2007#endif
2008
Zachary Ware63f277b2014-06-19 09:46:37 -05002009#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2010#define ST_FILE_ATTRIBUTES_IDX (ST_BIRTHTIME_IDX+1)
2011#else
2012#define ST_FILE_ATTRIBUTES_IDX ST_BIRTHTIME_IDX
2013#endif
2014
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002015static PyStructSequence_Desc stat_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002016 "stat_result", /* name */
2017 stat_result__doc__, /* doc */
2018 stat_result_fields,
2019 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002020};
2021
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002022PyDoc_STRVAR(statvfs_result__doc__,
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002023"statvfs_result: Result from statvfs or fstatvfs.\n\n\
2024This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00002025 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
Guido van Rossuma4dc73e2001-10-18 20:53:15 +00002026or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002027\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002028See os.statvfs for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002029
2030static PyStructSequence_Field statvfs_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002031 {"f_bsize", },
2032 {"f_frsize", },
2033 {"f_blocks", },
2034 {"f_bfree", },
2035 {"f_bavail", },
2036 {"f_files", },
2037 {"f_ffree", },
2038 {"f_favail", },
2039 {"f_flag", },
2040 {"f_namemax",},
2041 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002042};
2043
2044static PyStructSequence_Desc statvfs_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002045 "statvfs_result", /* name */
2046 statvfs_result__doc__, /* doc */
2047 statvfs_result_fields,
2048 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002049};
2050
Ross Lagerwall7807c352011-03-17 20:20:30 +02002051#if defined(HAVE_WAITID) && !defined(__APPLE__)
2052PyDoc_STRVAR(waitid_result__doc__,
2053"waitid_result: Result from waitid.\n\n\
2054This object may be accessed either as a tuple of\n\
2055 (si_pid, si_uid, si_signo, si_status, si_code),\n\
2056or via the attributes si_pid, si_uid, and so on.\n\
2057\n\
2058See os.waitid for more information.");
2059
2060static PyStructSequence_Field waitid_result_fields[] = {
2061 {"si_pid", },
2062 {"si_uid", },
2063 {"si_signo", },
2064 {"si_status", },
2065 {"si_code", },
2066 {0}
2067};
2068
2069static PyStructSequence_Desc waitid_result_desc = {
2070 "waitid_result", /* name */
2071 waitid_result__doc__, /* doc */
2072 waitid_result_fields,
2073 5
2074};
2075static PyTypeObject WaitidResultType;
2076#endif
2077
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00002078static int initialized;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002079static PyTypeObject StatResultType;
2080static PyTypeObject StatVFSResultType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002081#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05002082static PyTypeObject SchedParamType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002083#endif
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002084static newfunc structseq_new;
2085
2086static PyObject *
2087statresult_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2088{
Victor Stinner8c62be82010-05-06 00:08:46 +00002089 PyStructSequence *result;
2090 int i;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002091
Victor Stinner8c62be82010-05-06 00:08:46 +00002092 result = (PyStructSequence*)structseq_new(type, args, kwds);
2093 if (!result)
2094 return NULL;
2095 /* If we have been initialized from a tuple,
2096 st_?time might be set to None. Initialize it
2097 from the int slots. */
2098 for (i = 7; i <= 9; i++) {
2099 if (result->ob_item[i+3] == Py_None) {
2100 Py_DECREF(Py_None);
2101 Py_INCREF(result->ob_item[i]);
2102 result->ob_item[i+3] = result->ob_item[i];
2103 }
2104 }
2105 return (PyObject*)result;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002106}
2107
2108
2109
2110/* If true, st_?time is float. */
Martin v. Löwisfe33d0b2005-01-16 08:57:39 +00002111static int _stat_float_times = 1;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002112
2113PyDoc_STRVAR(stat_float_times__doc__,
2114"stat_float_times([newval]) -> oldval\n\n\
2115Determine whether os.[lf]stat represents time stamps as float objects.\n\
Larry Hastings2f936352014-08-05 14:04:04 +10002116\n\
2117If value is True, future calls to stat() return floats; if it is False,\n\
2118future calls return ints.\n\
2119If value is omitted, return the current setting.\n");
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002120
Larry Hastings2f936352014-08-05 14:04:04 +10002121/* AC 3.5: the public default value should be None, not ready for that yet */
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002122static PyObject*
2123stat_float_times(PyObject* self, PyObject *args)
2124{
Victor Stinner8c62be82010-05-06 00:08:46 +00002125 int newval = -1;
2126 if (!PyArg_ParseTuple(args, "|i:stat_float_times", &newval))
2127 return NULL;
Victor Stinner034d0aa2012-06-05 01:22:15 +02002128 if (PyErr_WarnEx(PyExc_DeprecationWarning,
2129 "stat_float_times() is deprecated",
2130 1))
2131 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00002132 if (newval == -1)
2133 /* Return old value */
2134 return PyBool_FromLong(_stat_float_times);
2135 _stat_float_times = newval;
2136 Py_INCREF(Py_None);
2137 return Py_None;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002138}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002139
Larry Hastings6fe20b32012-04-19 15:07:49 -07002140static PyObject *billion = NULL;
2141
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002142static void
Victor Stinner4195b5c2012-02-08 23:03:19 +01002143fill_time(PyObject *v, int index, time_t sec, unsigned long nsec)
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002144{
Larry Hastings6fe20b32012-04-19 15:07:49 -07002145 PyObject *s = _PyLong_FromTime_t(sec);
2146 PyObject *ns_fractional = PyLong_FromUnsignedLong(nsec);
2147 PyObject *s_in_ns = NULL;
2148 PyObject *ns_total = NULL;
2149 PyObject *float_s = NULL;
2150
2151 if (!(s && ns_fractional))
2152 goto exit;
2153
2154 s_in_ns = PyNumber_Multiply(s, billion);
2155 if (!s_in_ns)
2156 goto exit;
2157
2158 ns_total = PyNumber_Add(s_in_ns, ns_fractional);
2159 if (!ns_total)
2160 goto exit;
2161
Victor Stinner4195b5c2012-02-08 23:03:19 +01002162 if (_stat_float_times) {
Larry Hastings6fe20b32012-04-19 15:07:49 -07002163 float_s = PyFloat_FromDouble(sec + 1e-9*nsec);
2164 if (!float_s)
2165 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00002166 }
Larry Hastings6fe20b32012-04-19 15:07:49 -07002167 else {
2168 float_s = s;
2169 Py_INCREF(float_s);
2170 }
2171
2172 PyStructSequence_SET_ITEM(v, index, s);
2173 PyStructSequence_SET_ITEM(v, index+3, float_s);
2174 PyStructSequence_SET_ITEM(v, index+6, ns_total);
2175 s = NULL;
2176 float_s = NULL;
2177 ns_total = NULL;
2178exit:
2179 Py_XDECREF(s);
2180 Py_XDECREF(ns_fractional);
2181 Py_XDECREF(s_in_ns);
2182 Py_XDECREF(ns_total);
2183 Py_XDECREF(float_s);
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002184}
2185
Tim Peters5aa91602002-01-30 05:46:57 +00002186/* pack a system stat C structure into the Python stat tuple
Fred Drake699f3522000-06-29 21:12:41 +00002187 (used by posix_stat() and posix_fstat()) */
2188static PyObject*
Victor Stinner4195b5c2012-02-08 23:03:19 +01002189_pystat_fromstructstat(STRUCT_STAT *st)
Fred Drake699f3522000-06-29 21:12:41 +00002190{
Victor Stinner8c62be82010-05-06 00:08:46 +00002191 unsigned long ansec, mnsec, cnsec;
2192 PyObject *v = PyStructSequence_New(&StatResultType);
2193 if (v == NULL)
2194 return NULL;
Fred Drake699f3522000-06-29 21:12:41 +00002195
Victor Stinner8c62be82010-05-06 00:08:46 +00002196 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long)st->st_mode));
Fred Drake699f3522000-06-29 21:12:41 +00002197#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002198 PyStructSequence_SET_ITEM(v, 1,
2199 PyLong_FromLongLong((PY_LONG_LONG)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002200#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002201 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002202#endif
Serhiy Storchaka404fa922013-01-02 18:22:23 +02002203#ifdef MS_WINDOWS
2204 PyStructSequence_SET_ITEM(v, 2, PyLong_FromUnsignedLong(st->st_dev));
2205#elif defined(HAVE_LONG_LONG)
Victor Stinner8c62be82010-05-06 00:08:46 +00002206 PyStructSequence_SET_ITEM(v, 2,
2207 PyLong_FromLongLong((PY_LONG_LONG)st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002208#else
Brian Curtin9cc43212013-01-01 12:31:06 -06002209 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long)st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002210#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002211 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long)st->st_nlink));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02002212#if defined(MS_WINDOWS)
2213 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong(0));
2214 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong(0));
2215#else
2216 PyStructSequence_SET_ITEM(v, 4, _PyLong_FromUid(st->st_uid));
2217 PyStructSequence_SET_ITEM(v, 5, _PyLong_FromGid(st->st_gid));
2218#endif
Fred Drake699f3522000-06-29 21:12:41 +00002219#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002220 PyStructSequence_SET_ITEM(v, 6,
2221 PyLong_FromLongLong((PY_LONG_LONG)st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002222#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002223 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong(st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002224#endif
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002225
Martin v. Löwis14694662006-02-03 12:54:16 +00002226#if defined(HAVE_STAT_TV_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002227 ansec = st->st_atim.tv_nsec;
2228 mnsec = st->st_mtim.tv_nsec;
2229 cnsec = st->st_ctim.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002230#elif defined(HAVE_STAT_TV_NSEC2)
Victor Stinner8c62be82010-05-06 00:08:46 +00002231 ansec = st->st_atimespec.tv_nsec;
2232 mnsec = st->st_mtimespec.tv_nsec;
2233 cnsec = st->st_ctimespec.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002234#elif defined(HAVE_STAT_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002235 ansec = st->st_atime_nsec;
2236 mnsec = st->st_mtime_nsec;
2237 cnsec = st->st_ctime_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002238#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002239 ansec = mnsec = cnsec = 0;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002240#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002241 fill_time(v, 7, st->st_atime, ansec);
2242 fill_time(v, 8, st->st_mtime, mnsec);
2243 fill_time(v, 9, st->st_ctime, cnsec);
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002244
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002245#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00002246 PyStructSequence_SET_ITEM(v, ST_BLKSIZE_IDX,
2247 PyLong_FromLong((long)st->st_blksize));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002248#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002249#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00002250 PyStructSequence_SET_ITEM(v, ST_BLOCKS_IDX,
2251 PyLong_FromLong((long)st->st_blocks));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002252#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002253#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00002254 PyStructSequence_SET_ITEM(v, ST_RDEV_IDX,
2255 PyLong_FromLong((long)st->st_rdev));
Fred Drake699f3522000-06-29 21:12:41 +00002256#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002257#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00002258 PyStructSequence_SET_ITEM(v, ST_GEN_IDX,
2259 PyLong_FromLong((long)st->st_gen));
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002260#endif
2261#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00002262 {
Victor Stinner4195b5c2012-02-08 23:03:19 +01002263 PyObject *val;
2264 unsigned long bsec,bnsec;
2265 bsec = (long)st->st_birthtime;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002266#ifdef HAVE_STAT_TV_NSEC2
Victor Stinner4195b5c2012-02-08 23:03:19 +01002267 bnsec = st->st_birthtimespec.tv_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002268#else
Victor Stinner4195b5c2012-02-08 23:03:19 +01002269 bnsec = 0;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002270#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002271 if (_stat_float_times) {
2272 val = PyFloat_FromDouble(bsec + 1e-9*bnsec);
2273 } else {
2274 val = PyLong_FromLong((long)bsec);
2275 }
2276 PyStructSequence_SET_ITEM(v, ST_BIRTHTIME_IDX,
2277 val);
Victor Stinner8c62be82010-05-06 00:08:46 +00002278 }
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002279#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002280#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00002281 PyStructSequence_SET_ITEM(v, ST_FLAGS_IDX,
2282 PyLong_FromLong((long)st->st_flags));
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002283#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05002284#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2285 PyStructSequence_SET_ITEM(v, ST_FILE_ATTRIBUTES_IDX,
2286 PyLong_FromUnsignedLong(st->st_file_attributes));
2287#endif
Fred Drake699f3522000-06-29 21:12:41 +00002288
Victor Stinner8c62be82010-05-06 00:08:46 +00002289 if (PyErr_Occurred()) {
2290 Py_DECREF(v);
2291 return NULL;
2292 }
Fred Drake699f3522000-06-29 21:12:41 +00002293
Victor Stinner8c62be82010-05-06 00:08:46 +00002294 return v;
Fred Drake699f3522000-06-29 21:12:41 +00002295}
2296
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002297/* POSIX methods */
2298
Guido van Rossum94f6f721999-01-06 18:42:14 +00002299
2300static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07002301posix_do_stat(char *function_name, path_t *path,
2302 int dir_fd, int follow_symlinks)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002303{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002304 STRUCT_STAT st;
2305 int result;
2306
2307#if !defined(MS_WINDOWS) && !defined(HAVE_FSTATAT) && !defined(HAVE_LSTAT)
2308 if (follow_symlinks_specified(function_name, follow_symlinks))
2309 return NULL;
2310#endif
2311
2312 if (path_and_dir_fd_invalid("stat", path, dir_fd) ||
2313 dir_fd_and_fd_invalid("stat", dir_fd, path->fd) ||
2314 fd_and_follow_symlinks_invalid("stat", path->fd, follow_symlinks))
2315 return NULL;
2316
2317 Py_BEGIN_ALLOW_THREADS
2318 if (path->fd != -1)
2319 result = FSTAT(path->fd, &st);
2320 else
2321#ifdef MS_WINDOWS
2322 if (path->wide) {
2323 if (follow_symlinks)
2324 result = win32_stat_w(path->wide, &st);
2325 else
2326 result = win32_lstat_w(path->wide, &st);
2327 }
2328 else
2329#endif
2330#if defined(HAVE_LSTAT) || defined(MS_WINDOWS)
2331 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
2332 result = LSTAT(path->narrow, &st);
2333 else
2334#endif
2335#ifdef HAVE_FSTATAT
2336 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks)
2337 result = fstatat(dir_fd, path->narrow, &st,
2338 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2339 else
2340#endif
2341 result = STAT(path->narrow, &st);
2342 Py_END_ALLOW_THREADS
2343
Victor Stinner292c8352012-10-30 02:17:38 +01002344 if (result != 0) {
2345 return path_error(path);
2346 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07002347
2348 return _pystat_fromstructstat(&st);
2349}
2350
Larry Hastings2f936352014-08-05 14:04:04 +10002351/*[python input]
2352
2353for s in """
2354
2355FACCESSAT
2356FCHMODAT
2357FCHOWNAT
2358FSTATAT
2359LINKAT
2360MKDIRAT
2361MKFIFOAT
2362MKNODAT
2363OPENAT
2364READLINKAT
2365SYMLINKAT
2366UNLINKAT
2367
2368""".strip().split():
2369 s = s.strip()
2370 print("""
2371#ifdef HAVE_{s}
2372 #define {s}_DIR_FD_CONVERTER dir_fd_converter
Larry Hastings31826802013-10-19 00:09:25 -07002373#else
Larry Hastings2f936352014-08-05 14:04:04 +10002374 #define {s}_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings31826802013-10-19 00:09:25 -07002375#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002376""".rstrip().format(s=s))
2377
2378for s in """
2379
2380FCHDIR
2381FCHMOD
2382FCHOWN
2383FDOPENDIR
2384FEXECVE
2385FPATHCONF
2386FSTATVFS
2387FTRUNCATE
2388
2389""".strip().split():
2390 s = s.strip()
2391 print("""
2392#ifdef HAVE_{s}
2393 #define PATH_HAVE_{s} 1
2394#else
2395 #define PATH_HAVE_{s} 0
2396#endif
2397
2398""".rstrip().format(s=s))
2399[python start generated code]*/
2400
2401#ifdef HAVE_FACCESSAT
2402 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_converter
2403#else
2404 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_unavailable
2405#endif
2406
2407#ifdef HAVE_FCHMODAT
2408 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_converter
2409#else
2410 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_unavailable
2411#endif
2412
2413#ifdef HAVE_FCHOWNAT
2414 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_converter
2415#else
2416 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_unavailable
2417#endif
2418
2419#ifdef HAVE_FSTATAT
2420 #define FSTATAT_DIR_FD_CONVERTER dir_fd_converter
2421#else
2422 #define FSTATAT_DIR_FD_CONVERTER dir_fd_unavailable
2423#endif
2424
2425#ifdef HAVE_LINKAT
2426 #define LINKAT_DIR_FD_CONVERTER dir_fd_converter
2427#else
2428 #define LINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2429#endif
2430
2431#ifdef HAVE_MKDIRAT
2432 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_converter
2433#else
2434 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_unavailable
2435#endif
2436
2437#ifdef HAVE_MKFIFOAT
2438 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_converter
2439#else
2440 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_unavailable
2441#endif
2442
2443#ifdef HAVE_MKNODAT
2444 #define MKNODAT_DIR_FD_CONVERTER dir_fd_converter
2445#else
2446 #define MKNODAT_DIR_FD_CONVERTER dir_fd_unavailable
2447#endif
2448
2449#ifdef HAVE_OPENAT
2450 #define OPENAT_DIR_FD_CONVERTER dir_fd_converter
2451#else
2452 #define OPENAT_DIR_FD_CONVERTER dir_fd_unavailable
2453#endif
2454
2455#ifdef HAVE_READLINKAT
2456 #define READLINKAT_DIR_FD_CONVERTER dir_fd_converter
2457#else
2458 #define READLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2459#endif
2460
2461#ifdef HAVE_SYMLINKAT
2462 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_converter
2463#else
2464 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2465#endif
2466
2467#ifdef HAVE_UNLINKAT
2468 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_converter
2469#else
2470 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2471#endif
2472
2473#ifdef HAVE_FCHDIR
2474 #define PATH_HAVE_FCHDIR 1
2475#else
2476 #define PATH_HAVE_FCHDIR 0
2477#endif
2478
2479#ifdef HAVE_FCHMOD
2480 #define PATH_HAVE_FCHMOD 1
2481#else
2482 #define PATH_HAVE_FCHMOD 0
2483#endif
2484
2485#ifdef HAVE_FCHOWN
2486 #define PATH_HAVE_FCHOWN 1
2487#else
2488 #define PATH_HAVE_FCHOWN 0
2489#endif
2490
2491#ifdef HAVE_FDOPENDIR
2492 #define PATH_HAVE_FDOPENDIR 1
2493#else
2494 #define PATH_HAVE_FDOPENDIR 0
2495#endif
2496
2497#ifdef HAVE_FEXECVE
2498 #define PATH_HAVE_FEXECVE 1
2499#else
2500 #define PATH_HAVE_FEXECVE 0
2501#endif
2502
2503#ifdef HAVE_FPATHCONF
2504 #define PATH_HAVE_FPATHCONF 1
2505#else
2506 #define PATH_HAVE_FPATHCONF 0
2507#endif
2508
2509#ifdef HAVE_FSTATVFS
2510 #define PATH_HAVE_FSTATVFS 1
2511#else
2512 #define PATH_HAVE_FSTATVFS 0
2513#endif
2514
2515#ifdef HAVE_FTRUNCATE
2516 #define PATH_HAVE_FTRUNCATE 1
2517#else
2518 #define PATH_HAVE_FTRUNCATE 0
2519#endif
2520/*[python end generated code: output=4bd4f6f7d41267f1 input=80b4c890b6774ea5]*/
Larry Hastings31826802013-10-19 00:09:25 -07002521
2522
Larry Hastings61272b72014-01-07 12:41:53 -08002523/*[python input]
Larry Hastings31826802013-10-19 00:09:25 -07002524
2525class path_t_converter(CConverter):
2526
2527 type = "path_t"
2528 impl_by_reference = True
2529 parse_by_reference = True
2530
2531 converter = 'path_converter'
2532
2533 def converter_init(self, *, allow_fd=False, nullable=False):
Larry Hastings31826802013-10-19 00:09:25 -07002534 # right now path_t doesn't support default values.
2535 # to support a default value, you'll need to override initialize().
Larry Hastings2f936352014-08-05 14:04:04 +10002536 if self.default not in (unspecified, None):
Larry Hastings7726ac92014-01-31 22:03:12 -08002537 fail("Can't specify a default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002538
Larry Hastings2f936352014-08-05 14:04:04 +10002539 if self.c_default not in (None, 'Py_None'):
2540 raise RuntimeError("Can't specify a c_default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002541
2542 self.nullable = nullable
2543 self.allow_fd = allow_fd
2544
Larry Hastings7726ac92014-01-31 22:03:12 -08002545 def pre_render(self):
2546 def strify(value):
Larry Hastings2f936352014-08-05 14:04:04 +10002547 if isinstance(value, str):
2548 return value
Larry Hastings7726ac92014-01-31 22:03:12 -08002549 return str(int(bool(value)))
2550
2551 # add self.py_name here when merging with posixmodule conversion
Larry Hastings2f936352014-08-05 14:04:04 +10002552 self.c_default = 'PATH_T_INITIALIZE("{}", "{}", {}, {})'.format(
Larry Hastings31826802013-10-19 00:09:25 -07002553 self.function.name,
Larry Hastings2f936352014-08-05 14:04:04 +10002554 self.name,
Larry Hastings7726ac92014-01-31 22:03:12 -08002555 strify(self.nullable),
2556 strify(self.allow_fd),
Larry Hastings31826802013-10-19 00:09:25 -07002557 )
2558
2559 def cleanup(self):
2560 return "path_cleanup(&" + self.name + ");\n"
2561
2562
2563class dir_fd_converter(CConverter):
2564 type = 'int'
Larry Hastings31826802013-10-19 00:09:25 -07002565
Larry Hastings2f936352014-08-05 14:04:04 +10002566 def converter_init(self, requires=None):
Larry Hastings31826802013-10-19 00:09:25 -07002567 if self.default in (unspecified, None):
2568 self.c_default = 'DEFAULT_DIR_FD'
Larry Hastings2f936352014-08-05 14:04:04 +10002569 if isinstance(requires, str):
2570 self.converter = requires.upper() + '_DIR_FD_CONVERTER'
2571 else:
2572 self.converter = 'dir_fd_converter'
Larry Hastings31826802013-10-19 00:09:25 -07002573
Larry Hastings2f936352014-08-05 14:04:04 +10002574class fildes_converter(CConverter):
2575 type = 'int'
2576 converter = 'fildes_converter'
2577
2578class uid_t_converter(CConverter):
2579 type = "uid_t"
2580 converter = '_Py_Uid_Converter'
2581
2582class gid_t_converter(CConverter):
2583 type = "gid_t"
2584 converter = '_Py_Gid_Converter'
2585
2586class FSConverter_converter(CConverter):
2587 type = 'PyObject *'
2588 converter = 'PyUnicode_FSConverter'
2589 def converter_init(self):
2590 if self.default is not unspecified:
2591 fail("FSConverter_converter does not support default values")
2592 self.c_default = 'NULL'
2593
2594 def cleanup(self):
2595 return "Py_XDECREF(" + self.name + ");\n"
2596
2597class pid_t_converter(CConverter):
2598 type = 'pid_t'
2599 format_unit = '" _Py_PARSE_PID "'
2600
2601class idtype_t_converter(int_converter):
2602 type = 'idtype_t'
2603
2604class id_t_converter(CConverter):
2605 type = 'id_t'
2606 format_unit = '" _Py_PARSE_PID "'
2607
2608class Py_intptr_t_converter(CConverter):
2609 type = 'Py_intptr_t'
2610 format_unit = '" _Py_PARSE_INTPTR "'
2611
2612class Py_off_t_converter(CConverter):
2613 type = 'Py_off_t'
2614 converter = 'Py_off_t_converter'
2615
2616class Py_off_t_return_converter(long_return_converter):
2617 type = 'Py_off_t'
2618 conversion_fn = 'PyLong_FromPy_off_t'
2619
2620class path_confname_converter(CConverter):
2621 type="int"
2622 converter="conv_path_confname"
2623
2624class confstr_confname_converter(path_confname_converter):
2625 converter='conv_confstr_confname'
2626
2627class sysconf_confname_converter(path_confname_converter):
2628 converter="conv_sysconf_confname"
2629
2630class sched_param_converter(CConverter):
2631 type = 'struct sched_param'
2632 converter = 'convert_sched_param'
2633 impl_by_reference = True;
Larry Hastings31826802013-10-19 00:09:25 -07002634
Larry Hastings61272b72014-01-07 12:41:53 -08002635[python start generated code]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002636/*[python end generated code: output=da39a3ee5e6b4b0d input=147ba8f52a05aca4]*/
Larry Hastings31826802013-10-19 00:09:25 -07002637
Larry Hastings61272b72014-01-07 12:41:53 -08002638/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002639
Larry Hastings2a727912014-01-16 11:32:01 -08002640os.stat
Larry Hastings31826802013-10-19 00:09:25 -07002641
2642 path : path_t(allow_fd=True)
2643 Path to be examined; can be string, bytes, or open-file-descriptor int.
2644
2645 *
2646
Larry Hastings2f936352014-08-05 14:04:04 +10002647 dir_fd : dir_fd(requires='fstatat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002648 If not None, it should be a file descriptor open to a directory,
2649 and path should be a relative string; path will then be relative to
2650 that directory.
2651
2652 follow_symlinks: bool = True
2653 If False, and the last element of the path is a symbolic link,
2654 stat will examine the symbolic link itself instead of the file
2655 the link points to.
2656
2657Perform a stat system call on the given path.
2658
2659dir_fd and follow_symlinks may not be implemented
2660 on your platform. If they are unavailable, using them will raise a
2661 NotImplementedError.
2662
2663It's an error to use dir_fd or follow_symlinks when specifying path as
2664 an open file descriptor.
2665
Larry Hastings61272b72014-01-07 12:41:53 -08002666[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002667
2668PyDoc_STRVAR(os_stat__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002669"stat($module, /, path, *, dir_fd=None, follow_symlinks=True)\n"
2670"--\n"
2671"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002672"Perform a stat system call on the given path.\n"
2673"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002674" path\n"
2675" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
2676" dir_fd\n"
2677" If not None, it should be a file descriptor open to a directory,\n"
2678" and path should be a relative string; path will then be relative to\n"
2679" that directory.\n"
2680" follow_symlinks\n"
2681" If False, and the last element of the path is a symbolic link,\n"
2682" stat will examine the symbolic link itself instead of the file\n"
2683" the link points to.\n"
2684"\n"
2685"dir_fd and follow_symlinks may not be implemented\n"
2686" on your platform. If they are unavailable, using them will raise a\n"
2687" NotImplementedError.\n"
2688"\n"
2689"It\'s an error to use dir_fd or follow_symlinks when specifying path as\n"
2690" an open file descriptor.");
2691
2692#define OS_STAT_METHODDEF \
2693 {"stat", (PyCFunction)os_stat, METH_VARARGS|METH_KEYWORDS, os_stat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002694
2695static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002696os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002697
2698static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002699os_stat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002700{
Larry Hastings31826802013-10-19 00:09:25 -07002701 PyObject *return_value = NULL;
2702 static char *_keywords[] = {"path", "dir_fd", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002703 path_t path = PATH_T_INITIALIZE("stat", "path", 0, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002704 int dir_fd = DEFAULT_DIR_FD;
2705 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002706
Larry Hastings31826802013-10-19 00:09:25 -07002707 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2708 "O&|$O&p:stat", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002709 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002710 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08002711 return_value = os_stat_impl(module, &path, dir_fd, follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002712
2713exit:
2714 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002715 path_cleanup(&path);
Larry Hastings31826802013-10-19 00:09:25 -07002716
Larry Hastings9cf065c2012-06-22 16:30:09 -07002717 return return_value;
2718}
2719
Larry Hastings31826802013-10-19 00:09:25 -07002720static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002721os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002722/*[clinic end generated code: output=0e9f9508fa0c0607 input=099d356c306fa24a]*/
Larry Hastings31826802013-10-19 00:09:25 -07002723{
2724 return posix_do_stat("stat", path, dir_fd, follow_symlinks);
2725}
2726
Larry Hastings2f936352014-08-05 14:04:04 +10002727
2728/*[clinic input]
2729os.lstat
2730
2731 path : path_t
2732
2733 *
2734
2735 dir_fd : dir_fd(requires='fstatat') = None
2736
2737Perform a stat system call on the given path, without following symbolic links.
2738
2739Like stat(), but do not follow symbolic links.
2740Equivalent to stat(path, follow_symlinks=False).
2741[clinic start generated code]*/
2742
2743PyDoc_STRVAR(os_lstat__doc__,
2744"lstat($module, /, path, *, dir_fd=None)\n"
2745"--\n"
2746"\n"
2747"Perform a stat system call on the given path, without following symbolic links.\n"
2748"\n"
2749"Like stat(), but do not follow symbolic links.\n"
2750"Equivalent to stat(path, follow_symlinks=False).");
2751
2752#define OS_LSTAT_METHODDEF \
2753 {"lstat", (PyCFunction)os_lstat, METH_VARARGS|METH_KEYWORDS, os_lstat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002754
2755static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10002756os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002757
Larry Hastings2f936352014-08-05 14:04:04 +10002758static PyObject *
2759os_lstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
2760{
2761 PyObject *return_value = NULL;
2762 static char *_keywords[] = {"path", "dir_fd", NULL};
2763 path_t path = PATH_T_INITIALIZE("lstat", "path", 0, 0);
2764 int dir_fd = DEFAULT_DIR_FD;
2765
2766 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2767 "O&|$O&:lstat", _keywords,
2768 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd))
2769 goto exit;
2770 return_value = os_lstat_impl(module, &path, dir_fd);
2771
2772exit:
2773 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002774 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10002775
Larry Hastings9cf065c2012-06-22 16:30:09 -07002776 return return_value;
2777}
2778
Larry Hastings2f936352014-08-05 14:04:04 +10002779static PyObject *
2780os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd)
2781/*[clinic end generated code: output=85702247224a2b1c input=0b7474765927b925]*/
2782{
2783 int follow_symlinks = 0;
2784 return posix_do_stat("lstat", path, dir_fd, follow_symlinks);
2785}
Larry Hastings31826802013-10-19 00:09:25 -07002786
Larry Hastings2f936352014-08-05 14:04:04 +10002787
Larry Hastings61272b72014-01-07 12:41:53 -08002788/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +10002789os.access -> bool
Larry Hastings31826802013-10-19 00:09:25 -07002790
2791 path: path_t(allow_fd=True)
2792 Path to be tested; can be string, bytes, or open-file-descriptor int.
2793
2794 mode: int
2795 Operating-system mode bitfield. Can be F_OK to test existence,
2796 or the inclusive-OR of R_OK, W_OK, and X_OK.
2797
2798 *
2799
Larry Hastings2f936352014-08-05 14:04:04 +10002800 dir_fd : dir_fd(requires='faccessat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002801 If not None, it should be a file descriptor open to a directory,
2802 and path should be relative; path will then be relative to that
2803 directory.
2804
2805 effective_ids: bool = False
2806 If True, access will use the effective uid/gid instead of
2807 the real uid/gid.
2808
2809 follow_symlinks: bool = True
2810 If False, and the last element of the path is a symbolic link,
2811 access will examine the symbolic link itself instead of the file
2812 the link points to.
2813
2814Use the real uid/gid to test for access to a path.
2815
2816{parameters}
2817dir_fd, effective_ids, and follow_symlinks may not be implemented
2818 on your platform. If they are unavailable, using them will raise a
2819 NotImplementedError.
2820
2821Note that most operations will use the effective uid/gid, therefore this
2822 routine can be used in a suid/sgid environment to test if the invoking user
2823 has the specified access to the path.
2824
Larry Hastings61272b72014-01-07 12:41:53 -08002825[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002826
2827PyDoc_STRVAR(os_access__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002828"access($module, /, path, mode, *, dir_fd=None, effective_ids=False,\n"
2829" follow_symlinks=True)\n"
2830"--\n"
2831"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002832"Use the real uid/gid to test for access to a path.\n"
2833"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002834" path\n"
2835" Path to be tested; can be string, bytes, or open-file-descriptor int.\n"
2836" mode\n"
2837" Operating-system mode bitfield. Can be F_OK to test existence,\n"
2838" or the inclusive-OR of R_OK, W_OK, and X_OK.\n"
2839" dir_fd\n"
2840" If not None, it should be a file descriptor open to a directory,\n"
2841" and path should be relative; path will then be relative to that\n"
2842" directory.\n"
2843" effective_ids\n"
2844" If True, access will use the effective uid/gid instead of\n"
2845" the real uid/gid.\n"
2846" follow_symlinks\n"
2847" If False, and the last element of the path is a symbolic link,\n"
2848" access will examine the symbolic link itself instead of the file\n"
2849" the link points to.\n"
2850"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002851"dir_fd, effective_ids, and follow_symlinks may not be implemented\n"
2852" on your platform. If they are unavailable, using them will raise a\n"
2853" NotImplementedError.\n"
2854"\n"
2855"Note that most operations will use the effective uid/gid, therefore this\n"
2856" routine can be used in a suid/sgid environment to test if the invoking user\n"
2857" has the specified access to the path.");
2858
2859#define OS_ACCESS_METHODDEF \
2860 {"access", (PyCFunction)os_access, METH_VARARGS|METH_KEYWORDS, os_access__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002861
Larry Hastings2f936352014-08-05 14:04:04 +10002862static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002863os_access_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int effective_ids, int follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002864
2865static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002866os_access(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002867{
Larry Hastings31826802013-10-19 00:09:25 -07002868 PyObject *return_value = NULL;
2869 static char *_keywords[] = {"path", "mode", "dir_fd", "effective_ids", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002870 path_t path = PATH_T_INITIALIZE("access", "path", 0, 1);
Victor Stinner8c62be82010-05-06 00:08:46 +00002871 int mode;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002872 int dir_fd = DEFAULT_DIR_FD;
2873 int effective_ids = 0;
2874 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10002875 int _return_value;
Larry Hastings31826802013-10-19 00:09:25 -07002876
2877 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2878 "O&i|$O&pp:access", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002879 path_converter, &path, &mode, FACCESSAT_DIR_FD_CONVERTER, &dir_fd, &effective_ids, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002880 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +10002881 _return_value = os_access_impl(module, &path, mode, dir_fd, effective_ids, follow_symlinks);
2882 if ((_return_value == -1) && PyErr_Occurred())
2883 goto exit;
2884 return_value = PyBool_FromLong((long)_return_value);
Larry Hastings31826802013-10-19 00:09:25 -07002885
2886exit:
2887 /* Cleanup for path */
2888 path_cleanup(&path);
2889
2890 return return_value;
2891}
2892
Larry Hastings2f936352014-08-05 14:04:04 +10002893static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002894os_access_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int effective_ids, int follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002895/*[clinic end generated code: output=dfd404666906f012 input=b75a756797af45ec]*/
Larry Hastings31826802013-10-19 00:09:25 -07002896{
Larry Hastings2f936352014-08-05 14:04:04 +10002897 int return_value;
Victor Stinner8c62be82010-05-06 00:08:46 +00002898
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002899#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002900 DWORD attr;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002901#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07002902 int result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002903#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07002904
Larry Hastings9cf065c2012-06-22 16:30:09 -07002905#ifndef HAVE_FACCESSAT
2906 if (follow_symlinks_specified("access", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002907 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002908
2909 if (effective_ids) {
2910 argument_unavailable_error("access", "effective_ids");
Larry Hastings2f936352014-08-05 14:04:04 +10002911 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002912 }
2913#endif
2914
2915#ifdef MS_WINDOWS
2916 Py_BEGIN_ALLOW_THREADS
Christian Heimesebe83f92013-10-19 22:36:17 +02002917 if (path->wide != NULL)
2918 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002919 else
Christian Heimesebe83f92013-10-19 22:36:17 +02002920 attr = GetFileAttributesA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002921 Py_END_ALLOW_THREADS
2922
2923 /*
Georg Brandlf7875592012-06-24 13:58:31 +02002924 * Access is possible if
Larry Hastings9cf065c2012-06-22 16:30:09 -07002925 * * we didn't get a -1, and
2926 * * write access wasn't requested,
2927 * * or the file isn't read-only,
2928 * * or it's a directory.
2929 * (Directories cannot be read-only on Windows.)
2930 */
Larry Hastings2f936352014-08-05 14:04:04 +10002931 return_value = (attr != INVALID_FILE_ATTRIBUTES) &&
Georg Brandl5bb7aa92012-06-23 12:48:40 +02002932 (!(mode & 2) ||
Larry Hastings9cf065c2012-06-22 16:30:09 -07002933 !(attr & FILE_ATTRIBUTE_READONLY) ||
Larry Hastings2f936352014-08-05 14:04:04 +10002934 (attr & FILE_ATTRIBUTE_DIRECTORY));
Larry Hastings9cf065c2012-06-22 16:30:09 -07002935#else
2936
2937 Py_BEGIN_ALLOW_THREADS
2938#ifdef HAVE_FACCESSAT
2939 if ((dir_fd != DEFAULT_DIR_FD) ||
2940 effective_ids ||
2941 !follow_symlinks) {
2942 int flags = 0;
2943 if (!follow_symlinks)
2944 flags |= AT_SYMLINK_NOFOLLOW;
2945 if (effective_ids)
2946 flags |= AT_EACCESS;
Larry Hastings31826802013-10-19 00:09:25 -07002947 result = faccessat(dir_fd, path->narrow, mode, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002948 }
2949 else
2950#endif
Larry Hastings31826802013-10-19 00:09:25 -07002951 result = access(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002952 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002953 return_value = !result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002954#endif
2955
Larry Hastings9cf065c2012-06-22 16:30:09 -07002956 return return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002957}
2958
Guido van Rossumd371ff11999-01-25 16:12:23 +00002959#ifndef F_OK
2960#define F_OK 0
2961#endif
2962#ifndef R_OK
2963#define R_OK 4
2964#endif
2965#ifndef W_OK
2966#define W_OK 2
2967#endif
2968#ifndef X_OK
2969#define X_OK 1
2970#endif
2971
Larry Hastings31826802013-10-19 00:09:25 -07002972
Guido van Rossumd371ff11999-01-25 16:12:23 +00002973#ifdef HAVE_TTYNAME
Larry Hastings61272b72014-01-07 12:41:53 -08002974/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002975os.ttyname -> DecodeFSDefault
2976
2977 fd: int
2978 Integer file descriptor handle.
2979
2980 /
2981
2982Return the name of the terminal device connected to 'fd'.
Larry Hastings61272b72014-01-07 12:41:53 -08002983[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002984
2985PyDoc_STRVAR(os_ttyname__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002986"ttyname($module, fd, /)\n"
2987"--\n"
2988"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002989"Return the name of the terminal device connected to \'fd\'.\n"
2990"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002991" fd\n"
2992" Integer file descriptor handle.");
2993
2994#define OS_TTYNAME_METHODDEF \
2995 {"ttyname", (PyCFunction)os_ttyname, METH_VARARGS, os_ttyname__doc__},
2996
2997static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002998os_ttyname_impl(PyModuleDef *module, int fd);
Guido van Rossum94f6f721999-01-06 18:42:14 +00002999
3000static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003001os_ttyname(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +00003002{
Larry Hastings31826802013-10-19 00:09:25 -07003003 PyObject *return_value = NULL;
3004 int fd;
3005 char *_return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003006
Larry Hastings31826802013-10-19 00:09:25 -07003007 if (!PyArg_ParseTuple(args,
3008 "i:ttyname",
3009 &fd))
3010 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08003011 _return_value = os_ttyname_impl(module, fd);
Larry Hastings31826802013-10-19 00:09:25 -07003012 if (_return_value == NULL)
3013 goto exit;
3014 return_value = PyUnicode_DecodeFSDefault(_return_value);
3015
3016exit:
3017 return return_value;
3018}
3019
3020static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003021os_ttyname_impl(PyModuleDef *module, int fd)
Larry Hastings2623c8c2014-02-08 22:15:29 -08003022/*[clinic end generated code: output=cee7bc4cffec01a2 input=5f72ca83e76b3b45]*/
Larry Hastings31826802013-10-19 00:09:25 -07003023{
3024 char *ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003025
Larry Hastings31826802013-10-19 00:09:25 -07003026 ret = ttyname(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00003027 if (ret == NULL)
Larry Hastings31826802013-10-19 00:09:25 -07003028 posix_error();
3029 return ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003030}
Guido van Rossumd371ff11999-01-25 16:12:23 +00003031#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00003032
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003033#ifdef HAVE_CTERMID
Larry Hastings2f936352014-08-05 14:04:04 +10003034/*[clinic input]
3035os.ctermid
3036
3037Return the name of the controlling terminal for this process.
3038[clinic start generated code]*/
3039
3040PyDoc_STRVAR(os_ctermid__doc__,
3041"ctermid($module, /)\n"
3042"--\n"
3043"\n"
3044"Return the name of the controlling terminal for this process.");
3045
3046#define OS_CTERMID_METHODDEF \
3047 {"ctermid", (PyCFunction)os_ctermid, METH_NOARGS, os_ctermid__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003048
3049static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003050os_ctermid_impl(PyModuleDef *module);
3051
3052static PyObject *
3053os_ctermid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3054{
3055 return os_ctermid_impl(module);
3056}
3057
3058static PyObject *
3059os_ctermid_impl(PyModuleDef *module)
3060/*[clinic end generated code: output=277bf7964ec2d782 input=3b87fdd52556382d]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003061{
Victor Stinner8c62be82010-05-06 00:08:46 +00003062 char *ret;
3063 char buffer[L_ctermid];
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003064
Greg Wardb48bc172000-03-01 21:51:56 +00003065#ifdef USE_CTERMID_R
Victor Stinner8c62be82010-05-06 00:08:46 +00003066 ret = ctermid_r(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003067#else
Victor Stinner8c62be82010-05-06 00:08:46 +00003068 ret = ctermid(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003069#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00003070 if (ret == NULL)
3071 return posix_error();
Victor Stinner5fe6de82010-08-15 09:12:51 +00003072 return PyUnicode_DecodeFSDefault(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003073}
Larry Hastings2f936352014-08-05 14:04:04 +10003074#endif /* HAVE_CTERMID */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003075
Larry Hastings2f936352014-08-05 14:04:04 +10003076
3077/*[clinic input]
3078os.chdir
3079
3080 path: path_t(allow_fd='PATH_HAVE_FCHDIR')
3081
3082Change the current working directory to the specified path.
3083
3084path may always be specified as a string.
3085On some platforms, path may also be specified as an open file descriptor.
3086 If this functionality is unavailable, using it raises an exception.
3087[clinic start generated code]*/
3088
3089PyDoc_STRVAR(os_chdir__doc__,
3090"chdir($module, /, path)\n"
3091"--\n"
3092"\n"
3093"Change the current working directory to the specified path.\n"
3094"\n"
3095"path may always be specified as a string.\n"
3096"On some platforms, path may also be specified as an open file descriptor.\n"
3097" If this functionality is unavailable, using it raises an exception.");
3098
3099#define OS_CHDIR_METHODDEF \
3100 {"chdir", (PyCFunction)os_chdir, METH_VARARGS|METH_KEYWORDS, os_chdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003101
Barry Warsaw53699e91996-12-10 23:23:01 +00003102static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003103os_chdir_impl(PyModuleDef *module, path_t *path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003104
Larry Hastings2f936352014-08-05 14:04:04 +10003105static PyObject *
3106os_chdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3107{
3108 PyObject *return_value = NULL;
3109 static char *_keywords[] = {"path", NULL};
3110 path_t path = PATH_T_INITIALIZE("chdir", "path", 0, PATH_HAVE_FCHDIR);
3111
3112 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3113 "O&:chdir", _keywords,
3114 path_converter, &path))
3115 goto exit;
3116 return_value = os_chdir_impl(module, &path);
3117
3118exit:
3119 /* Cleanup for path */
3120 path_cleanup(&path);
3121
3122 return return_value;
3123}
3124
3125static PyObject *
3126os_chdir_impl(PyModuleDef *module, path_t *path)
3127/*[clinic end generated code: output=cc07592dd23ca9e0 input=1a4a15b4d12cb15d]*/
3128{
3129 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003130
3131 Py_BEGIN_ALLOW_THREADS
3132#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10003133 if (path->wide)
3134 result = win32_wchdir(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003135 else
Larry Hastings2f936352014-08-05 14:04:04 +10003136 result = win32_chdir(path->narrow);
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03003137 result = !result; /* on unix, success = 0, on windows, success = !0 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003138#else
3139#ifdef HAVE_FCHDIR
Larry Hastings2f936352014-08-05 14:04:04 +10003140 if (path->fd != -1)
3141 result = fchdir(path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003142 else
3143#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003144 result = chdir(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003145#endif
3146 Py_END_ALLOW_THREADS
3147
3148 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003149 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003150 }
3151
Larry Hastings2f936352014-08-05 14:04:04 +10003152 Py_RETURN_NONE;
3153}
3154
3155
3156#ifdef HAVE_FCHDIR
3157/*[clinic input]
3158os.fchdir
3159
3160 fd: fildes
3161
3162Change to the directory of the given file descriptor.
3163
3164fd must be opened on a directory, not a file.
3165Equivalent to os.chdir(fd).
3166
3167[clinic start generated code]*/
3168
3169PyDoc_STRVAR(os_fchdir__doc__,
3170"fchdir($module, /, fd)\n"
3171"--\n"
3172"\n"
3173"Change to the directory of the given file descriptor.\n"
3174"\n"
3175"fd must be opened on a directory, not a file.\n"
3176"Equivalent to os.chdir(fd).");
3177
3178#define OS_FCHDIR_METHODDEF \
3179 {"fchdir", (PyCFunction)os_fchdir, METH_VARARGS|METH_KEYWORDS, os_fchdir__doc__},
3180
3181static PyObject *
3182os_fchdir_impl(PyModuleDef *module, int fd);
3183
3184static PyObject *
3185os_fchdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3186{
3187 PyObject *return_value = NULL;
3188 static char *_keywords[] = {"fd", NULL};
3189 int fd;
3190
3191 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3192 "O&:fchdir", _keywords,
3193 fildes_converter, &fd))
3194 goto exit;
3195 return_value = os_fchdir_impl(module, fd);
Georg Brandlf7875592012-06-24 13:58:31 +02003196
Larry Hastings9cf065c2012-06-22 16:30:09 -07003197exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07003198 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003199}
3200
Fred Drake4d1e64b2002-04-15 19:40:07 +00003201static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003202os_fchdir_impl(PyModuleDef *module, int fd)
3203/*[clinic end generated code: output=9f6dbc89b2778834 input=18e816479a2fa985]*/
Fred Drake4d1e64b2002-04-15 19:40:07 +00003204{
Larry Hastings2f936352014-08-05 14:04:04 +10003205 return posix_fildes_fd(fd, fchdir);
Fred Drake4d1e64b2002-04-15 19:40:07 +00003206}
3207#endif /* HAVE_FCHDIR */
3208
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003209
Larry Hastings2f936352014-08-05 14:04:04 +10003210/*[clinic input]
3211os.chmod
3212
3213 path: path_t(allow_fd='PATH_HAVE_FCHMOD')
3214 Path to be modified. May always be specified as a str or bytes.
3215 On some platforms, path may also be specified as an open file descriptor.
3216 If this functionality is unavailable, using it raises an exception.
3217
3218 mode: int
3219 Operating-system mode bitfield.
3220
3221 *
3222
3223 dir_fd : dir_fd(requires='fchmodat') = None
3224 If not None, it should be a file descriptor open to a directory,
3225 and path should be relative; path will then be relative to that
3226 directory.
3227
3228 follow_symlinks: bool = True
3229 If False, and the last element of the path is a symbolic link,
3230 chmod will modify the symbolic link itself instead of the file
3231 the link points to.
3232
3233Change the access permissions of a file.
3234
3235It is an error to use dir_fd or follow_symlinks when specifying path as
3236 an open file descriptor.
3237dir_fd and follow_symlinks may not be implemented on your platform.
3238 If they are unavailable, using them will raise a NotImplementedError.
3239
3240[clinic start generated code]*/
3241
3242PyDoc_STRVAR(os_chmod__doc__,
3243"chmod($module, /, path, mode, *, dir_fd=None, follow_symlinks=True)\n"
3244"--\n"
3245"\n"
3246"Change the access permissions of a file.\n"
3247"\n"
3248" path\n"
3249" Path to be modified. May always be specified as a str or bytes.\n"
3250" On some platforms, path may also be specified as an open file descriptor.\n"
3251" If this functionality is unavailable, using it raises an exception.\n"
3252" mode\n"
3253" Operating-system mode bitfield.\n"
3254" dir_fd\n"
3255" If not None, it should be a file descriptor open to a directory,\n"
3256" and path should be relative; path will then be relative to that\n"
3257" directory.\n"
3258" follow_symlinks\n"
3259" If False, and the last element of the path is a symbolic link,\n"
3260" chmod will modify the symbolic link itself instead of the file\n"
3261" the link points to.\n"
3262"\n"
3263"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3264" an open file descriptor.\n"
3265"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3266" If they are unavailable, using them will raise a NotImplementedError.");
3267
3268#define OS_CHMOD_METHODDEF \
3269 {"chmod", (PyCFunction)os_chmod, METH_VARARGS|METH_KEYWORDS, os_chmod__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003270
Barry Warsaw53699e91996-12-10 23:23:01 +00003271static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003272os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks);
3273
3274static PyObject *
3275os_chmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003276{
Larry Hastings2f936352014-08-05 14:04:04 +10003277 PyObject *return_value = NULL;
3278 static char *_keywords[] = {"path", "mode", "dir_fd", "follow_symlinks", NULL};
3279 path_t path = PATH_T_INITIALIZE("chmod", "path", 0, PATH_HAVE_FCHMOD);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003280 int mode;
3281 int dir_fd = DEFAULT_DIR_FD;
3282 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10003283
3284 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3285 "O&i|$O&p:chmod", _keywords,
3286 path_converter, &path, &mode, FCHMODAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3287 goto exit;
3288 return_value = os_chmod_impl(module, &path, mode, dir_fd, follow_symlinks);
3289
3290exit:
3291 /* Cleanup for path */
3292 path_cleanup(&path);
3293
3294 return return_value;
3295}
3296
3297static PyObject *
3298os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks)
3299/*[clinic end generated code: output=1e9db031aea46422 input=7f1618e5e15cc196]*/
3300{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003301 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003302
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003303#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003304 DWORD attr;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003305#endif
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00003306
Larry Hastings9cf065c2012-06-22 16:30:09 -07003307#ifdef HAVE_FCHMODAT
3308 int fchmodat_nofollow_unsupported = 0;
3309#endif
3310
Larry Hastings9cf065c2012-06-22 16:30:09 -07003311#if !(defined(HAVE_FCHMODAT) || defined(HAVE_LCHMOD))
3312 if (follow_symlinks_specified("chmod", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003313 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003314#endif
3315
3316#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003317 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003318 if (path->wide)
3319 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003320 else
Larry Hastings2f936352014-08-05 14:04:04 +10003321 attr = GetFileAttributesA(path->narrow);
Tim Golden23005082013-10-25 11:22:37 +01003322 if (attr == INVALID_FILE_ATTRIBUTES)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003323 result = 0;
3324 else {
3325 if (mode & _S_IWRITE)
Victor Stinner8c62be82010-05-06 00:08:46 +00003326 attr &= ~FILE_ATTRIBUTE_READONLY;
3327 else
3328 attr |= FILE_ATTRIBUTE_READONLY;
Larry Hastings2f936352014-08-05 14:04:04 +10003329 if (path->wide)
3330 result = SetFileAttributesW(path->wide, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003331 else
Larry Hastings2f936352014-08-05 14:04:04 +10003332 result = SetFileAttributesA(path->narrow, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003333 }
3334 Py_END_ALLOW_THREADS
3335
3336 if (!result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003337 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003338 }
3339#else /* MS_WINDOWS */
3340 Py_BEGIN_ALLOW_THREADS
3341#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003342 if (path->fd != -1)
3343 result = fchmod(path->fd, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003344 else
3345#endif
3346#ifdef HAVE_LCHMOD
3347 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003348 result = lchmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003349 else
3350#endif
3351#ifdef HAVE_FCHMODAT
3352 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks) {
3353 /*
3354 * fchmodat() doesn't currently support AT_SYMLINK_NOFOLLOW!
3355 * The documentation specifically shows how to use it,
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003356 * and then says it isn't implemented yet.
3357 * (true on linux with glibc 2.15, and openindiana 3.x)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003358 *
3359 * Once it is supported, os.chmod will automatically
3360 * support dir_fd and follow_symlinks=False. (Hopefully.)
3361 * Until then, we need to be careful what exception we raise.
3362 */
Larry Hastings2f936352014-08-05 14:04:04 +10003363 result = fchmodat(dir_fd, path->narrow, mode,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003364 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3365 /*
3366 * But wait! We can't throw the exception without allowing threads,
3367 * and we can't do that in this nested scope. (Macro trickery, sigh.)
3368 */
3369 fchmodat_nofollow_unsupported =
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003370 result &&
3371 ((errno == ENOTSUP) || (errno == EOPNOTSUPP)) &&
3372 !follow_symlinks;
Victor Stinner8c62be82010-05-06 00:08:46 +00003373 }
3374 else
Thomas Wouters477c8d52006-05-27 19:21:47 +00003375#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003376 result = chmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003377 Py_END_ALLOW_THREADS
3378
3379 if (result) {
3380#ifdef HAVE_FCHMODAT
3381 if (fchmodat_nofollow_unsupported) {
3382 if (dir_fd != DEFAULT_DIR_FD)
3383 dir_fd_and_follow_symlinks_invalid("chmod",
3384 dir_fd, follow_symlinks);
3385 else
3386 follow_symlinks_specified("chmod", follow_symlinks);
3387 }
3388 else
3389#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003390 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003391 }
3392#endif
3393
Larry Hastings2f936352014-08-05 14:04:04 +10003394 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003395}
3396
Larry Hastings9cf065c2012-06-22 16:30:09 -07003397
Christian Heimes4e30a842007-11-30 22:12:06 +00003398#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003399/*[clinic input]
3400os.fchmod
3401
3402 fd: int
3403 mode: int
3404
3405Change the access permissions of the file given by file descriptor fd.
3406
3407Equivalent to os.chmod(fd, mode).
3408[clinic start generated code]*/
3409
3410PyDoc_STRVAR(os_fchmod__doc__,
3411"fchmod($module, /, fd, mode)\n"
3412"--\n"
3413"\n"
3414"Change the access permissions of the file given by file descriptor fd.\n"
3415"\n"
3416"Equivalent to os.chmod(fd, mode).");
3417
3418#define OS_FCHMOD_METHODDEF \
3419 {"fchmod", (PyCFunction)os_fchmod, METH_VARARGS|METH_KEYWORDS, os_fchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003420
3421static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003422os_fchmod_impl(PyModuleDef *module, int fd, int mode);
3423
3424static PyObject *
3425os_fchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003426{
Larry Hastings2f936352014-08-05 14:04:04 +10003427 PyObject *return_value = NULL;
3428 static char *_keywords[] = {"fd", "mode", NULL};
3429 int fd;
3430 int mode;
3431
3432 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3433 "ii:fchmod", _keywords,
3434 &fd, &mode))
3435 goto exit;
3436 return_value = os_fchmod_impl(module, fd, mode);
3437
3438exit:
3439 return return_value;
3440}
3441
3442static PyObject *
3443os_fchmod_impl(PyModuleDef *module, int fd, int mode)
3444/*[clinic end generated code: output=3c19fbfd724a8e0f input=8ab11975ca01ee5b]*/
3445{
3446 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003447 Py_BEGIN_ALLOW_THREADS
3448 res = fchmod(fd, mode);
3449 Py_END_ALLOW_THREADS
3450 if (res < 0)
3451 return posix_error();
3452 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003453}
3454#endif /* HAVE_FCHMOD */
3455
Larry Hastings2f936352014-08-05 14:04:04 +10003456
Christian Heimes4e30a842007-11-30 22:12:06 +00003457#ifdef HAVE_LCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003458/*[clinic input]
3459os.lchmod
3460
3461 path: path_t
3462 mode: int
3463
3464Change the access permissions of a file, without following symbolic links.
3465
3466If path is a symlink, this affects the link itself rather than the target.
3467Equivalent to chmod(path, mode, follow_symlinks=False)."
3468[clinic start generated code]*/
3469
3470PyDoc_STRVAR(os_lchmod__doc__,
3471"lchmod($module, /, path, mode)\n"
3472"--\n"
3473"\n"
3474"Change the access permissions of a file, without following symbolic links.\n"
3475"\n"
3476"If path is a symlink, this affects the link itself rather than the target.\n"
3477"Equivalent to chmod(path, mode, follow_symlinks=False).\"");
3478
3479#define OS_LCHMOD_METHODDEF \
3480 {"lchmod", (PyCFunction)os_lchmod, METH_VARARGS|METH_KEYWORDS, os_lchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003481
3482static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003483os_lchmod_impl(PyModuleDef *module, path_t *path, int mode);
3484
3485static PyObject *
3486os_lchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003487{
Larry Hastings2f936352014-08-05 14:04:04 +10003488 PyObject *return_value = NULL;
3489 static char *_keywords[] = {"path", "mode", NULL};
3490 path_t path = PATH_T_INITIALIZE("lchmod", "path", 0, 0);
3491 int mode;
3492
3493 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3494 "O&i:lchmod", _keywords,
3495 path_converter, &path, &mode))
3496 goto exit;
3497 return_value = os_lchmod_impl(module, &path, mode);
3498
3499exit:
3500 /* Cleanup for path */
3501 path_cleanup(&path);
3502
3503 return return_value;
3504}
3505
3506static PyObject *
3507os_lchmod_impl(PyModuleDef *module, path_t *path, int mode)
3508/*[clinic end generated code: output=2849977d65f8c68c input=90c5663c7465d24f]*/
3509{
Victor Stinner8c62be82010-05-06 00:08:46 +00003510 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003511 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003512 res = lchmod(path->narrow, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +00003513 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003514 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003515 path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003516 return NULL;
3517 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003518 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003519}
3520#endif /* HAVE_LCHMOD */
3521
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003522
Thomas Wouterscf297e42007-02-23 15:07:44 +00003523#ifdef HAVE_CHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003524/*[clinic input]
3525os.chflags
3526
3527 path: path_t
3528 flags: unsigned_long(bitwise=True)
3529 follow_symlinks: bool=True
3530
3531Set file flags.
3532
3533If follow_symlinks is False, and the last element of the path is a symbolic
3534 link, chflags will change flags on the symbolic link itself instead of the
3535 file the link points to.
3536follow_symlinks may not be implemented on your platform. If it is
3537unavailable, using it will raise a NotImplementedError.
3538
3539[clinic start generated code]*/
3540
3541PyDoc_STRVAR(os_chflags__doc__,
3542"chflags($module, /, path, flags, follow_symlinks=True)\n"
3543"--\n"
3544"\n"
3545"Set file flags.\n"
3546"\n"
3547"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3548" link, chflags will change flags on the symbolic link itself instead of the\n"
3549" file the link points to.\n"
3550"follow_symlinks may not be implemented on your platform. If it is\n"
3551"unavailable, using it will raise a NotImplementedError.");
3552
3553#define OS_CHFLAGS_METHODDEF \
3554 {"chflags", (PyCFunction)os_chflags, METH_VARARGS|METH_KEYWORDS, os_chflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003555
3556static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003557os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks);
3558
3559static PyObject *
3560os_chflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003561{
Larry Hastings2f936352014-08-05 14:04:04 +10003562 PyObject *return_value = NULL;
3563 static char *_keywords[] = {"path", "flags", "follow_symlinks", NULL};
3564 path_t path = PATH_T_INITIALIZE("chflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003565 unsigned long flags;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003566 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003567
Larry Hastings2f936352014-08-05 14:04:04 +10003568 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3569 "O&k|p:chflags", _keywords,
3570 path_converter, &path, &flags, &follow_symlinks))
3571 goto exit;
3572 return_value = os_chflags_impl(module, &path, flags, follow_symlinks);
3573
3574exit:
3575 /* Cleanup for path */
3576 path_cleanup(&path);
3577
3578 return return_value;
3579}
3580
3581static PyObject *
3582os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks)
3583/*[clinic end generated code: output=2767927bf071e3cf input=0327e29feb876236]*/
3584{
3585 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003586
3587#ifndef HAVE_LCHFLAGS
3588 if (follow_symlinks_specified("chflags", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003589 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003590#endif
3591
Victor Stinner8c62be82010-05-06 00:08:46 +00003592 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003593#ifdef HAVE_LCHFLAGS
3594 if (!follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10003595 result = lchflags(path->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003596 else
3597#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003598 result = chflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003599 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003600
Larry Hastings2f936352014-08-05 14:04:04 +10003601 if (result)
3602 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003603
Larry Hastings2f936352014-08-05 14:04:04 +10003604 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003605}
3606#endif /* HAVE_CHFLAGS */
3607
Larry Hastings2f936352014-08-05 14:04:04 +10003608
Thomas Wouterscf297e42007-02-23 15:07:44 +00003609#ifdef HAVE_LCHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003610/*[clinic input]
3611os.lchflags
3612
3613 path: path_t
3614 flags: unsigned_long(bitwise=True)
3615
3616Set file flags.
3617
3618This function will not follow symbolic links.
3619Equivalent to chflags(path, flags, follow_symlinks=False).
3620[clinic start generated code]*/
3621
3622PyDoc_STRVAR(os_lchflags__doc__,
3623"lchflags($module, /, path, flags)\n"
3624"--\n"
3625"\n"
3626"Set file flags.\n"
3627"\n"
3628"This function will not follow symbolic links.\n"
3629"Equivalent to chflags(path, flags, follow_symlinks=False).");
3630
3631#define OS_LCHFLAGS_METHODDEF \
3632 {"lchflags", (PyCFunction)os_lchflags, METH_VARARGS|METH_KEYWORDS, os_lchflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003633
3634static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003635os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags);
3636
3637static PyObject *
3638os_lchflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003639{
Larry Hastings2f936352014-08-05 14:04:04 +10003640 PyObject *return_value = NULL;
3641 static char *_keywords[] = {"path", "flags", NULL};
3642 path_t path = PATH_T_INITIALIZE("lchflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003643 unsigned long flags;
Larry Hastings2f936352014-08-05 14:04:04 +10003644
3645 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3646 "O&k:lchflags", _keywords,
3647 path_converter, &path, &flags))
3648 goto exit;
3649 return_value = os_lchflags_impl(module, &path, flags);
3650
3651exit:
3652 /* Cleanup for path */
3653 path_cleanup(&path);
3654
3655 return return_value;
3656}
3657
3658static PyObject *
3659os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags)
3660/*[clinic end generated code: output=bb93b6b8a5e45aa7 input=f9f82ea8b585ca9d]*/
3661{
Victor Stinner8c62be82010-05-06 00:08:46 +00003662 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003663 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003664 res = lchflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003665 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003666 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003667 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003668 }
Victor Stinner292c8352012-10-30 02:17:38 +01003669 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003670}
3671#endif /* HAVE_LCHFLAGS */
3672
Larry Hastings2f936352014-08-05 14:04:04 +10003673
Martin v. Löwis244edc82001-10-04 22:44:26 +00003674#ifdef HAVE_CHROOT
Larry Hastings2f936352014-08-05 14:04:04 +10003675/*[clinic input]
3676os.chroot
3677 path: path_t
3678
3679Change root directory to path.
3680
3681[clinic start generated code]*/
3682
3683PyDoc_STRVAR(os_chroot__doc__,
3684"chroot($module, /, path)\n"
3685"--\n"
3686"\n"
3687"Change root directory to path.");
3688
3689#define OS_CHROOT_METHODDEF \
3690 {"chroot", (PyCFunction)os_chroot, METH_VARARGS|METH_KEYWORDS, os_chroot__doc__},
Martin v. Löwis244edc82001-10-04 22:44:26 +00003691
3692static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003693os_chroot_impl(PyModuleDef *module, path_t *path);
3694
3695static PyObject *
3696os_chroot(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis244edc82001-10-04 22:44:26 +00003697{
Larry Hastings2f936352014-08-05 14:04:04 +10003698 PyObject *return_value = NULL;
3699 static char *_keywords[] = {"path", NULL};
3700 path_t path = PATH_T_INITIALIZE("chroot", "path", 0, 0);
3701
3702 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3703 "O&:chroot", _keywords,
3704 path_converter, &path))
3705 goto exit;
3706 return_value = os_chroot_impl(module, &path);
3707
3708exit:
3709 /* Cleanup for path */
3710 path_cleanup(&path);
3711
3712 return return_value;
Martin v. Löwis244edc82001-10-04 22:44:26 +00003713}
Larry Hastings2f936352014-08-05 14:04:04 +10003714
3715static PyObject *
3716os_chroot_impl(PyModuleDef *module, path_t *path)
3717/*[clinic end generated code: output=15b1256cbe4f24a1 input=14822965652c3dc3]*/
3718{
3719 int res;
3720 Py_BEGIN_ALLOW_THREADS
3721 res = chroot(path->narrow);
3722 Py_END_ALLOW_THREADS
3723 if (res < 0)
3724 return path_error(path);
3725 Py_RETURN_NONE;
3726}
3727#endif /* HAVE_CHROOT */
3728
Martin v. Löwis244edc82001-10-04 22:44:26 +00003729
Guido van Rossum21142a01999-01-08 21:05:37 +00003730#ifdef HAVE_FSYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003731/*[clinic input]
3732os.fsync
3733
3734 fd: fildes
3735
3736Force write of fd to disk.
3737[clinic start generated code]*/
3738
3739PyDoc_STRVAR(os_fsync__doc__,
3740"fsync($module, /, fd)\n"
3741"--\n"
3742"\n"
3743"Force write of fd to disk.");
3744
3745#define OS_FSYNC_METHODDEF \
3746 {"fsync", (PyCFunction)os_fsync, METH_VARARGS|METH_KEYWORDS, os_fsync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003747
3748static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003749os_fsync_impl(PyModuleDef *module, int fd);
3750
3751static PyObject *
3752os_fsync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003753{
Larry Hastings2f936352014-08-05 14:04:04 +10003754 PyObject *return_value = NULL;
3755 static char *_keywords[] = {"fd", NULL};
3756 int fd;
3757
3758 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3759 "O&:fsync", _keywords,
3760 fildes_converter, &fd))
3761 goto exit;
3762 return_value = os_fsync_impl(module, fd);
3763
3764exit:
3765 return return_value;
3766}
3767
3768static PyObject *
3769os_fsync_impl(PyModuleDef *module, int fd)
3770/*[clinic end generated code: output=59f32d3a0b360133 input=21c3645c056967f2]*/
3771{
3772 return posix_fildes_fd(fd, fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003773}
3774#endif /* HAVE_FSYNC */
3775
Larry Hastings2f936352014-08-05 14:04:04 +10003776
Ross Lagerwall7807c352011-03-17 20:20:30 +02003777#ifdef HAVE_SYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003778/*[clinic input]
3779os.sync
3780
3781Force write of everything to disk.
3782[clinic start generated code]*/
3783
3784PyDoc_STRVAR(os_sync__doc__,
3785"sync($module, /)\n"
3786"--\n"
3787"\n"
3788"Force write of everything to disk.");
3789
3790#define OS_SYNC_METHODDEF \
3791 {"sync", (PyCFunction)os_sync, METH_NOARGS, os_sync__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02003792
3793static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003794os_sync_impl(PyModuleDef *module);
3795
3796static PyObject *
3797os_sync(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3798{
3799 return os_sync_impl(module);
3800}
3801
3802static PyObject *
3803os_sync_impl(PyModuleDef *module)
3804/*[clinic end generated code: output=526c495683d0bb38 input=84749fe5e9b404ff]*/
Ross Lagerwall7807c352011-03-17 20:20:30 +02003805{
3806 Py_BEGIN_ALLOW_THREADS
3807 sync();
3808 Py_END_ALLOW_THREADS
3809 Py_RETURN_NONE;
3810}
Larry Hastings2f936352014-08-05 14:04:04 +10003811#endif /* HAVE_SYNC */
3812
Ross Lagerwall7807c352011-03-17 20:20:30 +02003813
Guido van Rossum21142a01999-01-08 21:05:37 +00003814#ifdef HAVE_FDATASYNC
Guido van Rossum7f58e2e2000-09-22 17:26:14 +00003815#ifdef __hpux
Guido van Rossumecc23b02000-09-22 16:01:05 +00003816extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
3817#endif
3818
Larry Hastings2f936352014-08-05 14:04:04 +10003819/*[clinic input]
3820os.fdatasync
3821
3822 fd: fildes
3823
3824Force write of fd to disk without forcing update of metadata.
3825[clinic start generated code]*/
3826
3827PyDoc_STRVAR(os_fdatasync__doc__,
3828"fdatasync($module, /, fd)\n"
3829"--\n"
3830"\n"
3831"Force write of fd to disk without forcing update of metadata.");
3832
3833#define OS_FDATASYNC_METHODDEF \
3834 {"fdatasync", (PyCFunction)os_fdatasync, METH_VARARGS|METH_KEYWORDS, os_fdatasync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003835
3836static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003837os_fdatasync_impl(PyModuleDef *module, int fd);
3838
3839static PyObject *
3840os_fdatasync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003841{
Larry Hastings2f936352014-08-05 14:04:04 +10003842 PyObject *return_value = NULL;
3843 static char *_keywords[] = {"fd", NULL};
3844 int fd;
3845
3846 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3847 "O&:fdatasync", _keywords,
3848 fildes_converter, &fd))
3849 goto exit;
3850 return_value = os_fdatasync_impl(module, fd);
3851
3852exit:
3853 return return_value;
3854}
3855
3856static PyObject *
3857os_fdatasync_impl(PyModuleDef *module, int fd)
3858/*[clinic end generated code: output=2335fdfd37c92180 input=bc74791ee54dd291]*/
3859{
3860 return posix_fildes_fd(fd, fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003861}
3862#endif /* HAVE_FDATASYNC */
3863
3864
Fredrik Lundh10723342000-07-10 16:38:09 +00003865#ifdef HAVE_CHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003866/*[clinic input]
3867os.chown
3868
3869 path : path_t(allow_fd='PATH_HAVE_FCHOWN')
3870 Path to be examined; can be string, bytes, or open-file-descriptor int.
3871
3872 uid: uid_t
3873
3874 gid: gid_t
3875
3876 *
3877
3878 dir_fd : dir_fd(requires='fchownat') = None
3879 If not None, it should be a file descriptor open to a directory,
3880 and path should be relative; path will then be relative to that
3881 directory.
3882
3883 follow_symlinks: bool = True
3884 If False, and the last element of the path is a symbolic link,
3885 stat will examine the symbolic link itself instead of the file
3886 the link points to.
3887
3888Change the owner and group id of path to the numeric uid and gid.\
3889
3890path may always be specified as a string.
3891On some platforms, path may also be specified as an open file descriptor.
3892 If this functionality is unavailable, using it raises an exception.
3893If dir_fd is not None, it should be a file descriptor open to a directory,
3894 and path should be relative; path will then be relative to that directory.
3895If follow_symlinks is False, and the last element of the path is a symbolic
3896 link, chown will modify the symbolic link itself instead of the file the
3897 link points to.
3898It is an error to use dir_fd or follow_symlinks when specifying path as
3899 an open file descriptor.
3900dir_fd and follow_symlinks may not be implemented on your platform.
3901 If they are unavailable, using them will raise a NotImplementedError.
3902
3903[clinic start generated code]*/
3904
3905PyDoc_STRVAR(os_chown__doc__,
3906"chown($module, /, path, uid, gid, *, dir_fd=None, follow_symlinks=True)\n"
3907"--\n"
3908"\n"
3909"Change the owner and group id of path to the numeric uid and gid.\\\n"
3910"\n"
3911" path\n"
3912" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
3913" dir_fd\n"
3914" If not None, it should be a file descriptor open to a directory,\n"
3915" and path should be relative; path will then be relative to that\n"
3916" directory.\n"
3917" follow_symlinks\n"
3918" If False, and the last element of the path is a symbolic link,\n"
3919" stat will examine the symbolic link itself instead of the file\n"
3920" the link points to.\n"
3921"\n"
3922"path may always be specified as a string.\n"
3923"On some platforms, path may also be specified as an open file descriptor.\n"
3924" If this functionality is unavailable, using it raises an exception.\n"
3925"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
3926" and path should be relative; path will then be relative to that directory.\n"
3927"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3928" link, chown will modify the symbolic link itself instead of the file the\n"
3929" link points to.\n"
3930"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3931" an open file descriptor.\n"
3932"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3933" If they are unavailable, using them will raise a NotImplementedError.");
3934
3935#define OS_CHOWN_METHODDEF \
3936 {"chown", (PyCFunction)os_chown, METH_VARARGS|METH_KEYWORDS, os_chown__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003937
Barry Warsaw53699e91996-12-10 23:23:01 +00003938static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003939os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks);
3940
3941static PyObject *
3942os_chown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumb6775db1994-08-01 11:34:53 +00003943{
Larry Hastings2f936352014-08-05 14:04:04 +10003944 PyObject *return_value = NULL;
3945 static char *_keywords[] = {"path", "uid", "gid", "dir_fd", "follow_symlinks", NULL};
3946 path_t path = PATH_T_INITIALIZE("chown", "path", 0, PATH_HAVE_FCHOWN);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003947 uid_t uid;
3948 gid_t gid;
3949 int dir_fd = DEFAULT_DIR_FD;
3950 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003951
Larry Hastings2f936352014-08-05 14:04:04 +10003952 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3953 "O&O&O&|$O&p:chown", _keywords,
3954 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid, FCHOWNAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3955 goto exit;
3956 return_value = os_chown_impl(module, &path, uid, gid, dir_fd, follow_symlinks);
3957
3958exit:
3959 /* Cleanup for path */
3960 path_cleanup(&path);
3961
3962 return return_value;
3963}
3964
3965static PyObject *
3966os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks)
3967/*[clinic end generated code: output=22f011e3b4f9ff49 input=a61cc35574814d5d]*/
3968{
3969 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003970
3971#if !(defined(HAVE_LCHOWN) || defined(HAVE_FCHOWNAT))
3972 if (follow_symlinks_specified("chown", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003973 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003974#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003975 if (dir_fd_and_fd_invalid("chown", dir_fd, path->fd) ||
3976 fd_and_follow_symlinks_invalid("chown", path->fd, follow_symlinks))
3977 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003978
3979#ifdef __APPLE__
3980 /*
3981 * This is for Mac OS X 10.3, which doesn't have lchown.
3982 * (But we still have an lchown symbol because of weak-linking.)
3983 * It doesn't have fchownat either. So there's no possibility
3984 * of a graceful failover.
Georg Brandlf7875592012-06-24 13:58:31 +02003985 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003986 if ((!follow_symlinks) && (lchown == NULL)) {
3987 follow_symlinks_specified("chown", follow_symlinks);
Larry Hastings2f936352014-08-05 14:04:04 +10003988 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003989 }
3990#endif
3991
Victor Stinner8c62be82010-05-06 00:08:46 +00003992 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003993#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003994 if (path->fd != -1)
3995 result = fchown(path->fd, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003996 else
3997#endif
3998#ifdef HAVE_LCHOWN
3999 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10004000 result = lchown(path->narrow, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004001 else
4002#endif
4003#ifdef HAVE_FCHOWNAT
4004 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004005 result = fchownat(dir_fd, path->narrow, uid, gid,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004006 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
4007 else
4008#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004009 result = chown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004010 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004011
Larry Hastings2f936352014-08-05 14:04:04 +10004012 if (result)
4013 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004014
Larry Hastings2f936352014-08-05 14:04:04 +10004015 Py_RETURN_NONE;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004016}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004017#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004018
Larry Hastings2f936352014-08-05 14:04:04 +10004019
Christian Heimes4e30a842007-11-30 22:12:06 +00004020#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004021/*[clinic input]
4022os.fchown
4023
4024 fd: int
4025 uid: uid_t
4026 gid: gid_t
4027
4028Change the owner and group id of the file specified by file descriptor.
4029
4030Equivalent to os.chown(fd, uid, gid).
4031
4032[clinic start generated code]*/
4033
4034PyDoc_STRVAR(os_fchown__doc__,
4035"fchown($module, /, fd, uid, gid)\n"
4036"--\n"
4037"\n"
4038"Change the owner and group id of the file specified by file descriptor.\n"
4039"\n"
4040"Equivalent to os.chown(fd, uid, gid).");
4041
4042#define OS_FCHOWN_METHODDEF \
4043 {"fchown", (PyCFunction)os_fchown, METH_VARARGS|METH_KEYWORDS, os_fchown__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00004044
4045static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004046os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid);
4047
4048static PyObject *
4049os_fchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00004050{
Larry Hastings2f936352014-08-05 14:04:04 +10004051 PyObject *return_value = NULL;
4052 static char *_keywords[] = {"fd", "uid", "gid", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00004053 int fd;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004054 uid_t uid;
4055 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004056
4057 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4058 "iO&O&:fchown", _keywords,
4059 &fd, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4060 goto exit;
4061 return_value = os_fchown_impl(module, fd, uid, gid);
4062
4063exit:
4064 return return_value;
4065}
4066
4067static PyObject *
4068os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid)
4069/*[clinic end generated code: output=687781cb7d8974d6 input=3af544ba1b13a0d7]*/
4070{
Victor Stinner8c62be82010-05-06 00:08:46 +00004071 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004072 Py_BEGIN_ALLOW_THREADS
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004073 res = fchown(fd, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004074 Py_END_ALLOW_THREADS
4075 if (res < 0)
4076 return posix_error();
4077 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00004078}
4079#endif /* HAVE_FCHOWN */
4080
Larry Hastings2f936352014-08-05 14:04:04 +10004081
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004082#ifdef HAVE_LCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004083/*[clinic input]
4084os.lchown
4085
4086 path : path_t
4087 uid: uid_t
4088 gid: gid_t
4089
4090Change the owner and group id of path to the numeric uid and gid.
4091
4092This function will not follow symbolic links.
4093Equivalent to os.chown(path, uid, gid, follow_symlinks=False).
4094[clinic start generated code]*/
4095
4096PyDoc_STRVAR(os_lchown__doc__,
4097"lchown($module, /, path, uid, gid)\n"
4098"--\n"
4099"\n"
4100"Change the owner and group id of path to the numeric uid and gid.\n"
4101"\n"
4102"This function will not follow symbolic links.\n"
4103"Equivalent to os.chown(path, uid, gid, follow_symlinks=False).");
4104
4105#define OS_LCHOWN_METHODDEF \
4106 {"lchown", (PyCFunction)os_lchown, METH_VARARGS|METH_KEYWORDS, os_lchown__doc__},
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004107
4108static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004109os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid);
4110
4111static PyObject *
4112os_lchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004113{
Larry Hastings2f936352014-08-05 14:04:04 +10004114 PyObject *return_value = NULL;
4115 static char *_keywords[] = {"path", "uid", "gid", NULL};
4116 path_t path = PATH_T_INITIALIZE("lchown", "path", 0, 0);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004117 uid_t uid;
4118 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004119
4120 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4121 "O&O&O&:lchown", _keywords,
4122 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4123 goto exit;
4124 return_value = os_lchown_impl(module, &path, uid, gid);
4125
4126exit:
4127 /* Cleanup for path */
4128 path_cleanup(&path);
4129
4130 return return_value;
4131}
4132
4133static PyObject *
4134os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid)
4135/*[clinic end generated code: output=bf25fdb0d25130e2 input=b1c6014d563a7161]*/
4136{
Victor Stinner8c62be82010-05-06 00:08:46 +00004137 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004138 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004139 res = lchown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004140 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01004141 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10004142 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01004143 }
Larry Hastings2f936352014-08-05 14:04:04 +10004144 Py_RETURN_NONE;
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004145}
4146#endif /* HAVE_LCHOWN */
4147
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004148
Barry Warsaw53699e91996-12-10 23:23:01 +00004149static PyObject *
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004150posix_getcwd(int use_bytes)
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004151{
Victor Stinner8c62be82010-05-06 00:08:46 +00004152 char buf[1026];
4153 char *res;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004154
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004155#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00004156 if (!use_bytes) {
4157 wchar_t wbuf[1026];
4158 wchar_t *wbuf2 = wbuf;
4159 PyObject *resobj;
4160 DWORD len;
4161 Py_BEGIN_ALLOW_THREADS
Victor Stinner75875072013-11-24 19:23:25 +01004162 len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004163 /* If the buffer is large enough, len does not include the
4164 terminating \0. If the buffer is too small, len includes
4165 the space needed for the terminator. */
Victor Stinner75875072013-11-24 19:23:25 +01004166 if (len >= Py_ARRAY_LENGTH(wbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004167 wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004168 if (wbuf2)
4169 len = GetCurrentDirectoryW(len, wbuf2);
4170 }
4171 Py_END_ALLOW_THREADS
4172 if (!wbuf2) {
4173 PyErr_NoMemory();
4174 return NULL;
4175 }
4176 if (!len) {
Victor Stinnerb024e842012-10-31 22:24:06 +01004177 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004178 PyMem_RawFree(wbuf2);
Victor Stinnerb024e842012-10-31 22:24:06 +01004179 return PyErr_SetFromWindowsErr(0);
Victor Stinner8c62be82010-05-06 00:08:46 +00004180 }
4181 resobj = PyUnicode_FromWideChar(wbuf2, len);
Victor Stinnerb024e842012-10-31 22:24:06 +01004182 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004183 PyMem_RawFree(wbuf2);
Victor Stinner8c62be82010-05-06 00:08:46 +00004184 return resobj;
4185 }
Victor Stinnerf7c5ae22011-11-16 23:43:07 +01004186
4187 if (win32_warn_bytes_api())
4188 return NULL;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004189#endif
4190
Victor Stinner8c62be82010-05-06 00:08:46 +00004191 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004192 res = getcwd(buf, sizeof buf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004193 Py_END_ALLOW_THREADS
4194 if (res == NULL)
4195 return posix_error();
4196 if (use_bytes)
4197 return PyBytes_FromStringAndSize(buf, strlen(buf));
Victor Stinner97c18ab2010-05-07 16:34:53 +00004198 return PyUnicode_DecodeFSDefault(buf);
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004199}
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004200
Larry Hastings2f936352014-08-05 14:04:04 +10004201
4202/*[clinic input]
4203os.getcwd
4204
4205Return a unicode string representing the current working directory.
4206[clinic start generated code]*/
4207
4208PyDoc_STRVAR(os_getcwd__doc__,
4209"getcwd($module, /)\n"
4210"--\n"
4211"\n"
4212"Return a unicode string representing the current working directory.");
4213
4214#define OS_GETCWD_METHODDEF \
4215 {"getcwd", (PyCFunction)os_getcwd, METH_NOARGS, os_getcwd__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004216
4217static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004218os_getcwd_impl(PyModuleDef *module);
4219
4220static PyObject *
4221os_getcwd(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4222{
4223 return os_getcwd_impl(module);
4224}
4225
4226static PyObject *
4227os_getcwd_impl(PyModuleDef *module)
4228/*[clinic end generated code: output=d70b281db5c78ff7 input=f069211bb70e3d39]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004229{
4230 return posix_getcwd(0);
4231}
4232
Larry Hastings2f936352014-08-05 14:04:04 +10004233
4234/*[clinic input]
4235os.getcwdb
4236
4237Return a bytes string representing the current working directory.
4238[clinic start generated code]*/
4239
4240PyDoc_STRVAR(os_getcwdb__doc__,
4241"getcwdb($module, /)\n"
4242"--\n"
4243"\n"
4244"Return a bytes string representing the current working directory.");
4245
4246#define OS_GETCWDB_METHODDEF \
4247 {"getcwdb", (PyCFunction)os_getcwdb, METH_NOARGS, os_getcwdb__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004248
4249static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004250os_getcwdb_impl(PyModuleDef *module);
4251
4252static PyObject *
4253os_getcwdb(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4254{
4255 return os_getcwdb_impl(module);
4256}
4257
4258static PyObject *
4259os_getcwdb_impl(PyModuleDef *module)
4260/*[clinic end generated code: output=75da47f2d75f9166 input=f6f6a378dad3d9cb]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004261{
4262 return posix_getcwd(1);
4263}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004264
Larry Hastings2f936352014-08-05 14:04:04 +10004265
Larry Hastings9cf065c2012-06-22 16:30:09 -07004266#if ((!defined(HAVE_LINK)) && defined(MS_WINDOWS))
4267#define HAVE_LINK 1
4268#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004269
Guido van Rossumb6775db1994-08-01 11:34:53 +00004270#ifdef HAVE_LINK
Larry Hastings2f936352014-08-05 14:04:04 +10004271/*[clinic input]
4272
4273os.link
4274
4275 src : path_t
4276 dst : path_t
4277 *
4278 src_dir_fd : dir_fd = None
4279 dst_dir_fd : dir_fd = None
4280 follow_symlinks: bool = True
4281
4282Create a hard link to a file.
4283
4284If either src_dir_fd or dst_dir_fd is not None, it should be a file
4285 descriptor open to a directory, and the respective path string (src or dst)
4286 should be relative; the path will then be relative to that directory.
4287If follow_symlinks is False, and the last element of src is a symbolic
4288 link, link will create a link to the symbolic link itself instead of the
4289 file the link points to.
4290src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your
4291 platform. If they are unavailable, using them will raise a
4292 NotImplementedError.
4293[clinic start generated code]*/
4294
4295PyDoc_STRVAR(os_link__doc__,
4296"link($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None,\n"
4297" follow_symlinks=True)\n"
4298"--\n"
4299"\n"
4300"Create a hard link to a file.\n"
4301"\n"
4302"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
4303" descriptor open to a directory, and the respective path string (src or dst)\n"
4304" should be relative; the path will then be relative to that directory.\n"
4305"If follow_symlinks is False, and the last element of src is a symbolic\n"
4306" link, link will create a link to the symbolic link itself instead of the\n"
4307" file the link points to.\n"
4308"src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your\n"
4309" platform. If they are unavailable, using them will raise a\n"
4310" NotImplementedError.");
4311
4312#define OS_LINK_METHODDEF \
4313 {"link", (PyCFunction)os_link, METH_VARARGS|METH_KEYWORDS, os_link__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004314
Barry Warsaw53699e91996-12-10 23:23:01 +00004315static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004316os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks);
4317
4318static PyObject *
4319os_link(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004320{
Larry Hastings2f936352014-08-05 14:04:04 +10004321 PyObject *return_value = NULL;
4322 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", "follow_symlinks", NULL};
4323 path_t src = PATH_T_INITIALIZE("link", "src", 0, 0);
4324 path_t dst = PATH_T_INITIALIZE("link", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004325 int src_dir_fd = DEFAULT_DIR_FD;
4326 int dst_dir_fd = DEFAULT_DIR_FD;
4327 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10004328
4329 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4330 "O&O&|$O&O&p:link", _keywords,
4331 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd, &follow_symlinks))
4332 goto exit;
4333 return_value = os_link_impl(module, &src, &dst, src_dir_fd, dst_dir_fd, follow_symlinks);
4334
4335exit:
4336 /* Cleanup for src */
4337 path_cleanup(&src);
4338 /* Cleanup for dst */
4339 path_cleanup(&dst);
4340
4341 return return_value;
4342}
4343
4344static PyObject *
4345os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks)
4346/*[clinic end generated code: output=53477662fe02e183 input=b0095ebbcbaa7e04]*/
4347{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004348#ifdef MS_WINDOWS
4349 BOOL result;
4350#else
4351 int result;
4352#endif
4353
Larry Hastings9cf065c2012-06-22 16:30:09 -07004354#ifndef HAVE_LINKAT
4355 if ((src_dir_fd != DEFAULT_DIR_FD) || (dst_dir_fd != DEFAULT_DIR_FD)) {
4356 argument_unavailable_error("link", "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10004357 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004358 }
4359#endif
4360
Larry Hastings2f936352014-08-05 14:04:04 +10004361 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004362 PyErr_SetString(PyExc_NotImplementedError,
4363 "link: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10004364 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004365 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004366
Brian Curtin1b9df392010-11-24 20:24:31 +00004367#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004368 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004369 if (src->wide)
4370 result = CreateHardLinkW(dst->wide, src->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004371 else
Larry Hastings2f936352014-08-05 14:04:04 +10004372 result = CreateHardLinkA(dst->narrow, src->narrow, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004373 Py_END_ALLOW_THREADS
Brian Curtin1b9df392010-11-24 20:24:31 +00004374
Larry Hastings2f936352014-08-05 14:04:04 +10004375 if (!result)
4376 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004377#else
4378 Py_BEGIN_ALLOW_THREADS
Larry Hastings67cbf7b2012-06-22 17:06:48 -07004379#ifdef HAVE_LINKAT
Larry Hastings9cf065c2012-06-22 16:30:09 -07004380 if ((src_dir_fd != DEFAULT_DIR_FD) ||
4381 (dst_dir_fd != DEFAULT_DIR_FD) ||
4382 (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004383 result = linkat(src_dir_fd, src->narrow,
4384 dst_dir_fd, dst->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004385 follow_symlinks ? AT_SYMLINK_FOLLOW : 0);
4386 else
4387#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004388 result = link(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004389 Py_END_ALLOW_THREADS
Brian Curtinfc889c42010-11-28 23:59:46 +00004390
Larry Hastings2f936352014-08-05 14:04:04 +10004391 if (result)
4392 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004393#endif
4394
Larry Hastings2f936352014-08-05 14:04:04 +10004395 Py_RETURN_NONE;
Brian Curtin1b9df392010-11-24 20:24:31 +00004396}
Larry Hastings9cf065c2012-06-22 16:30:09 -07004397#endif
4398
Brian Curtin1b9df392010-11-24 20:24:31 +00004399
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004400#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
Barry Warsaw53699e91996-12-10 23:23:01 +00004401static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004402_listdir_windows_no_opendir(path_t *path, PyObject *list)
Guido van Rossumb6775db1994-08-01 11:34:53 +00004403{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004404 PyObject *v;
4405 HANDLE hFindFile = INVALID_HANDLE_VALUE;
4406 BOOL result;
4407 WIN32_FIND_DATA FileData;
Victor Stinner75875072013-11-24 19:23:25 +01004408 char namebuf[MAX_PATH+4]; /* Overallocate for "\*.*" */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004409 char *bufptr = namebuf;
4410 /* only claim to have space for MAX_PATH */
Victor Stinner75875072013-11-24 19:23:25 +01004411 Py_ssize_t len = Py_ARRAY_LENGTH(namebuf)-4;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004412 PyObject *po = NULL;
4413 wchar_t *wnamebuf = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004414
Gregory P. Smith40a21602013-03-20 20:52:50 -07004415 if (!path->narrow) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004416 WIN32_FIND_DATAW wFileData;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004417 wchar_t *po_wchars;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004418
Gregory P. Smith40a21602013-03-20 20:52:50 -07004419 if (!path->wide) { /* Default arg: "." */
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004420 po_wchars = L".";
4421 len = 1;
4422 } else {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004423 po_wchars = path->wide;
4424 len = wcslen(path->wide);
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004425 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004426 /* The +5 is so we can append "\\*.*\0" */
Victor Stinnerb6404912013-07-07 16:21:41 +02004427 wnamebuf = PyMem_Malloc((len + 5) * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004428 if (!wnamebuf) {
4429 PyErr_NoMemory();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004430 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004431 }
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004432 wcscpy(wnamebuf, po_wchars);
Victor Stinner8c62be82010-05-06 00:08:46 +00004433 if (len > 0) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004434 wchar_t wch = wnamebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004435 if (wch != SEP && wch != ALTSEP && wch != L':')
4436 wnamebuf[len++] = SEP;
Victor Stinner8c62be82010-05-06 00:08:46 +00004437 wcscpy(wnamebuf + len, L"*.*");
4438 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004439 if ((list = PyList_New(0)) == NULL) {
4440 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004441 }
Antoine Pitroub73caab2010-08-09 23:39:31 +00004442 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004443 hFindFile = FindFirstFileW(wnamebuf, &wFileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004444 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004445 if (hFindFile == INVALID_HANDLE_VALUE) {
4446 int error = GetLastError();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004447 if (error == ERROR_FILE_NOT_FOUND)
4448 goto exit;
4449 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004450 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004451 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004452 }
4453 do {
4454 /* Skip over . and .. */
4455 if (wcscmp(wFileData.cFileName, L".") != 0 &&
4456 wcscmp(wFileData.cFileName, L"..") != 0) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004457 v = PyUnicode_FromWideChar(wFileData.cFileName,
4458 wcslen(wFileData.cFileName));
Victor Stinner8c62be82010-05-06 00:08:46 +00004459 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004460 Py_DECREF(list);
4461 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004462 break;
4463 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004464 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004465 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004466 Py_DECREF(list);
4467 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004468 break;
4469 }
4470 Py_DECREF(v);
4471 }
4472 Py_BEGIN_ALLOW_THREADS
4473 result = FindNextFileW(hFindFile, &wFileData);
4474 Py_END_ALLOW_THREADS
4475 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4476 it got to the end of the directory. */
4477 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004478 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004479 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004480 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004481 }
4482 } while (result == TRUE);
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00004483
Larry Hastings9cf065c2012-06-22 16:30:09 -07004484 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004485 }
Gregory P. Smith40a21602013-03-20 20:52:50 -07004486 strcpy(namebuf, path->narrow);
4487 len = path->length;
Victor Stinner8c62be82010-05-06 00:08:46 +00004488 if (len > 0) {
4489 char ch = namebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004490 if (ch != '\\' && ch != '/' && ch != ':')
4491 namebuf[len++] = '\\';
Victor Stinner8c62be82010-05-06 00:08:46 +00004492 strcpy(namebuf + len, "*.*");
4493 }
Guido van Rossumb6775db1994-08-01 11:34:53 +00004494
Larry Hastings9cf065c2012-06-22 16:30:09 -07004495 if ((list = PyList_New(0)) == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +00004496 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004497
Antoine Pitroub73caab2010-08-09 23:39:31 +00004498 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004499 hFindFile = FindFirstFile(namebuf, &FileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004500 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004501 if (hFindFile == INVALID_HANDLE_VALUE) {
4502 int error = GetLastError();
4503 if (error == ERROR_FILE_NOT_FOUND)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004504 goto exit;
4505 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004506 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004507 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004508 }
4509 do {
4510 /* Skip over . and .. */
4511 if (strcmp(FileData.cFileName, ".") != 0 &&
4512 strcmp(FileData.cFileName, "..") != 0) {
4513 v = PyBytes_FromString(FileData.cFileName);
4514 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004515 Py_DECREF(list);
4516 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004517 break;
4518 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004519 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004520 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004521 Py_DECREF(list);
4522 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004523 break;
4524 }
4525 Py_DECREF(v);
4526 }
4527 Py_BEGIN_ALLOW_THREADS
4528 result = FindNextFile(hFindFile, &FileData);
4529 Py_END_ALLOW_THREADS
4530 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4531 it got to the end of the directory. */
4532 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004533 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004534 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004535 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004536 }
4537 } while (result == TRUE);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004538
Larry Hastings9cf065c2012-06-22 16:30:09 -07004539exit:
4540 if (hFindFile != INVALID_HANDLE_VALUE) {
4541 if (FindClose(hFindFile) == FALSE) {
4542 if (list != NULL) {
4543 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004544 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004545 }
4546 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004547 }
Victor Stinnerb6404912013-07-07 16:21:41 +02004548 PyMem_Free(wnamebuf);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004549
Larry Hastings9cf065c2012-06-22 16:30:09 -07004550 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004551} /* end of _listdir_windows_no_opendir */
4552
4553#else /* thus POSIX, ie: not (MS_WINDOWS and not HAVE_OPENDIR) */
4554
4555static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004556_posix_listdir(path_t *path, PyObject *list)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004557{
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004558 PyObject *v;
4559 DIR *dirp = NULL;
4560 struct dirent *ep;
4561 int return_str; /* if false, return bytes */
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004562#ifdef HAVE_FDOPENDIR
4563 int fd = -1;
4564#endif
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004565
Victor Stinner8c62be82010-05-06 00:08:46 +00004566 errno = 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004567#ifdef HAVE_FDOPENDIR
Gregory P. Smith40a21602013-03-20 20:52:50 -07004568 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004569 /* closedir() closes the FD, so we duplicate it */
Victor Stinnerdaf45552013-08-28 00:53:59 +02004570 fd = _Py_dup(path->fd);
Victor Stinnerf3266652013-12-19 13:24:49 +01004571 if (fd == -1)
4572 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004573
Larry Hastingsfdaea062012-06-25 04:42:23 -07004574 return_str = 1;
4575
Larry Hastings9cf065c2012-06-22 16:30:09 -07004576 Py_BEGIN_ALLOW_THREADS
4577 dirp = fdopendir(fd);
4578 Py_END_ALLOW_THREADS
4579 }
4580 else
4581#endif
4582 {
Larry Hastingsfdaea062012-06-25 04:42:23 -07004583 char *name;
Gregory P. Smith40a21602013-03-20 20:52:50 -07004584 if (path->narrow) {
4585 name = path->narrow;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004586 /* only return bytes if they specified a bytes object */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004587 return_str = !(PyBytes_Check(path->object));
Larry Hastingsfdaea062012-06-25 04:42:23 -07004588 }
4589 else {
4590 name = ".";
4591 return_str = 1;
4592 }
4593
Larry Hastings9cf065c2012-06-22 16:30:09 -07004594 Py_BEGIN_ALLOW_THREADS
4595 dirp = opendir(name);
4596 Py_END_ALLOW_THREADS
4597 }
4598
4599 if (dirp == NULL) {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004600 list = path_error(path);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004601#ifdef HAVE_FDOPENDIR
4602 if (fd != -1) {
4603 Py_BEGIN_ALLOW_THREADS
4604 close(fd);
4605 Py_END_ALLOW_THREADS
4606 }
4607#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004608 goto exit;
4609 }
4610 if ((list = PyList_New(0)) == NULL) {
4611 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004612 }
4613 for (;;) {
4614 errno = 0;
4615 Py_BEGIN_ALLOW_THREADS
4616 ep = readdir(dirp);
4617 Py_END_ALLOW_THREADS
4618 if (ep == NULL) {
4619 if (errno == 0) {
4620 break;
4621 } else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004622 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004623 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004624 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004625 }
4626 }
4627 if (ep->d_name[0] == '.' &&
4628 (NAMLEN(ep) == 1 ||
4629 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
4630 continue;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004631 if (return_str)
Victor Stinnera45598a2010-05-14 16:35:39 +00004632 v = PyUnicode_DecodeFSDefaultAndSize(ep->d_name, NAMLEN(ep));
4633 else
4634 v = PyBytes_FromStringAndSize(ep->d_name, NAMLEN(ep));
Victor Stinner8c62be82010-05-06 00:08:46 +00004635 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004636 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004637 break;
4638 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004639 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004640 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004641 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004642 break;
4643 }
4644 Py_DECREF(v);
4645 }
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00004646
Larry Hastings9cf065c2012-06-22 16:30:09 -07004647exit:
4648 if (dirp != NULL) {
4649 Py_BEGIN_ALLOW_THREADS
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004650#ifdef HAVE_FDOPENDIR
Larry Hastings9cf065c2012-06-22 16:30:09 -07004651 if (fd > -1)
4652 rewinddir(dirp);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004653#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004654 closedir(dirp);
4655 Py_END_ALLOW_THREADS
4656 }
4657
Larry Hastings9cf065c2012-06-22 16:30:09 -07004658 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004659} /* end of _posix_listdir */
4660#endif /* which OS */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004661
Larry Hastings2f936352014-08-05 14:04:04 +10004662
4663/*[clinic input]
4664os.listdir
4665
4666 path : path_t(nullable=True, allow_fd='PATH_HAVE_FDOPENDIR') = None
4667
4668Return a list containing the names of the files in the directory.
4669
4670path can be specified as either str or bytes. If path is bytes,
4671 the filenames returned will also be bytes; in all other circumstances
4672 the filenames returned will be str.
4673If path is None, uses the path='.'.
4674On some platforms, path may also be specified as an open file descriptor;\
4675 the file descriptor must refer to a directory.
4676 If this functionality is unavailable, using it raises NotImplementedError.
4677
4678The list is in arbitrary order. It does not include the special
4679entries '.' and '..' even if they are present in the directory.
4680
4681
4682[clinic start generated code]*/
4683
4684PyDoc_STRVAR(os_listdir__doc__,
4685"listdir($module, /, path=None)\n"
4686"--\n"
4687"\n"
4688"Return a list containing the names of the files in the directory.\n"
4689"\n"
4690"path can be specified as either str or bytes. If path is bytes,\n"
4691" the filenames returned will also be bytes; in all other circumstances\n"
4692" the filenames returned will be str.\n"
4693"If path is None, uses the path=\'.\'.\n"
4694"On some platforms, path may also be specified as an open file descriptor;\\\n"
4695" the file descriptor must refer to a directory.\n"
4696" If this functionality is unavailable, using it raises NotImplementedError.\n"
4697"\n"
4698"The list is in arbitrary order. It does not include the special\n"
4699"entries \'.\' and \'..\' even if they are present in the directory.");
4700
4701#define OS_LISTDIR_METHODDEF \
4702 {"listdir", (PyCFunction)os_listdir, METH_VARARGS|METH_KEYWORDS, os_listdir__doc__},
4703
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004704static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004705os_listdir_impl(PyModuleDef *module, path_t *path);
4706
4707static PyObject *
4708os_listdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004709{
Larry Hastings2f936352014-08-05 14:04:04 +10004710 PyObject *return_value = NULL;
4711 static char *_keywords[] = {"path", NULL};
4712 path_t path = PATH_T_INITIALIZE("listdir", "path", 1, PATH_HAVE_FDOPENDIR);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004713
Larry Hastings2f936352014-08-05 14:04:04 +10004714 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4715 "|O&:listdir", _keywords,
4716 path_converter, &path))
4717 goto exit;
4718 return_value = os_listdir_impl(module, &path);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004719
Larry Hastings2f936352014-08-05 14:04:04 +10004720exit:
4721 /* Cleanup for path */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004722 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10004723
Gregory P. Smith40a21602013-03-20 20:52:50 -07004724 return return_value;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004725}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004726
Larry Hastings2f936352014-08-05 14:04:04 +10004727static PyObject *
4728os_listdir_impl(PyModuleDef *module, path_t *path)
4729/*[clinic end generated code: output=e159bd9be6909018 input=09e300416e3cd729]*/
4730{
4731#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
4732 return _listdir_windows_no_opendir(path, NULL);
4733#else
4734 return _posix_listdir(path, NULL);
4735#endif
4736}
4737
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00004738#ifdef MS_WINDOWS
Mark Hammondef8b6542001-05-13 08:04:26 +00004739/* A helper function for abspath on win32 */
Larry Hastings2f936352014-08-05 14:04:04 +10004740/* AC 3.5: probably just convert to using path converter */
Mark Hammondef8b6542001-05-13 08:04:26 +00004741static PyObject *
4742posix__getfullpathname(PyObject *self, PyObject *args)
4743{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004744 const char *path;
Victor Stinner75875072013-11-24 19:23:25 +01004745 char outbuf[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00004746 char *temp;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004747 PyObject *po;
4748
4749 if (PyArg_ParseTuple(args, "U|:_getfullpathname", &po))
4750 {
4751 wchar_t *wpath;
Victor Stinner75875072013-11-24 19:23:25 +01004752 wchar_t woutbuf[MAX_PATH], *woutbufp = woutbuf;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004753 wchar_t *wtemp;
Victor Stinner8c62be82010-05-06 00:08:46 +00004754 DWORD result;
4755 PyObject *v;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004756
4757 wpath = PyUnicode_AsUnicode(po);
4758 if (wpath == NULL)
4759 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004760 result = GetFullPathNameW(wpath,
Victor Stinner63941882011-09-29 00:42:28 +02004761 Py_ARRAY_LENGTH(woutbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004762 woutbuf, &wtemp);
Victor Stinner63941882011-09-29 00:42:28 +02004763 if (result > Py_ARRAY_LENGTH(woutbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004764 woutbufp = PyMem_Malloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004765 if (!woutbufp)
4766 return PyErr_NoMemory();
4767 result = GetFullPathNameW(wpath, result, woutbufp, &wtemp);
4768 }
4769 if (result)
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004770 v = PyUnicode_FromWideChar(woutbufp, wcslen(woutbufp));
Victor Stinner8c62be82010-05-06 00:08:46 +00004771 else
Victor Stinnereb5657a2011-09-30 01:44:27 +02004772 v = win32_error_object("GetFullPathNameW", po);
Victor Stinner8c62be82010-05-06 00:08:46 +00004773 if (woutbufp != woutbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004774 PyMem_Free(woutbufp);
Victor Stinner8c62be82010-05-06 00:08:46 +00004775 return v;
4776 }
4777 /* Drop the argument parsing error as narrow strings
4778 are also valid. */
4779 PyErr_Clear();
Victor Stinnereb5657a2011-09-30 01:44:27 +02004780
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004781 if (!PyArg_ParseTuple (args, "y:_getfullpathname",
4782 &path))
Victor Stinner8c62be82010-05-06 00:08:46 +00004783 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004784 if (win32_warn_bytes_api())
4785 return NULL;
Victor Stinner63941882011-09-29 00:42:28 +02004786 if (!GetFullPathName(path, Py_ARRAY_LENGTH(outbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004787 outbuf, &temp)) {
4788 win32_error("GetFullPathName", path);
Victor Stinner8c62be82010-05-06 00:08:46 +00004789 return NULL;
4790 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004791 if (PyUnicode_Check(PyTuple_GetItem(args, 0))) {
4792 return PyUnicode_Decode(outbuf, strlen(outbuf),
4793 Py_FileSystemDefaultEncoding, NULL);
4794 }
4795 return PyBytes_FromString(outbuf);
Larry Hastings2f936352014-08-05 14:04:04 +10004796}
Brian Curtind40e6f72010-07-08 21:39:08 +00004797
Brian Curtind25aef52011-06-13 15:16:04 -05004798
Larry Hastings2f936352014-08-05 14:04:04 +10004799/*[clinic input]
4800os._getfinalpathname
Brian Curtinf5e76d02010-11-24 13:14:05 +00004801
Larry Hastings2f936352014-08-05 14:04:04 +10004802 path: unicode
4803 /
4804
4805A helper function for samepath on windows.
4806[clinic start generated code]*/
4807
4808PyDoc_STRVAR(os__getfinalpathname__doc__,
4809"_getfinalpathname($module, path, /)\n"
4810"--\n"
4811"\n"
4812"A helper function for samepath on windows.");
4813
4814#define OS__GETFINALPATHNAME_METHODDEF \
4815 {"_getfinalpathname", (PyCFunction)os__getfinalpathname, METH_VARARGS, os__getfinalpathname__doc__},
4816
Brian Curtind40e6f72010-07-08 21:39:08 +00004817static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004818os__getfinalpathname_impl(PyModuleDef *module, PyObject *path);
4819
4820static PyObject *
4821os__getfinalpathname(PyModuleDef *module, PyObject *args)
4822{
4823 PyObject *return_value = NULL;
4824 PyObject *path;
4825
4826 if (!PyArg_ParseTuple(args,
4827 "U:_getfinalpathname",
4828 &path))
4829 goto exit;
4830 return_value = os__getfinalpathname_impl(module, path);
4831
4832exit:
4833 return return_value;
4834}
4835
4836static PyObject *
4837os__getfinalpathname_impl(PyModuleDef *module, PyObject *path)
4838/*[clinic end generated code: output=4563c6eacf1b0881 input=71d5e89334891bf4]*/
Brian Curtind40e6f72010-07-08 21:39:08 +00004839{
4840 HANDLE hFile;
4841 int buf_size;
4842 wchar_t *target_path;
4843 int result_length;
Larry Hastings2f936352014-08-05 14:04:04 +10004844 PyObject *result;
4845 wchar_t *path_wchar;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004846
Larry Hastings2f936352014-08-05 14:04:04 +10004847 path_wchar = PyUnicode_AsUnicode(path);
4848 if (path_wchar == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02004849 return NULL;
Brian Curtind40e6f72010-07-08 21:39:08 +00004850
4851 if(!check_GetFinalPathNameByHandle()) {
4852 /* If the OS doesn't have GetFinalPathNameByHandle, return a
4853 NotImplementedError. */
4854 return PyErr_Format(PyExc_NotImplementedError,
4855 "GetFinalPathNameByHandle not available on this platform");
4856 }
4857
4858 hFile = CreateFileW(
Larry Hastings2f936352014-08-05 14:04:04 +10004859 path_wchar,
Brian Curtind40e6f72010-07-08 21:39:08 +00004860 0, /* desired access */
4861 0, /* share mode */
4862 NULL, /* security attributes */
4863 OPEN_EXISTING,
4864 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
4865 FILE_FLAG_BACKUP_SEMANTICS,
4866 NULL);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004867
Victor Stinnereb5657a2011-09-30 01:44:27 +02004868 if(hFile == INVALID_HANDLE_VALUE)
Larry Hastings2f936352014-08-05 14:04:04 +10004869 return win32_error_object("CreateFileW", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004870
4871 /* We have a good handle to the target, use it to determine the
4872 target path name. */
4873 buf_size = Py_GetFinalPathNameByHandleW(hFile, 0, 0, VOLUME_NAME_NT);
4874
4875 if(!buf_size)
Larry Hastings2f936352014-08-05 14:04:04 +10004876 return win32_error_object("GetFinalPathNameByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004877
Victor Stinnerb6404912013-07-07 16:21:41 +02004878 target_path = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtind40e6f72010-07-08 21:39:08 +00004879 if(!target_path)
4880 return PyErr_NoMemory();
4881
4882 result_length = Py_GetFinalPathNameByHandleW(hFile, target_path,
4883 buf_size, VOLUME_NAME_DOS);
4884 if(!result_length)
Larry Hastings2f936352014-08-05 14:04:04 +10004885 return win32_error_object("GetFinalPathNamyByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004886
4887 if(!CloseHandle(hFile))
Larry Hastings2f936352014-08-05 14:04:04 +10004888 return win32_error_object("CloseHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004889
4890 target_path[result_length] = 0;
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004891 result = PyUnicode_FromWideChar(target_path, result_length);
Victor Stinnerb6404912013-07-07 16:21:41 +02004892 PyMem_Free(target_path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004893 return result;
Larry Hastings2f936352014-08-05 14:04:04 +10004894}
Brian Curtin62857742010-09-06 17:07:27 +00004895
Brian Curtin95d028f2011-06-09 09:10:38 -05004896PyDoc_STRVAR(posix__isdir__doc__,
4897"Return true if the pathname refers to an existing directory.");
4898
Larry Hastings2f936352014-08-05 14:04:04 +10004899/* AC 3.5: convert using path converter */
Brian Curtin9c669cc2011-06-08 18:17:18 -05004900static PyObject *
4901posix__isdir(PyObject *self, PyObject *args)
4902{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004903 const char *path;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004904 PyObject *po;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004905 DWORD attributes;
4906
4907 if (PyArg_ParseTuple(args, "U|:_isdir", &po)) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004908 wchar_t *wpath = PyUnicode_AsUnicode(po);
4909 if (wpath == NULL)
4910 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004911
4912 attributes = GetFileAttributesW(wpath);
4913 if (attributes == INVALID_FILE_ATTRIBUTES)
4914 Py_RETURN_FALSE;
4915 goto check;
4916 }
4917 /* Drop the argument parsing error as narrow strings
4918 are also valid. */
4919 PyErr_Clear();
4920
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004921 if (!PyArg_ParseTuple(args, "y:_isdir", &path))
Brian Curtin9c669cc2011-06-08 18:17:18 -05004922 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004923 if (win32_warn_bytes_api())
4924 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004925 attributes = GetFileAttributesA(path);
4926 if (attributes == INVALID_FILE_ATTRIBUTES)
4927 Py_RETURN_FALSE;
4928
4929check:
4930 if (attributes & FILE_ATTRIBUTE_DIRECTORY)
4931 Py_RETURN_TRUE;
4932 else
4933 Py_RETURN_FALSE;
4934}
Tim Golden6b528062013-08-01 12:44:00 +01004935
Tim Golden6b528062013-08-01 12:44:00 +01004936
Larry Hastings2f936352014-08-05 14:04:04 +10004937/*[clinic input]
4938os._getvolumepathname
4939
4940 path: unicode
4941
4942A helper function for ismount on Win32.
4943[clinic start generated code]*/
4944
4945PyDoc_STRVAR(os__getvolumepathname__doc__,
4946"_getvolumepathname($module, /, path)\n"
4947"--\n"
4948"\n"
4949"A helper function for ismount on Win32.");
4950
4951#define OS__GETVOLUMEPATHNAME_METHODDEF \
4952 {"_getvolumepathname", (PyCFunction)os__getvolumepathname, METH_VARARGS|METH_KEYWORDS, os__getvolumepathname__doc__},
4953
Tim Golden6b528062013-08-01 12:44:00 +01004954static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004955os__getvolumepathname_impl(PyModuleDef *module, PyObject *path);
4956
4957static PyObject *
4958os__getvolumepathname(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Tim Golden6b528062013-08-01 12:44:00 +01004959{
Larry Hastings2f936352014-08-05 14:04:04 +10004960 PyObject *return_value = NULL;
4961 static char *_keywords[] = {"path", NULL};
4962 PyObject *path;
4963
4964 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4965 "U:_getvolumepathname", _keywords,
4966 &path))
4967 goto exit;
4968 return_value = os__getvolumepathname_impl(module, path);
4969
4970exit:
4971 return return_value;
4972}
4973
4974static PyObject *
4975os__getvolumepathname_impl(PyModuleDef *module, PyObject *path)
4976/*[clinic end generated code: output=ac0833b6d6da7657 input=7eacadc40acbda6b]*/
4977{
4978 PyObject *result;
4979 wchar_t *path_wchar, *mountpath=NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01004980 size_t buflen;
Tim Golden6b528062013-08-01 12:44:00 +01004981 BOOL ret;
4982
Larry Hastings2f936352014-08-05 14:04:04 +10004983 path_wchar = PyUnicode_AsUnicodeAndSize(path, &buflen);
4984 if (path_wchar == NULL)
Tim Golden6b528062013-08-01 12:44:00 +01004985 return NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01004986 buflen += 1;
Tim Golden6b528062013-08-01 12:44:00 +01004987
4988 /* Volume path should be shorter than entire path */
Victor Stinner6edddfa2013-11-24 19:22:57 +01004989 buflen = Py_MAX(buflen, MAX_PATH);
4990
4991 if (buflen > DWORD_MAX) {
4992 PyErr_SetString(PyExc_OverflowError, "path too long");
4993 return NULL;
4994 }
4995
4996 mountpath = (wchar_t *)PyMem_Malloc(buflen * sizeof(wchar_t));
Tim Golden6b528062013-08-01 12:44:00 +01004997 if (mountpath == NULL)
4998 return PyErr_NoMemory();
4999
5000 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005001 ret = GetVolumePathNameW(path_wchar, mountpath,
Victor Stinner6edddfa2013-11-24 19:22:57 +01005002 Py_SAFE_DOWNCAST(buflen, size_t, DWORD));
Tim Golden6b528062013-08-01 12:44:00 +01005003 Py_END_ALLOW_THREADS
5004
5005 if (!ret) {
Larry Hastings2f936352014-08-05 14:04:04 +10005006 result = win32_error_object("_getvolumepathname", path);
Tim Golden6b528062013-08-01 12:44:00 +01005007 goto exit;
5008 }
5009 result = PyUnicode_FromWideChar(mountpath, wcslen(mountpath));
5010
5011exit:
5012 PyMem_Free(mountpath);
5013 return result;
5014}
Tim Golden6b528062013-08-01 12:44:00 +01005015
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00005016#endif /* MS_WINDOWS */
Mark Hammondef8b6542001-05-13 08:04:26 +00005017
Larry Hastings2f936352014-08-05 14:04:04 +10005018
5019/*[clinic input]
5020os.mkdir
5021
5022 path : path_t
5023
5024 mode: int = 0o777
5025
5026 *
5027
5028 dir_fd : dir_fd(requires='mkdirat') = None
5029
5030# "mkdir(path, mode=0o777, *, dir_fd=None)\n\n\
5031
5032Create a directory.
5033
5034If dir_fd is not None, it should be a file descriptor open to a directory,
5035 and path should be relative; path will then be relative to that directory.
5036dir_fd may not be implemented on your platform.
5037 If it is unavailable, using it will raise a NotImplementedError.
5038
5039The mode argument is ignored on Windows.
5040[clinic start generated code]*/
5041
5042PyDoc_STRVAR(os_mkdir__doc__,
5043"mkdir($module, /, path, mode=511, *, dir_fd=None)\n"
5044"--\n"
5045"\n"
5046"Create a directory.\n"
5047"\n"
5048"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5049" and path should be relative; path will then be relative to that directory.\n"
5050"dir_fd may not be implemented on your platform.\n"
5051" If it is unavailable, using it will raise a NotImplementedError.\n"
5052"\n"
5053"The mode argument is ignored on Windows.");
5054
5055#define OS_MKDIR_METHODDEF \
5056 {"mkdir", (PyCFunction)os_mkdir, METH_VARARGS|METH_KEYWORDS, os_mkdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005057
Barry Warsaw53699e91996-12-10 23:23:01 +00005058static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005059os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005060
Larry Hastings2f936352014-08-05 14:04:04 +10005061static PyObject *
5062os_mkdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5063{
5064 PyObject *return_value = NULL;
5065 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
5066 path_t path = PATH_T_INITIALIZE("mkdir", "path", 0, 0);
5067 int mode = 511;
5068 int dir_fd = DEFAULT_DIR_FD;
5069
5070 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5071 "O&|i$O&:mkdir", _keywords,
5072 path_converter, &path, &mode, MKDIRAT_DIR_FD_CONVERTER, &dir_fd))
5073 goto exit;
5074 return_value = os_mkdir_impl(module, &path, mode, dir_fd);
5075
5076exit:
5077 /* Cleanup for path */
5078 path_cleanup(&path);
5079
5080 return return_value;
5081}
5082
5083static PyObject *
5084os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
5085/*[clinic end generated code: output=55c6ef2bc1b207e6 input=e965f68377e9b1ce]*/
5086{
5087 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005088
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00005089#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005090 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005091 if (path->wide)
5092 result = CreateDirectoryW(path->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005093 else
Larry Hastings2f936352014-08-05 14:04:04 +10005094 result = CreateDirectoryA(path->narrow, NULL);
Victor Stinner8c62be82010-05-06 00:08:46 +00005095 Py_END_ALLOW_THREADS
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005096
Larry Hastings2f936352014-08-05 14:04:04 +10005097 if (!result)
5098 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005099#else
Victor Stinner8c62be82010-05-06 00:08:46 +00005100 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07005101#if HAVE_MKDIRAT
5102 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005103 result = mkdirat(dir_fd, path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005104 else
5105#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00005106#if ( defined(__WATCOMC__) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Larry Hastings2f936352014-08-05 14:04:04 +10005107 result = mkdir(path->narrow);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005108#else
Larry Hastings2f936352014-08-05 14:04:04 +10005109 result = mkdir(path->narrow, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005110#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005111 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005112 if (result < 0)
5113 return path_error(path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00005114#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005115 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005116}
5117
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005118
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005119/* sys/resource.h is needed for at least: wait3(), wait4(), broken nice. */
5120#if defined(HAVE_SYS_RESOURCE_H)
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005121#include <sys/resource.h>
5122#endif
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005123
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005124
5125#ifdef HAVE_NICE
Larry Hastings2f936352014-08-05 14:04:04 +10005126/*[clinic input]
5127os.nice
5128
5129 increment: int
5130 /
5131
5132Add increment to the priority of process and return the new priority.
5133[clinic start generated code]*/
5134
5135PyDoc_STRVAR(os_nice__doc__,
5136"nice($module, increment, /)\n"
5137"--\n"
5138"\n"
5139"Add increment to the priority of process and return the new priority.");
5140
5141#define OS_NICE_METHODDEF \
5142 {"nice", (PyCFunction)os_nice, METH_VARARGS, os_nice__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005143
Barry Warsaw53699e91996-12-10 23:23:01 +00005144static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005145os_nice_impl(PyModuleDef *module, int increment);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005146
Larry Hastings2f936352014-08-05 14:04:04 +10005147static PyObject *
5148os_nice(PyModuleDef *module, PyObject *args)
5149{
5150 PyObject *return_value = NULL;
5151 int increment;
5152
5153 if (!PyArg_ParseTuple(args,
5154 "i:nice",
5155 &increment))
5156 goto exit;
5157 return_value = os_nice_impl(module, increment);
5158
5159exit:
5160 return return_value;
5161}
5162
5163static PyObject *
5164os_nice_impl(PyModuleDef *module, int increment)
5165/*[clinic end generated code: output=c360dc2a3bd8e3d0 input=864be2d402a21da2]*/
5166{
5167 int value;
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005168
Victor Stinner8c62be82010-05-06 00:08:46 +00005169 /* There are two flavours of 'nice': one that returns the new
5170 priority (as required by almost all standards out there) and the
5171 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
5172 the use of getpriority() to get the new priority.
Tim Peters5aa91602002-01-30 05:46:57 +00005173
Victor Stinner8c62be82010-05-06 00:08:46 +00005174 If we are of the nice family that returns the new priority, we
5175 need to clear errno before the call, and check if errno is filled
5176 before calling posix_error() on a returnvalue of -1, because the
5177 -1 may be the actual new priority! */
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005178
Victor Stinner8c62be82010-05-06 00:08:46 +00005179 errno = 0;
5180 value = nice(increment);
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005181#if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005182 if (value == 0)
5183 value = getpriority(PRIO_PROCESS, 0);
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005184#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005185 if (value == -1 && errno != 0)
5186 /* either nice() or getpriority() returned an error */
5187 return posix_error();
5188 return PyLong_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005189}
Guido van Rossumb6775db1994-08-01 11:34:53 +00005190#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00005191
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005192
5193#ifdef HAVE_GETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005194/*[clinic input]
5195os.getpriority
5196
5197 which: int
5198 who: int
5199
5200Return program scheduling priority.
5201[clinic start generated code]*/
5202
5203PyDoc_STRVAR(os_getpriority__doc__,
5204"getpriority($module, /, which, who)\n"
5205"--\n"
5206"\n"
5207"Return program scheduling priority.");
5208
5209#define OS_GETPRIORITY_METHODDEF \
5210 {"getpriority", (PyCFunction)os_getpriority, METH_VARARGS|METH_KEYWORDS, os_getpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005211
5212static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005213os_getpriority_impl(PyModuleDef *module, int which, int who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005214
Larry Hastings2f936352014-08-05 14:04:04 +10005215static PyObject *
5216os_getpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5217{
5218 PyObject *return_value = NULL;
5219 static char *_keywords[] = {"which", "who", NULL};
5220 int which;
5221 int who;
5222
5223 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5224 "ii:getpriority", _keywords,
5225 &which, &who))
5226 goto exit;
5227 return_value = os_getpriority_impl(module, which, who);
5228
5229exit:
5230 return return_value;
5231}
5232
5233static PyObject *
5234os_getpriority_impl(PyModuleDef *module, int which, int who)
5235/*[clinic end generated code: output=81639cf765f05dae input=9be615d40e2544ef]*/
5236{
5237 int retval;
5238
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005239 errno = 0;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005240 retval = getpriority(which, who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005241 if (errno != 0)
5242 return posix_error();
5243 return PyLong_FromLong((long)retval);
5244}
5245#endif /* HAVE_GETPRIORITY */
5246
5247
5248#ifdef HAVE_SETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005249/*[clinic input]
5250os.setpriority
5251
5252 which: int
5253 who: int
5254 priority: int
5255
5256Set program scheduling priority.
5257[clinic start generated code]*/
5258
5259PyDoc_STRVAR(os_setpriority__doc__,
5260"setpriority($module, /, which, who, priority)\n"
5261"--\n"
5262"\n"
5263"Set program scheduling priority.");
5264
5265#define OS_SETPRIORITY_METHODDEF \
5266 {"setpriority", (PyCFunction)os_setpriority, METH_VARARGS|METH_KEYWORDS, os_setpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005267
5268static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005269os_setpriority_impl(PyModuleDef *module, int which, int who, int priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005270
Larry Hastings2f936352014-08-05 14:04:04 +10005271static PyObject *
5272os_setpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5273{
5274 PyObject *return_value = NULL;
5275 static char *_keywords[] = {"which", "who", "priority", NULL};
5276 int which;
5277 int who;
5278 int priority;
5279
5280 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5281 "iii:setpriority", _keywords,
5282 &which, &who, &priority))
5283 goto exit;
5284 return_value = os_setpriority_impl(module, which, who, priority);
5285
5286exit:
5287 return return_value;
5288}
5289
5290static PyObject *
5291os_setpriority_impl(PyModuleDef *module, int which, int who, int priority)
5292/*[clinic end generated code: output=ddad62651fb2120c input=710ccbf65b9dc513]*/
5293{
5294 int retval;
5295
5296 retval = setpriority(which, who, priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005297 if (retval == -1)
5298 return posix_error();
5299 Py_RETURN_NONE;
5300}
5301#endif /* HAVE_SETPRIORITY */
5302
5303
Barry Warsaw53699e91996-12-10 23:23:01 +00005304static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005305internal_rename(path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int is_replace)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005306{
Larry Hastings9cf065c2012-06-22 16:30:09 -07005307 char *function_name = is_replace ? "replace" : "rename";
Larry Hastings9cf065c2012-06-22 16:30:09 -07005308 int dir_fd_specified;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005309
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005310#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005311 BOOL result;
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005312 int flags = is_replace ? MOVEFILE_REPLACE_EXISTING : 0;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005313#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005314 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005315#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07005316
Larry Hastings9cf065c2012-06-22 16:30:09 -07005317 dir_fd_specified = (src_dir_fd != DEFAULT_DIR_FD) ||
5318 (dst_dir_fd != DEFAULT_DIR_FD);
5319#ifndef HAVE_RENAMEAT
5320 if (dir_fd_specified) {
5321 argument_unavailable_error(function_name, "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10005322 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005323 }
5324#endif
5325
Larry Hastings2f936352014-08-05 14:04:04 +10005326 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07005327 PyErr_Format(PyExc_ValueError,
5328 "%s: src and dst must be the same type", function_name);
Larry Hastings2f936352014-08-05 14:04:04 +10005329 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005330 }
5331
5332#ifdef MS_WINDOWS
5333 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005334 if (src->wide)
5335 result = MoveFileExW(src->wide, dst->wide, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005336 else
Larry Hastings2f936352014-08-05 14:04:04 +10005337 result = MoveFileExA(src->narrow, dst->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005338 Py_END_ALLOW_THREADS
5339
Larry Hastings2f936352014-08-05 14:04:04 +10005340 if (!result)
5341 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005342
5343#else
5344 Py_BEGIN_ALLOW_THREADS
5345#ifdef HAVE_RENAMEAT
5346 if (dir_fd_specified)
Larry Hastings2f936352014-08-05 14:04:04 +10005347 result = renameat(src_dir_fd, src->narrow, dst_dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005348 else
5349#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005350 result = rename(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005351 Py_END_ALLOW_THREADS
5352
Larry Hastings2f936352014-08-05 14:04:04 +10005353 if (result)
5354 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005355#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005356 Py_RETURN_NONE;
5357}
Larry Hastings9cf065c2012-06-22 16:30:09 -07005358
Larry Hastings2f936352014-08-05 14:04:04 +10005359
5360/*[clinic input]
5361os.rename
5362
5363 src : path_t
5364 dst : path_t
5365 *
5366 src_dir_fd : dir_fd = None
5367 dst_dir_fd : dir_fd = None
5368
5369Rename a file or directory.
5370
5371If either src_dir_fd or dst_dir_fd is not None, it should be a file
5372 descriptor open to a directory, and the respective path string (src or dst)
5373 should be relative; the path will then be relative to that directory.
5374src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5375 If they are unavailable, using them will raise a NotImplementedError.
5376[clinic start generated code]*/
5377
5378PyDoc_STRVAR(os_rename__doc__,
5379"rename($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5380"--\n"
5381"\n"
5382"Rename a file or directory.\n"
5383"\n"
5384"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5385" descriptor open to a directory, and the respective path string (src or dst)\n"
5386" should be relative; the path will then be relative to that directory.\n"
5387"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5388" If they are unavailable, using them will raise a NotImplementedError.");
5389
5390#define OS_RENAME_METHODDEF \
5391 {"rename", (PyCFunction)os_rename, METH_VARARGS|METH_KEYWORDS, os_rename__doc__},
5392
5393static PyObject *
5394os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd);
5395
5396static PyObject *
5397os_rename(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5398{
5399 PyObject *return_value = NULL;
5400 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5401 path_t src = PATH_T_INITIALIZE("rename", "src", 0, 0);
5402 path_t dst = PATH_T_INITIALIZE("rename", "dst", 0, 0);
5403 int src_dir_fd = DEFAULT_DIR_FD;
5404 int dst_dir_fd = DEFAULT_DIR_FD;
5405
5406 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5407 "O&O&|$O&O&:rename", _keywords,
5408 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5409 goto exit;
5410 return_value = os_rename_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5411
Larry Hastings9cf065c2012-06-22 16:30:09 -07005412exit:
Larry Hastings2f936352014-08-05 14:04:04 +10005413 /* Cleanup for src */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005414 path_cleanup(&src);
Larry Hastings2f936352014-08-05 14:04:04 +10005415 /* Cleanup for dst */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005416 path_cleanup(&dst);
Larry Hastings2f936352014-08-05 14:04:04 +10005417
Larry Hastings9cf065c2012-06-22 16:30:09 -07005418 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005419}
5420
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005421static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005422os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5423/*[clinic end generated code: output=c936bdc81f460a1e input=faa61c847912c850]*/
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005424{
Larry Hastings2f936352014-08-05 14:04:04 +10005425 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 0);
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005426}
5427
Larry Hastings2f936352014-08-05 14:04:04 +10005428
5429/*[clinic input]
5430os.replace = os.rename
5431
5432Rename a file or directory, overwriting the destination.
5433
5434If either src_dir_fd or dst_dir_fd is not None, it should be a file
5435 descriptor open to a directory, and the respective path string (src or dst)
5436 should be relative; the path will then be relative to that directory.
5437src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5438 If they are unavailable, using them will raise a NotImplementedError."
5439[clinic start generated code]*/
5440
5441PyDoc_STRVAR(os_replace__doc__,
5442"replace($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5443"--\n"
5444"\n"
5445"Rename a file or directory, overwriting the destination.\n"
5446"\n"
5447"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5448" descriptor open to a directory, and the respective path string (src or dst)\n"
5449" should be relative; the path will then be relative to that directory.\n"
5450"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5451" If they are unavailable, using them will raise a NotImplementedError.\"");
5452
5453#define OS_REPLACE_METHODDEF \
5454 {"replace", (PyCFunction)os_replace, METH_VARARGS|METH_KEYWORDS, os_replace__doc__},
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005455
5456static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005457os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005458
Barry Warsaw53699e91996-12-10 23:23:01 +00005459static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005460os_replace(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005461{
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005462 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10005463 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5464 path_t src = PATH_T_INITIALIZE("replace", "src", 0, 0);
5465 path_t dst = PATH_T_INITIALIZE("replace", "dst", 0, 0);
5466 int src_dir_fd = DEFAULT_DIR_FD;
5467 int dst_dir_fd = DEFAULT_DIR_FD;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005468
Larry Hastings2f936352014-08-05 14:04:04 +10005469 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5470 "O&O&|$O&O&:replace", _keywords,
5471 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5472 goto exit;
5473 return_value = os_replace_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5474
5475exit:
5476 /* Cleanup for src */
5477 path_cleanup(&src);
5478 /* Cleanup for dst */
5479 path_cleanup(&dst);
5480
5481 return return_value;
5482}
5483
5484static PyObject *
5485os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5486/*[clinic end generated code: output=224e4710d290d171 input=25515dfb107c8421]*/
5487{
5488 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 1);
5489}
5490
5491
5492/*[clinic input]
5493os.rmdir
5494
5495 path: path_t
5496 *
5497 dir_fd: dir_fd(requires='unlinkat') = None
5498
5499Remove a directory.
5500
5501If dir_fd is not None, it should be a file descriptor open to a directory,
5502 and path should be relative; path will then be relative to that directory.
5503dir_fd may not be implemented on your platform.
5504 If it is unavailable, using it will raise a NotImplementedError.
5505[clinic start generated code]*/
5506
5507PyDoc_STRVAR(os_rmdir__doc__,
5508"rmdir($module, /, path, *, dir_fd=None)\n"
5509"--\n"
5510"\n"
5511"Remove a directory.\n"
5512"\n"
5513"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5514" and path should be relative; path will then be relative to that directory.\n"
5515"dir_fd may not be implemented on your platform.\n"
5516" If it is unavailable, using it will raise a NotImplementedError.");
5517
5518#define OS_RMDIR_METHODDEF \
5519 {"rmdir", (PyCFunction)os_rmdir, METH_VARARGS|METH_KEYWORDS, os_rmdir__doc__},
5520
5521static PyObject *
5522os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd);
5523
5524static PyObject *
5525os_rmdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5526{
5527 PyObject *return_value = NULL;
5528 static char *_keywords[] = {"path", "dir_fd", NULL};
5529 path_t path = PATH_T_INITIALIZE("rmdir", "path", 0, 0);
5530 int dir_fd = DEFAULT_DIR_FD;
5531
5532 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5533 "O&|$O&:rmdir", _keywords,
5534 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5535 goto exit;
5536 return_value = os_rmdir_impl(module, &path, dir_fd);
5537
5538exit:
5539 /* Cleanup for path */
5540 path_cleanup(&path);
5541
5542 return return_value;
5543}
5544
5545static PyObject *
5546os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd)
5547/*[clinic end generated code: output=70b9fdbe3bee0591 input=38c8b375ca34a7e2]*/
5548{
5549 int result;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005550
5551 Py_BEGIN_ALLOW_THREADS
5552#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005553 if (path->wide)
5554 result = RemoveDirectoryW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005555 else
Larry Hastings2f936352014-08-05 14:04:04 +10005556 result = RemoveDirectoryA(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005557 result = !result; /* Windows, success=1, UNIX, success=0 */
5558#else
5559#ifdef HAVE_UNLINKAT
5560 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005561 result = unlinkat(dir_fd, path->narrow, AT_REMOVEDIR);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005562 else
5563#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005564 result = rmdir(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005565#endif
5566 Py_END_ALLOW_THREADS
5567
Larry Hastings2f936352014-08-05 14:04:04 +10005568 if (result)
5569 return path_error(path);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005570
Larry Hastings2f936352014-08-05 14:04:04 +10005571 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005572}
5573
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005574
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005575#ifdef HAVE_SYSTEM
Larry Hastings2f936352014-08-05 14:04:04 +10005576#ifdef MS_WINDOWS
5577/*[clinic input]
5578os.system -> long
5579
5580 command: Py_UNICODE
5581
5582Execute the command in a subshell.
5583[clinic start generated code]*/
5584
5585PyDoc_STRVAR(os_system__doc__,
5586"system($module, /, command)\n"
5587"--\n"
5588"\n"
5589"Execute the command in a subshell.");
5590
5591#define OS_SYSTEM_METHODDEF \
5592 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5593
5594static long
5595os_system_impl(PyModuleDef *module, Py_UNICODE *command);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005596
Barry Warsaw53699e91996-12-10 23:23:01 +00005597static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005598os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005599{
Larry Hastings2f936352014-08-05 14:04:04 +10005600 PyObject *return_value = NULL;
5601 static char *_keywords[] = {"command", NULL};
5602 Py_UNICODE *command;
5603 long _return_value;
Victor Stinnercfa72782010-04-16 11:45:13 +00005604
Larry Hastings2f936352014-08-05 14:04:04 +10005605 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5606 "u:system", _keywords,
5607 &command))
5608 goto exit;
5609 _return_value = os_system_impl(module, command);
5610 if ((_return_value == -1) && PyErr_Occurred())
5611 goto exit;
5612 return_value = PyLong_FromLong(_return_value);
Victor Stinnercfa72782010-04-16 11:45:13 +00005613
Larry Hastings2f936352014-08-05 14:04:04 +10005614exit:
5615 return return_value;
5616}
5617
5618static long
5619os_system_impl(PyModuleDef *module, Py_UNICODE *command)
5620/*[clinic end generated code: output=29fe699c0b2e9d38 input=303f5ce97df606b0]*/
5621{
5622 long result;
Victor Stinner8c62be82010-05-06 00:08:46 +00005623 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005624 result = _wsystem(command);
Victor Stinner8c62be82010-05-06 00:08:46 +00005625 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005626 return result;
5627}
5628#else /* MS_WINDOWS */
5629/*[clinic input]
5630os.system -> long
5631
5632 command: FSConverter
5633
5634Execute the command in a subshell.
5635[clinic start generated code]*/
5636
5637PyDoc_STRVAR(os_system__doc__,
5638"system($module, /, command)\n"
5639"--\n"
5640"\n"
5641"Execute the command in a subshell.");
5642
5643#define OS_SYSTEM_METHODDEF \
5644 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5645
5646static long
5647os_system_impl(PyModuleDef *module, PyObject *command);
5648
5649static PyObject *
5650os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5651{
5652 PyObject *return_value = NULL;
5653 static char *_keywords[] = {"command", NULL};
5654 PyObject *command = NULL;
5655 long _return_value;
5656
5657 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5658 "O&:system", _keywords,
5659 PyUnicode_FSConverter, &command))
5660 goto exit;
5661 _return_value = os_system_impl(module, command);
5662 if ((_return_value == -1) && PyErr_Occurred())
5663 goto exit;
5664 return_value = PyLong_FromLong(_return_value);
5665
5666exit:
5667 /* Cleanup for command */
5668 Py_XDECREF(command);
5669
5670 return return_value;
5671}
5672
5673static long
5674os_system_impl(PyModuleDef *module, PyObject *command)
5675/*[clinic end generated code: output=5be9f3c40ead3bad input=86a58554ba6094af]*/
5676{
5677 long result;
5678 char *bytes = PyBytes_AsString(command);
5679 Py_BEGIN_ALLOW_THREADS
5680 result = system(bytes);
5681 Py_END_ALLOW_THREADS
5682 return result;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005683}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005684#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005685#endif /* HAVE_SYSTEM */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005686
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005687
Larry Hastings2f936352014-08-05 14:04:04 +10005688/*[clinic input]
5689os.umask
5690
5691 mask: int
5692 /
5693
5694Set the current numeric umask and return the previous umask.
5695[clinic start generated code]*/
5696
5697PyDoc_STRVAR(os_umask__doc__,
5698"umask($module, mask, /)\n"
5699"--\n"
5700"\n"
5701"Set the current numeric umask and return the previous umask.");
5702
5703#define OS_UMASK_METHODDEF \
5704 {"umask", (PyCFunction)os_umask, METH_VARARGS, os_umask__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005705
Barry Warsaw53699e91996-12-10 23:23:01 +00005706static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005707os_umask_impl(PyModuleDef *module, int mask);
5708
5709static PyObject *
5710os_umask(PyModuleDef *module, PyObject *args)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005711{
Larry Hastings2f936352014-08-05 14:04:04 +10005712 PyObject *return_value = NULL;
5713 int mask;
5714
5715 if (!PyArg_ParseTuple(args,
5716 "i:umask",
5717 &mask))
5718 goto exit;
5719 return_value = os_umask_impl(module, mask);
5720
5721exit:
5722 return return_value;
5723}
5724
5725static PyObject *
5726os_umask_impl(PyModuleDef *module, int mask)
5727/*[clinic end generated code: output=90048b39d2d4a961 input=ab6bfd9b24d8a7e8]*/
5728{
5729 int i = (int)umask(mask);
Victor Stinner8c62be82010-05-06 00:08:46 +00005730 if (i < 0)
5731 return posix_error();
5732 return PyLong_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005733}
5734
Brian Curtind40e6f72010-07-08 21:39:08 +00005735#ifdef MS_WINDOWS
5736
5737/* override the default DeleteFileW behavior so that directory
5738symlinks can be removed with this function, the same as with
5739Unix symlinks */
5740BOOL WINAPI Py_DeleteFileW(LPCWSTR lpFileName)
5741{
5742 WIN32_FILE_ATTRIBUTE_DATA info;
5743 WIN32_FIND_DATAW find_data;
5744 HANDLE find_data_handle;
5745 int is_directory = 0;
5746 int is_link = 0;
5747
5748 if (GetFileAttributesExW(lpFileName, GetFileExInfoStandard, &info)) {
5749 is_directory = info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00005750
Brian Curtind40e6f72010-07-08 21:39:08 +00005751 /* Get WIN32_FIND_DATA structure for the path to determine if
5752 it is a symlink */
5753 if(is_directory &&
5754 info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
5755 find_data_handle = FindFirstFileW(lpFileName, &find_data);
5756
5757 if(find_data_handle != INVALID_HANDLE_VALUE) {
Tim Golden0321cf22014-05-05 19:46:17 +01005758 /* IO_REPARSE_TAG_SYMLINK if it is a symlink and
5759 IO_REPARSE_TAG_MOUNT_POINT if it is a junction point. */
5760 is_link = find_data.dwReserved0 == IO_REPARSE_TAG_SYMLINK ||
5761 find_data.dwReserved0 == IO_REPARSE_TAG_MOUNT_POINT;
Brian Curtind40e6f72010-07-08 21:39:08 +00005762 FindClose(find_data_handle);
5763 }
5764 }
5765 }
5766
5767 if (is_directory && is_link)
5768 return RemoveDirectoryW(lpFileName);
5769
5770 return DeleteFileW(lpFileName);
5771}
5772#endif /* MS_WINDOWS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005773
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005774
Larry Hastings2f936352014-08-05 14:04:04 +10005775/*[clinic input]
5776os.unlink
5777
5778 path: path_t
5779 *
5780 dir_fd: dir_fd(requires='unlinkat')=None
5781
5782Remove a file (same as remove()).
5783
5784If dir_fd is not None, it should be a file descriptor open to a directory,
5785 and path should be relative; path will then be relative to that directory.
5786dir_fd may not be implemented on your platform.
5787 If it is unavailable, using it will raise a NotImplementedError.
5788
5789[clinic start generated code]*/
5790
5791PyDoc_STRVAR(os_unlink__doc__,
5792"unlink($module, /, path, *, dir_fd=None)\n"
5793"--\n"
5794"\n"
5795"Remove a file (same as remove()).\n"
5796"\n"
5797"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5798" and path should be relative; path will then be relative to that directory.\n"
5799"dir_fd may not be implemented on your platform.\n"
5800" If it is unavailable, using it will raise a NotImplementedError.");
5801
5802#define OS_UNLINK_METHODDEF \
5803 {"unlink", (PyCFunction)os_unlink, METH_VARARGS|METH_KEYWORDS, os_unlink__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005804
Barry Warsaw53699e91996-12-10 23:23:01 +00005805static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005806os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005807
Larry Hastings2f936352014-08-05 14:04:04 +10005808static PyObject *
5809os_unlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5810{
5811 PyObject *return_value = NULL;
5812 static char *_keywords[] = {"path", "dir_fd", NULL};
5813 path_t path = PATH_T_INITIALIZE("unlink", "path", 0, 0);
5814 int dir_fd = DEFAULT_DIR_FD;
5815
5816 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5817 "O&|$O&:unlink", _keywords,
5818 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5819 goto exit;
5820 return_value = os_unlink_impl(module, &path, dir_fd);
5821
5822exit:
5823 /* Cleanup for path */
5824 path_cleanup(&path);
5825
5826 return return_value;
5827}
5828
5829static PyObject *
5830os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd)
5831/*[clinic end generated code: output=59a6e66d67ff2e75 input=d7bcde2b1b2a2552]*/
5832{
5833 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005834
5835 Py_BEGIN_ALLOW_THREADS
5836#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005837 if (path->wide)
5838 result = Py_DeleteFileW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005839 else
Larry Hastings2f936352014-08-05 14:04:04 +10005840 result = DeleteFileA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005841 result = !result; /* Windows, success=1, UNIX, success=0 */
5842#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005843#ifdef HAVE_UNLINKAT
5844 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005845 result = unlinkat(dir_fd, path->narrow, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005846 else
5847#endif /* HAVE_UNLINKAT */
Larry Hastings2f936352014-08-05 14:04:04 +10005848 result = unlink(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005849#endif
5850 Py_END_ALLOW_THREADS
5851
Larry Hastings2f936352014-08-05 14:04:04 +10005852 if (result)
5853 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005854
Larry Hastings2f936352014-08-05 14:04:04 +10005855 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005856}
5857
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005858
Larry Hastings2f936352014-08-05 14:04:04 +10005859/*[clinic input]
5860os.remove = os.unlink
5861
5862Remove a file (same as unlink()).
5863
5864If dir_fd is not None, it should be a file descriptor open to a directory,
5865 and path should be relative; path will then be relative to that directory.
5866dir_fd may not be implemented on your platform.
5867 If it is unavailable, using it will raise a NotImplementedError.
5868[clinic start generated code]*/
5869
5870PyDoc_STRVAR(os_remove__doc__,
5871"remove($module, /, path, *, dir_fd=None)\n"
5872"--\n"
5873"\n"
5874"Remove a file (same as unlink()).\n"
5875"\n"
5876"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5877" and path should be relative; path will then be relative to that directory.\n"
5878"dir_fd may not be implemented on your platform.\n"
5879" If it is unavailable, using it will raise a NotImplementedError.");
5880
5881#define OS_REMOVE_METHODDEF \
5882 {"remove", (PyCFunction)os_remove, METH_VARARGS|METH_KEYWORDS, os_remove__doc__},
5883
5884static PyObject *
5885os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd);
5886
5887static PyObject *
5888os_remove(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5889{
5890 PyObject *return_value = NULL;
5891 static char *_keywords[] = {"path", "dir_fd", NULL};
5892 path_t path = PATH_T_INITIALIZE("remove", "path", 0, 0);
5893 int dir_fd = DEFAULT_DIR_FD;
5894
5895 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5896 "O&|$O&:remove", _keywords,
5897 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5898 goto exit;
5899 return_value = os_remove_impl(module, &path, dir_fd);
5900
5901exit:
5902 /* Cleanup for path */
5903 path_cleanup(&path);
5904
5905 return return_value;
5906}
5907
5908static PyObject *
5909os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd)
5910/*[clinic end generated code: output=cb170cf1e195b8ed input=e05c5ab55cd30983]*/
5911{
5912 return os_unlink_impl(module, path, dir_fd);
5913}
5914
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005915
Larry Hastings605a62d2012-06-24 04:33:36 -07005916static PyStructSequence_Field uname_result_fields[] = {
5917 {"sysname", "operating system name"},
5918 {"nodename", "name of machine on network (implementation-defined)"},
5919 {"release", "operating system release"},
5920 {"version", "operating system version"},
5921 {"machine", "hardware identifier"},
5922 {NULL}
5923};
5924
5925PyDoc_STRVAR(uname_result__doc__,
5926"uname_result: Result from os.uname().\n\n\
5927This object may be accessed either as a tuple of\n\
5928 (sysname, nodename, release, version, machine),\n\
5929or via the attributes sysname, nodename, release, version, and machine.\n\
5930\n\
5931See os.uname for more information.");
5932
5933static PyStructSequence_Desc uname_result_desc = {
5934 "uname_result", /* name */
5935 uname_result__doc__, /* doc */
5936 uname_result_fields,
5937 5
5938};
5939
5940static PyTypeObject UnameResultType;
5941
5942
5943#ifdef HAVE_UNAME
Larry Hastings2f936352014-08-05 14:04:04 +10005944/*[clinic input]
5945os.uname
5946
5947Return an object identifying the current operating system.
5948
5949The object behaves like a named tuple with the following fields:
5950 (sysname, nodename, release, version, machine)
5951
5952[clinic start generated code]*/
5953
5954PyDoc_STRVAR(os_uname__doc__,
5955"uname($module, /)\n"
5956"--\n"
5957"\n"
5958"Return an object identifying the current operating system.\n"
5959"\n"
5960"The object behaves like a named tuple with the following fields:\n"
5961" (sysname, nodename, release, version, machine)");
5962
5963#define OS_UNAME_METHODDEF \
5964 {"uname", (PyCFunction)os_uname, METH_NOARGS, os_uname__doc__},
5965
Barry Warsaw53699e91996-12-10 23:23:01 +00005966static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005967os_uname_impl(PyModuleDef *module);
5968
5969static PyObject *
5970os_uname(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
5971{
5972 return os_uname_impl(module);
5973}
5974
5975static PyObject *
5976os_uname_impl(PyModuleDef *module)
5977/*[clinic end generated code: output=459a86521ff5041c input=e68bd246db3043ed]*/
Guido van Rossumc39de5f1992-02-05 11:15:54 +00005978{
Victor Stinner8c62be82010-05-06 00:08:46 +00005979 struct utsname u;
5980 int res;
Larry Hastings605a62d2012-06-24 04:33:36 -07005981 PyObject *value;
Neal Norwitze241ce82003-02-17 18:17:05 +00005982
Victor Stinner8c62be82010-05-06 00:08:46 +00005983 Py_BEGIN_ALLOW_THREADS
5984 res = uname(&u);
5985 Py_END_ALLOW_THREADS
5986 if (res < 0)
5987 return posix_error();
Larry Hastings605a62d2012-06-24 04:33:36 -07005988
5989 value = PyStructSequence_New(&UnameResultType);
5990 if (value == NULL)
5991 return NULL;
5992
5993#define SET(i, field) \
5994 { \
Victor Stinnera534fc42013-06-03 22:07:27 +02005995 PyObject *o = PyUnicode_DecodeFSDefault(field); \
Larry Hastings605a62d2012-06-24 04:33:36 -07005996 if (!o) { \
5997 Py_DECREF(value); \
5998 return NULL; \
5999 } \
6000 PyStructSequence_SET_ITEM(value, i, o); \
6001 } \
6002
6003 SET(0, u.sysname);
6004 SET(1, u.nodename);
6005 SET(2, u.release);
6006 SET(3, u.version);
6007 SET(4, u.machine);
6008
6009#undef SET
6010
6011 return value;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00006012}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006013#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006014
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006015
Larry Hastings9cf065c2012-06-22 16:30:09 -07006016
6017typedef struct {
6018 int now;
6019 time_t atime_s;
6020 long atime_ns;
6021 time_t mtime_s;
6022 long mtime_ns;
6023} utime_t;
6024
6025/*
6026 * these macros assume that "utime" is a pointer to a utime_t
6027 * they also intentionally leak the declaration of a pointer named "time"
6028 */
6029#define UTIME_TO_TIMESPEC \
6030 struct timespec ts[2]; \
6031 struct timespec *time; \
6032 if (utime->now) \
6033 time = NULL; \
6034 else { \
6035 ts[0].tv_sec = utime->atime_s; \
6036 ts[0].tv_nsec = utime->atime_ns; \
6037 ts[1].tv_sec = utime->mtime_s; \
6038 ts[1].tv_nsec = utime->mtime_ns; \
6039 time = ts; \
6040 } \
6041
6042#define UTIME_TO_TIMEVAL \
6043 struct timeval tv[2]; \
6044 struct timeval *time; \
6045 if (utime->now) \
6046 time = NULL; \
6047 else { \
6048 tv[0].tv_sec = utime->atime_s; \
6049 tv[0].tv_usec = utime->atime_ns / 1000; \
6050 tv[1].tv_sec = utime->mtime_s; \
6051 tv[1].tv_usec = utime->mtime_ns / 1000; \
6052 time = tv; \
6053 } \
6054
6055#define UTIME_TO_UTIMBUF \
6056 struct utimbuf u[2]; \
6057 struct utimbuf *time; \
6058 if (utime->now) \
6059 time = NULL; \
6060 else { \
6061 u.actime = utime->atime_s; \
6062 u.modtime = utime->mtime_s; \
6063 time = u; \
6064 }
6065
6066#define UTIME_TO_TIME_T \
6067 time_t timet[2]; \
6068 struct timet time; \
6069 if (utime->now) \
6070 time = NULL; \
6071 else { \
6072 timet[0] = utime->atime_s; \
6073 timet[1] = utime->mtime_s; \
6074 time = &timet; \
6075 } \
6076
6077
6078#define UTIME_HAVE_DIR_FD (defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT))
6079
6080#if UTIME_HAVE_DIR_FD
6081
6082static int
6083utime_dir_fd(utime_t *utime, int dir_fd, char *path, int follow_symlinks)
6084{
6085#ifdef HAVE_UTIMENSAT
6086 int flags = follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW;
6087 UTIME_TO_TIMESPEC;
6088 return utimensat(dir_fd, path, time, flags);
6089#elif defined(HAVE_FUTIMESAT)
6090 UTIME_TO_TIMEVAL;
6091 /*
6092 * follow_symlinks will never be false here;
6093 * we only allow !follow_symlinks and dir_fd together
6094 * if we have utimensat()
6095 */
6096 assert(follow_symlinks);
6097 return futimesat(dir_fd, path, time);
6098#endif
6099}
6100
Larry Hastings2f936352014-08-05 14:04:04 +10006101 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_converter
6102#else
6103 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings9cf065c2012-06-22 16:30:09 -07006104#endif
6105
6106#define UTIME_HAVE_FD (defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS))
6107
6108#if UTIME_HAVE_FD
6109
6110static int
6111utime_fd(utime_t *utime, int fd)
6112{
6113#ifdef HAVE_FUTIMENS
6114 UTIME_TO_TIMESPEC;
6115 return futimens(fd, time);
6116#else
6117 UTIME_TO_TIMEVAL;
6118 return futimes(fd, time);
6119#endif
6120}
6121
Larry Hastings2f936352014-08-05 14:04:04 +10006122 #define PATH_UTIME_HAVE_FD 1
6123#else
6124 #define PATH_UTIME_HAVE_FD 0
Larry Hastings9cf065c2012-06-22 16:30:09 -07006125#endif
6126
6127
6128#define UTIME_HAVE_NOFOLLOW_SYMLINKS \
6129 (defined(HAVE_UTIMENSAT) || defined(HAVE_LUTIMES))
6130
6131#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6132
6133static int
6134utime_nofollow_symlinks(utime_t *utime, char *path)
6135{
6136#ifdef HAVE_UTIMENSAT
6137 UTIME_TO_TIMESPEC;
6138 return utimensat(DEFAULT_DIR_FD, path, time, AT_SYMLINK_NOFOLLOW);
6139#else
6140 UTIME_TO_TIMEVAL;
6141 return lutimes(path, time);
6142#endif
6143}
6144
6145#endif
6146
6147#ifndef MS_WINDOWS
6148
6149static int
6150utime_default(utime_t *utime, char *path)
6151{
6152#ifdef HAVE_UTIMENSAT
6153 UTIME_TO_TIMESPEC;
6154 return utimensat(DEFAULT_DIR_FD, path, time, 0);
6155#elif defined(HAVE_UTIMES)
6156 UTIME_TO_TIMEVAL;
6157 return utimes(path, time);
6158#elif defined(HAVE_UTIME_H)
6159 UTIME_TO_UTIMBUF;
6160 return utime(path, time);
6161#else
6162 UTIME_TO_TIME_T;
6163 return utime(path, time);
6164#endif
6165}
6166
6167#endif
6168
Larry Hastings76ad59b2012-05-03 00:30:07 -07006169static int
6170split_py_long_to_s_and_ns(PyObject *py_long, time_t *s, long *ns)
6171{
6172 int result = 0;
Benjamin Petersonfbd85a02012-05-04 11:06:09 -04006173 PyObject *divmod;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006174 divmod = PyNumber_Divmod(py_long, billion);
6175 if (!divmod)
6176 goto exit;
6177 *s = _PyLong_AsTime_t(PyTuple_GET_ITEM(divmod, 0));
6178 if ((*s == -1) && PyErr_Occurred())
6179 goto exit;
6180 *ns = PyLong_AsLong(PyTuple_GET_ITEM(divmod, 1));
Benjamin Peterson35a8f0d2012-05-04 01:10:59 -04006181 if ((*ns == -1) && PyErr_Occurred())
Larry Hastings76ad59b2012-05-03 00:30:07 -07006182 goto exit;
6183
6184 result = 1;
6185exit:
6186 Py_XDECREF(divmod);
6187 return result;
6188}
6189
Larry Hastings2f936352014-08-05 14:04:04 +10006190
6191/*[clinic input]
6192os.utime
6193
6194 path: path_t(allow_fd='PATH_UTIME_HAVE_FD')
6195 times: object = NULL
6196 *
6197 ns: object = NULL
6198 dir_fd: dir_fd(requires='futimensat') = None
6199 follow_symlinks: bool=True
6200
6201# "utime(path, times=None, *, ns=None, dir_fd=None, follow_symlinks=True)\n\
6202
6203Set the access and modified time of path.
6204
6205path may always be specified as a string.
6206On some platforms, path may also be specified as an open file descriptor.
6207 If this functionality is unavailable, using it raises an exception.
6208
6209If times is not None, it must be a tuple (atime, mtime);
6210 atime and mtime should be expressed as float seconds since the epoch.
6211If ns is not None, it must be a tuple (atime_ns, mtime_ns);
6212 atime_ns and mtime_ns should be expressed as integer nanoseconds
6213 since the epoch.
6214If both times and ns are None, utime uses the current time.
6215Specifying tuples for both times and ns is an error.
6216
6217If dir_fd is not None, it should be a file descriptor open to a directory,
6218 and path should be relative; path will then be relative to that directory.
6219If follow_symlinks is False, and the last element of the path is a symbolic
6220 link, utime will modify the symbolic link itself instead of the file the
6221 link points to.
6222It is an error to use dir_fd or follow_symlinks when specifying path
6223 as an open file descriptor.
6224dir_fd and follow_symlinks may not be available on your platform.
6225 If they are unavailable, using them will raise a NotImplementedError.
6226
6227[clinic start generated code]*/
6228
6229PyDoc_STRVAR(os_utime__doc__,
6230"utime($module, /, path, times=None, *, ns=None, dir_fd=None,\n"
6231" follow_symlinks=True)\n"
6232"--\n"
6233"\n"
6234"Set the access and modified time of path.\n"
6235"\n"
6236"path may always be specified as a string.\n"
6237"On some platforms, path may also be specified as an open file descriptor.\n"
6238" If this functionality is unavailable, using it raises an exception.\n"
6239"\n"
6240"If times is not None, it must be a tuple (atime, mtime);\n"
6241" atime and mtime should be expressed as float seconds since the epoch.\n"
6242"If ns is not None, it must be a tuple (atime_ns, mtime_ns);\n"
6243" atime_ns and mtime_ns should be expressed as integer nanoseconds\n"
6244" since the epoch.\n"
6245"If both times and ns are None, utime uses the current time.\n"
6246"Specifying tuples for both times and ns is an error.\n"
6247"\n"
6248"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
6249" and path should be relative; path will then be relative to that directory.\n"
6250"If follow_symlinks is False, and the last element of the path is a symbolic\n"
6251" link, utime will modify the symbolic link itself instead of the file the\n"
6252" link points to.\n"
6253"It is an error to use dir_fd or follow_symlinks when specifying path\n"
6254" as an open file descriptor.\n"
6255"dir_fd and follow_symlinks may not be available on your platform.\n"
6256" If they are unavailable, using them will raise a NotImplementedError.");
6257
6258#define OS_UTIME_METHODDEF \
6259 {"utime", (PyCFunction)os_utime, METH_VARARGS|METH_KEYWORDS, os_utime__doc__},
6260
Larry Hastings9cf065c2012-06-22 16:30:09 -07006261static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006262os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks);
6263
6264static PyObject *
6265os_utime(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings76ad59b2012-05-03 00:30:07 -07006266{
Larry Hastings2f936352014-08-05 14:04:04 +10006267 PyObject *return_value = NULL;
6268 static char *_keywords[] = {"path", "times", "ns", "dir_fd", "follow_symlinks", NULL};
6269 path_t path = PATH_T_INITIALIZE("utime", "path", 0, PATH_UTIME_HAVE_FD);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006270 PyObject *times = NULL;
6271 PyObject *ns = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07006272 int dir_fd = DEFAULT_DIR_FD;
6273 int follow_symlinks = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006274
Larry Hastings2f936352014-08-05 14:04:04 +10006275 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6276 "O&|O$OO&p:utime", _keywords,
6277 path_converter, &path, &times, &ns, FUTIMENSAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
6278 goto exit;
6279 return_value = os_utime_impl(module, &path, times, ns, dir_fd, follow_symlinks);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006280
Larry Hastings2f936352014-08-05 14:04:04 +10006281exit:
6282 /* Cleanup for path */
6283 path_cleanup(&path);
6284
6285 return return_value;
6286}
6287
6288static PyObject *
6289os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks)
6290/*[clinic end generated code: output=891489c35cc68c5d input=1f18c17d5941aa82]*/
6291{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006292#ifdef MS_WINDOWS
6293 HANDLE hFile;
6294 FILETIME atime, mtime;
6295#else
6296 int result;
6297#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006298
Larry Hastings9cf065c2012-06-22 16:30:09 -07006299 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10006300 utime_t utime;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006301
Christian Heimesb3c87242013-08-01 00:08:16 +02006302 memset(&utime, 0, sizeof(utime_t));
Larry Hastings76ad59b2012-05-03 00:30:07 -07006303
Larry Hastings9cf065c2012-06-22 16:30:09 -07006304 if (times && (times != Py_None) && ns) {
6305 PyErr_SetString(PyExc_ValueError,
6306 "utime: you may specify either 'times'"
6307 " or 'ns' but not both");
6308 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006309 }
6310
6311 if (times && (times != Py_None)) {
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006312 time_t a_sec, m_sec;
6313 long a_nsec, m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006314 if (!PyTuple_CheckExact(times) || (PyTuple_Size(times) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006315 PyErr_SetString(PyExc_TypeError,
6316 "utime: 'times' must be either"
6317 " a tuple of two ints or None");
6318 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006319 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006320 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006321 if (_PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 0),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006322 &a_sec, &a_nsec, _PyTime_ROUND_DOWN) == -1 ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006323 _PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 1),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006324 &m_sec, &m_nsec, _PyTime_ROUND_DOWN) == -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006325 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006326 }
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006327 utime.atime_s = a_sec;
6328 utime.atime_ns = a_nsec;
6329 utime.mtime_s = m_sec;
6330 utime.mtime_ns = m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006331 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006332 else if (ns) {
Larry Hastings76ad59b2012-05-03 00:30:07 -07006333 if (!PyTuple_CheckExact(ns) || (PyTuple_Size(ns) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006334 PyErr_SetString(PyExc_TypeError,
6335 "utime: 'ns' must be a tuple of two ints");
6336 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006337 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006338 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006339 if (!split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 0),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006340 &utime.atime_s, &utime.atime_ns) ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006341 !split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 1),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006342 &utime.mtime_s, &utime.mtime_ns)) {
6343 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006344 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006345 }
6346 else {
6347 /* times and ns are both None/unspecified. use "now". */
6348 utime.now = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006349 }
6350
Larry Hastings9cf065c2012-06-22 16:30:09 -07006351#if !UTIME_HAVE_NOFOLLOW_SYMLINKS
6352 if (follow_symlinks_specified("utime", follow_symlinks))
6353 goto exit;
6354#endif
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006355
Larry Hastings2f936352014-08-05 14:04:04 +10006356 if (path_and_dir_fd_invalid("utime", path, dir_fd) ||
6357 dir_fd_and_fd_invalid("utime", dir_fd, path->fd) ||
6358 fd_and_follow_symlinks_invalid("utime", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -07006359 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006360
Larry Hastings9cf065c2012-06-22 16:30:09 -07006361#if !defined(HAVE_UTIMENSAT)
6362 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
Georg Brandl969288e2012-06-26 09:25:44 +02006363 PyErr_SetString(PyExc_ValueError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006364 "utime: cannot use dir_fd and follow_symlinks "
6365 "together on this platform");
6366 goto exit;
6367 }
6368#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006369
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006370#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07006371 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006372 if (path->wide)
6373 hFile = CreateFileW(path->wide, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006374 NULL, OPEN_EXISTING,
6375 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006376 else
Larry Hastings2f936352014-08-05 14:04:04 +10006377 hFile = CreateFileA(path->narrow, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006378 NULL, OPEN_EXISTING,
6379 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006380 Py_END_ALLOW_THREADS
6381 if (hFile == INVALID_HANDLE_VALUE) {
Larry Hastings2f936352014-08-05 14:04:04 +10006382 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006383 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006384 }
6385
Larry Hastings9cf065c2012-06-22 16:30:09 -07006386 if (utime.now) {
Antoine Pitrou91a7af32013-11-23 15:23:26 +01006387 GetSystemTimeAsFileTime(&mtime);
6388 atime = mtime;
Victor Stinner8c62be82010-05-06 00:08:46 +00006389 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006390 else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006391 time_t_to_FILE_TIME(utime.atime_s, utime.atime_ns, &atime);
6392 time_t_to_FILE_TIME(utime.mtime_s, utime.mtime_ns, &mtime);
Victor Stinner8c62be82010-05-06 00:08:46 +00006393 }
6394 if (!SetFileTime(hFile, NULL, &atime, &mtime)) {
6395 /* Avoid putting the file name into the error here,
6396 as that may confuse the user into believing that
6397 something is wrong with the file, when it also
6398 could be the time stamp that gives a problem. */
Victor Stinnerb024e842012-10-31 22:24:06 +01006399 PyErr_SetFromWindowsErr(0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006400 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006401 }
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006402#else /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006403 Py_BEGIN_ALLOW_THREADS
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006404
Larry Hastings9cf065c2012-06-22 16:30:09 -07006405#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6406 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10006407 result = utime_nofollow_symlinks(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006408 else
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006409#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07006410
6411#if UTIME_HAVE_DIR_FD
6412 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10006413 result = utime_dir_fd(&utime, dir_fd, path->narrow, follow_symlinks);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006414 else
6415#endif
6416
6417#if UTIME_HAVE_FD
Larry Hastings2f936352014-08-05 14:04:04 +10006418 if (path->fd != -1)
6419 result = utime_fd(&utime, path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006420 else
6421#endif
6422
Larry Hastings2f936352014-08-05 14:04:04 +10006423 result = utime_default(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006424
6425 Py_END_ALLOW_THREADS
6426
6427 if (result < 0) {
6428 /* see previous comment about not putting filename in error here */
6429 return_value = posix_error();
6430 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006431 }
Larry Hastings76ad59b2012-05-03 00:30:07 -07006432
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006433#endif /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006434
6435 Py_INCREF(Py_None);
6436 return_value = Py_None;
6437
6438exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006439#ifdef MS_WINDOWS
6440 if (hFile != INVALID_HANDLE_VALUE)
6441 CloseHandle(hFile);
6442#endif
6443 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00006444}
6445
Guido van Rossum3b066191991-06-04 19:40:25 +00006446/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006447
Larry Hastings2f936352014-08-05 14:04:04 +10006448
6449/*[clinic input]
6450os._exit
6451
6452 status: int
6453
6454Exit to the system with specified status, without normal exit processing.
6455[clinic start generated code]*/
6456
6457PyDoc_STRVAR(os__exit__doc__,
6458"_exit($module, /, status)\n"
6459"--\n"
6460"\n"
6461"Exit to the system with specified status, without normal exit processing.");
6462
6463#define OS__EXIT_METHODDEF \
6464 {"_exit", (PyCFunction)os__exit, METH_VARARGS|METH_KEYWORDS, os__exit__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006465
Barry Warsaw53699e91996-12-10 23:23:01 +00006466static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006467os__exit_impl(PyModuleDef *module, int status);
6468
6469static PyObject *
6470os__exit(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85e3b011991-06-03 12:42:10 +00006471{
Larry Hastings2f936352014-08-05 14:04:04 +10006472 PyObject *return_value = NULL;
6473 static char *_keywords[] = {"status", NULL};
6474 int status;
6475
6476 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6477 "i:_exit", _keywords,
6478 &status))
6479 goto exit;
6480 return_value = os__exit_impl(module, status);
6481
6482exit:
6483 return return_value;
6484}
6485
6486static PyObject *
6487os__exit_impl(PyModuleDef *module, int status)
6488/*[clinic end generated code: output=4f9858c4cc2dcb89 input=5e6d57556b0c4a62]*/
6489{
6490 _exit(status);
Victor Stinner8c62be82010-05-06 00:08:46 +00006491 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006492}
6493
Martin v. Löwis114619e2002-10-07 06:44:21 +00006494#if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
6495static void
Martin v. Löwis725507b2006-03-07 12:08:51 +00006496free_string_array(char **array, Py_ssize_t count)
Martin v. Löwis114619e2002-10-07 06:44:21 +00006497{
Victor Stinner8c62be82010-05-06 00:08:46 +00006498 Py_ssize_t i;
6499 for (i = 0; i < count; i++)
6500 PyMem_Free(array[i]);
6501 PyMem_DEL(array);
Martin v. Löwis114619e2002-10-07 06:44:21 +00006502}
Martin v. Löwis011e8422009-05-05 04:43:17 +00006503
Antoine Pitrou69f71142009-05-24 21:25:49 +00006504static
Martin v. Löwis011e8422009-05-05 04:43:17 +00006505int fsconvert_strdup(PyObject *o, char**out)
6506{
Victor Stinner8c62be82010-05-06 00:08:46 +00006507 PyObject *bytes;
6508 Py_ssize_t size;
6509 if (!PyUnicode_FSConverter(o, &bytes))
6510 return 0;
6511 size = PyBytes_GET_SIZE(bytes);
6512 *out = PyMem_Malloc(size+1);
Victor Stinner50abf222013-11-07 23:56:10 +01006513 if (!*out) {
6514 PyErr_NoMemory();
Victor Stinner8c62be82010-05-06 00:08:46 +00006515 return 0;
Victor Stinner50abf222013-11-07 23:56:10 +01006516 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006517 memcpy(*out, PyBytes_AsString(bytes), size+1);
6518 Py_DECREF(bytes);
6519 return 1;
Martin v. Löwis011e8422009-05-05 04:43:17 +00006520}
Martin v. Löwis114619e2002-10-07 06:44:21 +00006521#endif
6522
Ross Lagerwall7807c352011-03-17 20:20:30 +02006523#if defined(HAVE_EXECV) || defined (HAVE_FEXECVE)
Victor Stinner13bb71c2010-04-23 21:41:56 +00006524static char**
6525parse_envlist(PyObject* env, Py_ssize_t *envc_ptr)
6526{
Victor Stinner8c62be82010-05-06 00:08:46 +00006527 char **envlist;
6528 Py_ssize_t i, pos, envc;
6529 PyObject *keys=NULL, *vals=NULL;
6530 PyObject *key, *val, *key2, *val2;
6531 char *p, *k, *v;
6532 size_t len;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006533
Victor Stinner8c62be82010-05-06 00:08:46 +00006534 i = PyMapping_Size(env);
6535 if (i < 0)
6536 return NULL;
6537 envlist = PyMem_NEW(char *, i + 1);
6538 if (envlist == NULL) {
6539 PyErr_NoMemory();
6540 return NULL;
6541 }
6542 envc = 0;
6543 keys = PyMapping_Keys(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006544 if (!keys)
6545 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00006546 vals = PyMapping_Values(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006547 if (!vals)
Victor Stinner8c62be82010-05-06 00:08:46 +00006548 goto error;
6549 if (!PyList_Check(keys) || !PyList_Check(vals)) {
6550 PyErr_Format(PyExc_TypeError,
6551 "env.keys() or env.values() is not a list");
6552 goto error;
6553 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006554
Victor Stinner8c62be82010-05-06 00:08:46 +00006555 for (pos = 0; pos < i; pos++) {
6556 key = PyList_GetItem(keys, pos);
6557 val = PyList_GetItem(vals, pos);
6558 if (!key || !val)
6559 goto error;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006560
Victor Stinner8c62be82010-05-06 00:08:46 +00006561 if (PyUnicode_FSConverter(key, &key2) == 0)
6562 goto error;
6563 if (PyUnicode_FSConverter(val, &val2) == 0) {
6564 Py_DECREF(key2);
6565 goto error;
6566 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006567
Victor Stinner8c62be82010-05-06 00:08:46 +00006568 k = PyBytes_AsString(key2);
6569 v = PyBytes_AsString(val2);
6570 len = PyBytes_GET_SIZE(key2) + PyBytes_GET_SIZE(val2) + 2;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006571
Victor Stinner8c62be82010-05-06 00:08:46 +00006572 p = PyMem_NEW(char, len);
6573 if (p == NULL) {
6574 PyErr_NoMemory();
6575 Py_DECREF(key2);
6576 Py_DECREF(val2);
6577 goto error;
6578 }
6579 PyOS_snprintf(p, len, "%s=%s", k, v);
6580 envlist[envc++] = p;
6581 Py_DECREF(key2);
6582 Py_DECREF(val2);
Victor Stinner8c62be82010-05-06 00:08:46 +00006583 }
6584 Py_DECREF(vals);
6585 Py_DECREF(keys);
Victor Stinner13bb71c2010-04-23 21:41:56 +00006586
Victor Stinner8c62be82010-05-06 00:08:46 +00006587 envlist[envc] = 0;
6588 *envc_ptr = envc;
6589 return envlist;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006590
6591error:
Victor Stinner8c62be82010-05-06 00:08:46 +00006592 Py_XDECREF(keys);
6593 Py_XDECREF(vals);
6594 while (--envc >= 0)
6595 PyMem_DEL(envlist[envc]);
6596 PyMem_DEL(envlist);
6597 return NULL;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006598}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006599
Ross Lagerwall7807c352011-03-17 20:20:30 +02006600static char**
6601parse_arglist(PyObject* argv, Py_ssize_t *argc)
6602{
6603 int i;
6604 char **argvlist = PyMem_NEW(char *, *argc+1);
6605 if (argvlist == NULL) {
6606 PyErr_NoMemory();
6607 return NULL;
6608 }
6609 for (i = 0; i < *argc; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006610 PyObject* item = PySequence_ITEM(argv, i);
6611 if (item == NULL)
6612 goto fail;
6613 if (!fsconvert_strdup(item, &argvlist[i])) {
6614 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006615 goto fail;
6616 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006617 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006618 }
6619 argvlist[*argc] = NULL;
6620 return argvlist;
6621fail:
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006622 *argc = i;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006623 free_string_array(argvlist, *argc);
6624 return NULL;
6625}
6626#endif
6627
Larry Hastings2f936352014-08-05 14:04:04 +10006628
Ross Lagerwall7807c352011-03-17 20:20:30 +02006629#ifdef HAVE_EXECV
Larry Hastings2f936352014-08-05 14:04:04 +10006630/*[clinic input]
6631os.execv
6632
6633 path: FSConverter
6634 Path of executable file.
6635 argv: object
6636 Tuple or list of strings.
6637 /
6638
6639Execute an executable path with arguments, replacing current process.
6640[clinic start generated code]*/
6641
6642PyDoc_STRVAR(os_execv__doc__,
6643"execv($module, path, argv, /)\n"
6644"--\n"
6645"\n"
6646"Execute an executable path with arguments, replacing current process.\n"
6647"\n"
6648" path\n"
6649" Path of executable file.\n"
6650" argv\n"
6651" Tuple or list of strings.");
6652
6653#define OS_EXECV_METHODDEF \
6654 {"execv", (PyCFunction)os_execv, METH_VARARGS, os_execv__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02006655
6656static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006657os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv);
6658
6659static PyObject *
6660os_execv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006661{
Larry Hastings2f936352014-08-05 14:04:04 +10006662 PyObject *return_value = NULL;
6663 PyObject *path = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006664 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006665
6666 if (!PyArg_ParseTuple(args,
6667 "O&O:execv",
6668 PyUnicode_FSConverter, &path, &argv))
6669 goto exit;
6670 return_value = os_execv_impl(module, path, argv);
6671
6672exit:
6673 /* Cleanup for path */
6674 Py_XDECREF(path);
6675
6676 return return_value;
6677}
6678
6679static PyObject *
6680os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv)
6681/*[clinic end generated code: output=b0f5f2caa6097edc input=96041559925e5229]*/
6682{
6683 char *path_char;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006684 char **argvlist;
6685 Py_ssize_t argc;
6686
6687 /* execv has two arguments: (path, argv), where
6688 argv is a list or tuple of strings. */
6689
Larry Hastings2f936352014-08-05 14:04:04 +10006690 path_char = PyBytes_AsString(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006691 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
6692 PyErr_SetString(PyExc_TypeError,
6693 "execv() arg 2 must be a tuple or list");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006694 return NULL;
6695 }
6696 argc = PySequence_Size(argv);
6697 if (argc < 1) {
6698 PyErr_SetString(PyExc_ValueError, "execv() arg 2 must not be empty");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006699 return NULL;
6700 }
6701
6702 argvlist = parse_arglist(argv, &argc);
6703 if (argvlist == NULL) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02006704 return NULL;
6705 }
6706
Larry Hastings2f936352014-08-05 14:04:04 +10006707 execv(path_char, argvlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006708
6709 /* If we get here it's definitely an error */
6710
6711 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006712 return posix_error();
6713}
6714
Larry Hastings2f936352014-08-05 14:04:04 +10006715
6716/*[clinic input]
6717os.execve
6718
6719 path: path_t(allow_fd='PATH_HAVE_FEXECVE')
6720 Path of executable file.
6721 argv: object
6722 Tuple or list of strings.
6723 env: object
6724 Dictionary of strings mapping to strings.
6725
6726Execute an executable path with arguments, replacing current process.
6727[clinic start generated code]*/
6728
6729PyDoc_STRVAR(os_execve__doc__,
6730"execve($module, /, path, argv, env)\n"
6731"--\n"
6732"\n"
6733"Execute an executable path with arguments, replacing current process.\n"
6734"\n"
6735" path\n"
6736" Path of executable file.\n"
6737" argv\n"
6738" Tuple or list of strings.\n"
6739" env\n"
6740" Dictionary of strings mapping to strings.");
6741
6742#define OS_EXECVE_METHODDEF \
6743 {"execve", (PyCFunction)os_execve, METH_VARARGS|METH_KEYWORDS, os_execve__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006744
Barry Warsaw53699e91996-12-10 23:23:01 +00006745static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006746os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env);
6747
6748static PyObject *
6749os_execve(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006750{
Larry Hastings2f936352014-08-05 14:04:04 +10006751 PyObject *return_value = NULL;
6752 static char *_keywords[] = {"path", "argv", "env", NULL};
6753 path_t path = PATH_T_INITIALIZE("execve", "path", 0, PATH_HAVE_FEXECVE);
6754 PyObject *argv;
6755 PyObject *env;
6756
6757 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6758 "O&OO:execve", _keywords,
6759 path_converter, &path, &argv, &env))
6760 goto exit;
6761 return_value = os_execve_impl(module, &path, argv, env);
6762
6763exit:
6764 /* Cleanup for path */
6765 path_cleanup(&path);
6766
6767 return return_value;
6768}
6769
6770static PyObject *
6771os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env)
6772/*[clinic end generated code: output=fb283760f5d15ab7 input=626804fa092606d9]*/
6773{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006774 char **argvlist = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006775 char **envlist;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006776 Py_ssize_t argc, envc;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006777
Victor Stinner8c62be82010-05-06 00:08:46 +00006778 /* execve has three arguments: (path, argv, env), where
6779 argv is a list or tuple of strings and env is a dictionary
6780 like posix.environ. */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006781
Ross Lagerwall7807c352011-03-17 20:20:30 +02006782 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006783 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006784 "execve: argv must be a tuple or list");
6785 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006786 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02006787 argc = PySequence_Size(argv);
Victor Stinner8c62be82010-05-06 00:08:46 +00006788 if (!PyMapping_Check(env)) {
6789 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006790 "execve: environment must be a mapping object");
6791 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006792 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006793
Ross Lagerwall7807c352011-03-17 20:20:30 +02006794 argvlist = parse_arglist(argv, &argc);
Victor Stinner8c62be82010-05-06 00:08:46 +00006795 if (argvlist == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006796 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006797 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006798
Victor Stinner8c62be82010-05-06 00:08:46 +00006799 envlist = parse_envlist(env, &envc);
6800 if (envlist == NULL)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006801 goto fail;
6802
Larry Hastings9cf065c2012-06-22 16:30:09 -07006803#ifdef HAVE_FEXECVE
Larry Hastings2f936352014-08-05 14:04:04 +10006804 if (path->fd > -1)
6805 fexecve(path->fd, argvlist, envlist);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006806 else
6807#endif
Larry Hastings2f936352014-08-05 14:04:04 +10006808 execve(path->narrow, argvlist, envlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006809
6810 /* If we get here it's definitely an error */
6811
Larry Hastings2f936352014-08-05 14:04:04 +10006812 path_error(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006813
6814 while (--envc >= 0)
6815 PyMem_DEL(envlist[envc]);
6816 PyMem_DEL(envlist);
6817 fail:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006818 if (argvlist)
6819 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006820 return NULL;
6821}
Larry Hastings9cf065c2012-06-22 16:30:09 -07006822#endif /* HAVE_EXECV */
6823
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006824
Guido van Rossuma1065681999-01-25 23:20:23 +00006825#ifdef HAVE_SPAWNV
Larry Hastings2f936352014-08-05 14:04:04 +10006826/*[clinic input]
6827os.spawnv
6828
6829 mode: int
6830 Mode of process creation.
6831 path: FSConverter
6832 Path of executable file.
6833 argv: object
6834 Tuple or list of strings.
6835 /
6836
6837Execute the program specified by path in a new process.
6838[clinic start generated code]*/
6839
6840PyDoc_STRVAR(os_spawnv__doc__,
6841"spawnv($module, mode, path, argv, /)\n"
6842"--\n"
6843"\n"
6844"Execute the program specified by path in a new process.\n"
6845"\n"
6846" mode\n"
6847" Mode of process creation.\n"
6848" path\n"
6849" Path of executable file.\n"
6850" argv\n"
6851" Tuple or list of strings.");
6852
6853#define OS_SPAWNV_METHODDEF \
6854 {"spawnv", (PyCFunction)os_spawnv, METH_VARARGS, os_spawnv__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00006855
6856static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006857os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv);
6858
6859static PyObject *
6860os_spawnv(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00006861{
Larry Hastings2f936352014-08-05 14:04:04 +10006862 PyObject *return_value = NULL;
6863 int mode;
6864 PyObject *path = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006865 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006866
6867 if (!PyArg_ParseTuple(args,
6868 "iO&O:spawnv",
6869 &mode, PyUnicode_FSConverter, &path, &argv))
6870 goto exit;
6871 return_value = os_spawnv_impl(module, mode, path, argv);
6872
6873exit:
6874 /* Cleanup for path */
6875 Py_XDECREF(path);
6876
6877 return return_value;
6878}
6879
6880static PyObject *
6881os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv)
6882/*[clinic end generated code: output=dfee6be062e780e3 input=042c91dfc1e6debc]*/
6883{
6884 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00006885 char **argvlist;
Larry Hastings2f936352014-08-05 14:04:04 +10006886 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00006887 Py_ssize_t argc;
6888 Py_intptr_t spawnval;
6889 PyObject *(*getitem)(PyObject *, Py_ssize_t);
Guido van Rossuma1065681999-01-25 23:20:23 +00006890
Victor Stinner8c62be82010-05-06 00:08:46 +00006891 /* spawnv has three arguments: (mode, path, argv), where
6892 argv is a list or tuple of strings. */
Guido van Rossuma1065681999-01-25 23:20:23 +00006893
Larry Hastings2f936352014-08-05 14:04:04 +10006894 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00006895 if (PyList_Check(argv)) {
6896 argc = PyList_Size(argv);
6897 getitem = PyList_GetItem;
6898 }
6899 else if (PyTuple_Check(argv)) {
6900 argc = PyTuple_Size(argv);
6901 getitem = PyTuple_GetItem;
6902 }
6903 else {
6904 PyErr_SetString(PyExc_TypeError,
6905 "spawnv() arg 2 must be a tuple or list");
Victor Stinner8c62be82010-05-06 00:08:46 +00006906 return NULL;
6907 }
Guido van Rossuma1065681999-01-25 23:20:23 +00006908
Victor Stinner8c62be82010-05-06 00:08:46 +00006909 argvlist = PyMem_NEW(char *, argc+1);
6910 if (argvlist == NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006911 return PyErr_NoMemory();
6912 }
6913 for (i = 0; i < argc; i++) {
6914 if (!fsconvert_strdup((*getitem)(argv, i),
6915 &argvlist[i])) {
6916 free_string_array(argvlist, i);
6917 PyErr_SetString(
6918 PyExc_TypeError,
6919 "spawnv() arg 2 must contain only strings");
Victor Stinner8c62be82010-05-06 00:08:46 +00006920 return NULL;
6921 }
6922 }
6923 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00006924
Victor Stinner8c62be82010-05-06 00:08:46 +00006925 if (mode == _OLD_P_OVERLAY)
6926 mode = _P_OVERLAY;
Tim Peters5aa91602002-01-30 05:46:57 +00006927
Victor Stinner8c62be82010-05-06 00:08:46 +00006928 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006929 spawnval = _spawnv(mode, path_char, argvlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00006930 Py_END_ALLOW_THREADS
Tim Peters5aa91602002-01-30 05:46:57 +00006931
Victor Stinner8c62be82010-05-06 00:08:46 +00006932 free_string_array(argvlist, argc);
Guido van Rossuma1065681999-01-25 23:20:23 +00006933
Victor Stinner8c62be82010-05-06 00:08:46 +00006934 if (spawnval == -1)
6935 return posix_error();
6936 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006937 return Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00006938}
6939
6940
Larry Hastings2f936352014-08-05 14:04:04 +10006941/*[clinic input]
6942os.spawnve
6943
6944 mode: int
6945 Mode of process creation.
6946 path: FSConverter
6947 Path of executable file.
6948 argv: object
6949 Tuple or list of strings.
6950 env: object
6951 Dictionary of strings mapping to strings.
6952 /
6953
6954Execute the program specified by path in a new process.
6955[clinic start generated code]*/
6956
6957PyDoc_STRVAR(os_spawnve__doc__,
6958"spawnve($module, mode, path, argv, env, /)\n"
6959"--\n"
6960"\n"
6961"Execute the program specified by path in a new process.\n"
6962"\n"
6963" mode\n"
6964" Mode of process creation.\n"
6965" path\n"
6966" Path of executable file.\n"
6967" argv\n"
6968" Tuple or list of strings.\n"
6969" env\n"
6970" Dictionary of strings mapping to strings.");
6971
6972#define OS_SPAWNVE_METHODDEF \
6973 {"spawnve", (PyCFunction)os_spawnve, METH_VARARGS, os_spawnve__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00006974
6975static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006976os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env);
6977
6978static PyObject *
6979os_spawnve(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00006980{
Larry Hastings2f936352014-08-05 14:04:04 +10006981 PyObject *return_value = NULL;
6982 int mode;
6983 PyObject *path = NULL;
6984 PyObject *argv;
6985 PyObject *env;
6986
6987 if (!PyArg_ParseTuple(args,
6988 "iO&OO:spawnve",
6989 &mode, PyUnicode_FSConverter, &path, &argv, &env))
6990 goto exit;
6991 return_value = os_spawnve_impl(module, mode, path, argv, env);
6992
6993exit:
6994 /* Cleanup for path */
6995 Py_XDECREF(path);
6996
6997 return return_value;
6998}
6999
7000static PyObject *
7001os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env)
7002/*[clinic end generated code: output=6f7df38473f63c7c input=02362fd937963f8f]*/
7003{
7004 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00007005 char **argvlist;
7006 char **envlist;
7007 PyObject *res = NULL;
Antoine Pitrou22e41552010-08-15 18:07:50 +00007008 Py_ssize_t argc, i, envc;
Victor Stinner8c62be82010-05-06 00:08:46 +00007009 Py_intptr_t spawnval;
7010 PyObject *(*getitem)(PyObject *, Py_ssize_t);
7011 Py_ssize_t lastarg = 0;
Guido van Rossuma1065681999-01-25 23:20:23 +00007012
Victor Stinner8c62be82010-05-06 00:08:46 +00007013 /* spawnve has four arguments: (mode, path, argv, env), where
7014 argv is a list or tuple of strings and env is a dictionary
7015 like posix.environ. */
Guido van Rossuma1065681999-01-25 23:20:23 +00007016
Larry Hastings2f936352014-08-05 14:04:04 +10007017 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00007018 if (PyList_Check(argv)) {
7019 argc = PyList_Size(argv);
7020 getitem = PyList_GetItem;
7021 }
7022 else if (PyTuple_Check(argv)) {
7023 argc = PyTuple_Size(argv);
7024 getitem = PyTuple_GetItem;
7025 }
7026 else {
7027 PyErr_SetString(PyExc_TypeError,
7028 "spawnve() arg 2 must be a tuple or list");
7029 goto fail_0;
7030 }
7031 if (!PyMapping_Check(env)) {
7032 PyErr_SetString(PyExc_TypeError,
7033 "spawnve() arg 3 must be a mapping object");
7034 goto fail_0;
7035 }
Guido van Rossuma1065681999-01-25 23:20:23 +00007036
Victor Stinner8c62be82010-05-06 00:08:46 +00007037 argvlist = PyMem_NEW(char *, argc+1);
7038 if (argvlist == NULL) {
7039 PyErr_NoMemory();
7040 goto fail_0;
7041 }
7042 for (i = 0; i < argc; i++) {
7043 if (!fsconvert_strdup((*getitem)(argv, i),
7044 &argvlist[i]))
7045 {
7046 lastarg = i;
7047 goto fail_1;
7048 }
7049 }
7050 lastarg = argc;
7051 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00007052
Victor Stinner8c62be82010-05-06 00:08:46 +00007053 envlist = parse_envlist(env, &envc);
7054 if (envlist == NULL)
7055 goto fail_1;
Guido van Rossuma1065681999-01-25 23:20:23 +00007056
Victor Stinner8c62be82010-05-06 00:08:46 +00007057 if (mode == _OLD_P_OVERLAY)
7058 mode = _P_OVERLAY;
Tim Peters25059d32001-12-07 20:35:43 +00007059
Victor Stinner8c62be82010-05-06 00:08:46 +00007060 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007061 spawnval = _spawnve(mode, path_char, argvlist, envlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00007062 Py_END_ALLOW_THREADS
Tim Peters25059d32001-12-07 20:35:43 +00007063
Victor Stinner8c62be82010-05-06 00:08:46 +00007064 if (spawnval == -1)
7065 (void) posix_error();
7066 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01007067 res = Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00007068
Victor Stinner8c62be82010-05-06 00:08:46 +00007069 while (--envc >= 0)
7070 PyMem_DEL(envlist[envc]);
7071 PyMem_DEL(envlist);
Guido van Rossum0847c5c2002-12-13 18:36:22 +00007072 fail_1:
Victor Stinner8c62be82010-05-06 00:08:46 +00007073 free_string_array(argvlist, lastarg);
Martin v. Löwis114619e2002-10-07 06:44:21 +00007074 fail_0:
Victor Stinner8c62be82010-05-06 00:08:46 +00007075 return res;
Guido van Rossuma1065681999-01-25 23:20:23 +00007076}
Andrew MacIntyre69e18c92004-04-04 07:11:43 +00007077
Guido van Rossuma1065681999-01-25 23:20:23 +00007078#endif /* HAVE_SPAWNV */
7079
7080
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007081#ifdef HAVE_FORK1
Larry Hastings2f936352014-08-05 14:04:04 +10007082/*[clinic input]
7083os.fork1
7084
7085Fork a child process with a single multiplexed (i.e., not bound) thread.
7086
7087Return 0 to child process and PID of child to parent process.
7088[clinic start generated code]*/
7089
7090PyDoc_STRVAR(os_fork1__doc__,
7091"fork1($module, /)\n"
7092"--\n"
7093"\n"
7094"Fork a child process with a single multiplexed (i.e., not bound) thread.\n"
7095"\n"
7096"Return 0 to child process and PID of child to parent process.");
7097
7098#define OS_FORK1_METHODDEF \
7099 {"fork1", (PyCFunction)os_fork1, METH_NOARGS, os_fork1__doc__},
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007100
7101static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007102os_fork1_impl(PyModuleDef *module);
7103
7104static PyObject *
7105os_fork1(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7106{
7107 return os_fork1_impl(module);
7108}
7109
7110static PyObject *
7111os_fork1_impl(PyModuleDef *module)
7112/*[clinic end generated code: output=fa04088d6bc02efa input=12db02167893926e]*/
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007113{
Victor Stinner8c62be82010-05-06 00:08:46 +00007114 pid_t pid;
7115 int result = 0;
7116 _PyImport_AcquireLock();
7117 pid = fork1();
7118 if (pid == 0) {
7119 /* child: this clobbers and resets the import lock. */
7120 PyOS_AfterFork();
7121 } else {
7122 /* parent: release the import lock. */
7123 result = _PyImport_ReleaseLock();
7124 }
7125 if (pid == -1)
7126 return posix_error();
7127 if (result < 0) {
7128 /* Don't clobber the OSError if the fork failed. */
7129 PyErr_SetString(PyExc_RuntimeError,
7130 "not holding the import lock");
7131 return NULL;
7132 }
7133 return PyLong_FromPid(pid);
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007134}
Larry Hastings2f936352014-08-05 14:04:04 +10007135#endif /* HAVE_FORK1 */
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007136
7137
Guido van Rossumad0ee831995-03-01 10:34:45 +00007138#ifdef HAVE_FORK
Larry Hastings2f936352014-08-05 14:04:04 +10007139/*[clinic input]
7140os.fork
7141
7142Fork a child process.
7143
7144Return 0 to child process and PID of child to parent process.
7145[clinic start generated code]*/
7146
7147PyDoc_STRVAR(os_fork__doc__,
7148"fork($module, /)\n"
7149"--\n"
7150"\n"
7151"Fork a child process.\n"
7152"\n"
7153"Return 0 to child process and PID of child to parent process.");
7154
7155#define OS_FORK_METHODDEF \
7156 {"fork", (PyCFunction)os_fork, METH_NOARGS, os_fork__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007157
Barry Warsaw53699e91996-12-10 23:23:01 +00007158static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007159os_fork_impl(PyModuleDef *module);
7160
7161static PyObject *
7162os_fork(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7163{
7164 return os_fork_impl(module);
7165}
7166
7167static PyObject *
7168os_fork_impl(PyModuleDef *module)
7169/*[clinic end generated code: output=b3c8e6bdc11eedc6 input=13c956413110eeaa]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00007170{
Victor Stinner8c62be82010-05-06 00:08:46 +00007171 pid_t pid;
7172 int result = 0;
7173 _PyImport_AcquireLock();
7174 pid = fork();
7175 if (pid == 0) {
7176 /* child: this clobbers and resets the import lock. */
7177 PyOS_AfterFork();
7178 } else {
7179 /* parent: release the import lock. */
7180 result = _PyImport_ReleaseLock();
7181 }
7182 if (pid == -1)
7183 return posix_error();
7184 if (result < 0) {
7185 /* Don't clobber the OSError if the fork failed. */
7186 PyErr_SetString(PyExc_RuntimeError,
7187 "not holding the import lock");
7188 return NULL;
7189 }
7190 return PyLong_FromPid(pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00007191}
Larry Hastings2f936352014-08-05 14:04:04 +10007192#endif /* HAVE_FORK */
7193
Guido van Rossum85e3b011991-06-03 12:42:10 +00007194
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007195#ifdef HAVE_SCHED_H
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007196#ifdef HAVE_SCHED_GET_PRIORITY_MAX
Larry Hastings2f936352014-08-05 14:04:04 +10007197/*[clinic input]
7198os.sched_get_priority_max
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007199
Larry Hastings2f936352014-08-05 14:04:04 +10007200 policy: int
7201
7202Get the maximum scheduling priority for policy.
7203[clinic start generated code]*/
7204
7205PyDoc_STRVAR(os_sched_get_priority_max__doc__,
7206"sched_get_priority_max($module, /, policy)\n"
7207"--\n"
7208"\n"
7209"Get the maximum scheduling priority for policy.");
7210
7211#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF \
7212 {"sched_get_priority_max", (PyCFunction)os_sched_get_priority_max, METH_VARARGS|METH_KEYWORDS, os_sched_get_priority_max__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007213
7214static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007215os_sched_get_priority_max_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007216
Larry Hastings2f936352014-08-05 14:04:04 +10007217static PyObject *
7218os_sched_get_priority_max(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7219{
7220 PyObject *return_value = NULL;
7221 static char *_keywords[] = {"policy", NULL};
7222 int policy;
7223
7224 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7225 "i:sched_get_priority_max", _keywords,
7226 &policy))
7227 goto exit;
7228 return_value = os_sched_get_priority_max_impl(module, policy);
7229
7230exit:
7231 return return_value;
7232}
7233
7234static PyObject *
7235os_sched_get_priority_max_impl(PyModuleDef *module, int policy)
7236/*[clinic end generated code: output=a580a52f25238c1f input=2097b7998eca6874]*/
7237{
7238 int max;
7239
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007240 max = sched_get_priority_max(policy);
7241 if (max < 0)
7242 return posix_error();
7243 return PyLong_FromLong(max);
7244}
7245
Larry Hastings2f936352014-08-05 14:04:04 +10007246
7247/*[clinic input]
7248os.sched_get_priority_min
7249
7250 policy: int
7251
7252Get the minimum scheduling priority for policy.
7253[clinic start generated code]*/
7254
7255PyDoc_STRVAR(os_sched_get_priority_min__doc__,
7256"sched_get_priority_min($module, /, policy)\n"
7257"--\n"
7258"\n"
7259"Get the minimum scheduling priority for policy.");
7260
7261#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF \
7262 {"sched_get_priority_min", (PyCFunction)os_sched_get_priority_min, METH_VARARGS|METH_KEYWORDS, os_sched_get_priority_min__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007263
7264static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007265os_sched_get_priority_min_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007266
Larry Hastings2f936352014-08-05 14:04:04 +10007267static PyObject *
7268os_sched_get_priority_min(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7269{
7270 PyObject *return_value = NULL;
7271 static char *_keywords[] = {"policy", NULL};
7272 int policy;
7273
7274 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7275 "i:sched_get_priority_min", _keywords,
7276 &policy))
7277 goto exit;
7278 return_value = os_sched_get_priority_min_impl(module, policy);
7279
7280exit:
7281 return return_value;
7282}
7283
7284static PyObject *
7285os_sched_get_priority_min_impl(PyModuleDef *module, int policy)
7286/*[clinic end generated code: output=bad8ba10e7d0e977 input=21bc8fa0d70983bf]*/
7287{
7288 int min = sched_get_priority_min(policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007289 if (min < 0)
7290 return posix_error();
7291 return PyLong_FromLong(min);
7292}
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007293#endif /* HAVE_SCHED_GET_PRIORITY_MAX */
7294
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007295
Larry Hastings2f936352014-08-05 14:04:04 +10007296#ifdef HAVE_SCHED_SETSCHEDULER
7297/*[clinic input]
7298os.sched_getscheduler
7299 pid: pid_t
7300 /
7301
7302Get the scheduling policy for the process identifiedy by pid.
7303
7304Passing 0 for pid returns the scheduling policy for the calling process.
7305[clinic start generated code]*/
7306
7307PyDoc_STRVAR(os_sched_getscheduler__doc__,
7308"sched_getscheduler($module, pid, /)\n"
7309"--\n"
7310"\n"
7311"Get the scheduling policy for the process identifiedy by pid.\n"
7312"\n"
7313"Passing 0 for pid returns the scheduling policy for the calling process.");
7314
7315#define OS_SCHED_GETSCHEDULER_METHODDEF \
7316 {"sched_getscheduler", (PyCFunction)os_sched_getscheduler, METH_VARARGS, os_sched_getscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007317
7318static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007319os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid);
7320
7321static PyObject *
7322os_sched_getscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007323{
Larry Hastings2f936352014-08-05 14:04:04 +10007324 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007325 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007326
7327 if (!PyArg_ParseTuple(args,
7328 "" _Py_PARSE_PID ":sched_getscheduler",
7329 &pid))
7330 goto exit;
7331 return_value = os_sched_getscheduler_impl(module, pid);
7332
7333exit:
7334 return return_value;
7335}
7336
7337static PyObject *
7338os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid)
7339/*[clinic end generated code: output=e0d6244207b1d828 input=5f14cfd1f189e1a0]*/
7340{
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007341 int policy;
7342
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007343 policy = sched_getscheduler(pid);
7344 if (policy < 0)
7345 return posix_error();
7346 return PyLong_FromLong(policy);
7347}
Larry Hastings2f936352014-08-05 14:04:04 +10007348#endif /* HAVE_SCHED_SETSCHEDULER */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007349
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007350
7351#if defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM)
Larry Hastings2f936352014-08-05 14:04:04 +10007352/*[clinic input]
7353class os.sched_param "PyObject *" "&SchedParamType"
7354
7355@classmethod
7356os.sched_param.__new__
7357
7358 sched_priority: object
7359 A scheduling parameter.
7360
7361Current has only one field: sched_priority");
7362[clinic start generated code]*/
7363
7364PyDoc_STRVAR(os_sched_param__doc__,
7365"sched_param(sched_priority)\n"
7366"--\n"
7367"\n"
7368"Current has only one field: sched_priority\");\n"
7369"\n"
7370" sched_priority\n"
7371" A scheduling parameter.");
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007372
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007373static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007374os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007375
Larry Hastings2f936352014-08-05 14:04:04 +10007376static PyObject *
7377os_sched_param(PyTypeObject *type, PyObject *args, PyObject *kwargs)
7378{
7379 PyObject *return_value = NULL;
7380 static char *_keywords[] = {"sched_priority", NULL};
7381 PyObject *sched_priority;
7382
7383 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7384 "O:sched_param", _keywords,
7385 &sched_priority))
7386 goto exit;
7387 return_value = os_sched_param_impl(type, sched_priority);
7388
7389exit:
7390 return return_value;
7391}
7392
7393static PyObject *
7394os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority)
7395/*[clinic end generated code: output=d3791e345f7fe573 input=73a4c22f7071fc62]*/
7396{
7397 PyObject *res;
7398
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007399 res = PyStructSequence_New(type);
7400 if (!res)
7401 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10007402 Py_INCREF(sched_priority);
7403 PyStructSequence_SET_ITEM(res, 0, sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007404 return res;
7405}
7406
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007407
7408static PyStructSequence_Field sched_param_fields[] = {
7409 {"sched_priority", "the scheduling priority"},
7410 {0}
7411};
7412
7413static PyStructSequence_Desc sched_param_desc = {
7414 "sched_param", /* name */
Larry Hastings2f936352014-08-05 14:04:04 +10007415 os_sched_param__doc__, /* doc */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007416 sched_param_fields,
7417 1
7418};
7419
7420static int
7421convert_sched_param(PyObject *param, struct sched_param *res)
7422{
7423 long priority;
7424
7425 if (Py_TYPE(param) != &SchedParamType) {
7426 PyErr_SetString(PyExc_TypeError, "must have a sched_param object");
7427 return 0;
7428 }
7429 priority = PyLong_AsLong(PyStructSequence_GET_ITEM(param, 0));
7430 if (priority == -1 && PyErr_Occurred())
7431 return 0;
7432 if (priority > INT_MAX || priority < INT_MIN) {
7433 PyErr_SetString(PyExc_OverflowError, "sched_priority out of range");
7434 return 0;
7435 }
7436 res->sched_priority = Py_SAFE_DOWNCAST(priority, long, int);
7437 return 1;
7438}
Larry Hastings2f936352014-08-05 14:04:04 +10007439#endif /* defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM) */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007440
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007441
7442#ifdef HAVE_SCHED_SETSCHEDULER
Larry Hastings2f936352014-08-05 14:04:04 +10007443/*[clinic input]
7444os.sched_setscheduler
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007445
Larry Hastings2f936352014-08-05 14:04:04 +10007446 pid: pid_t
7447 policy: int
7448 param: sched_param
7449 /
7450
7451Set the scheduling policy for the process identified by pid.
7452
7453If pid is 0, the calling process is changed.
7454param is an instance of sched_param.
7455[clinic start generated code]*/
7456
7457PyDoc_STRVAR(os_sched_setscheduler__doc__,
7458"sched_setscheduler($module, pid, policy, param, /)\n"
7459"--\n"
7460"\n"
7461"Set the scheduling policy for the process identified by pid.\n"
7462"\n"
7463"If pid is 0, the calling process is changed.\n"
7464"param is an instance of sched_param.");
7465
7466#define OS_SCHED_SETSCHEDULER_METHODDEF \
7467 {"sched_setscheduler", (PyCFunction)os_sched_setscheduler, METH_VARARGS, os_sched_setscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007468
7469static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007470os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param);
7471
7472static PyObject *
7473os_sched_setscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007474{
Larry Hastings2f936352014-08-05 14:04:04 +10007475 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007476 pid_t pid;
7477 int policy;
7478 struct sched_param param;
7479
Larry Hastings2f936352014-08-05 14:04:04 +10007480 if (!PyArg_ParseTuple(args,
7481 "" _Py_PARSE_PID "iO&:sched_setscheduler",
7482 &pid, &policy, convert_sched_param, &param))
7483 goto exit;
7484 return_value = os_sched_setscheduler_impl(module, pid, policy, &param);
Jesus Cea9c822272011-09-10 01:40:52 +02007485
Larry Hastings2f936352014-08-05 14:04:04 +10007486exit:
7487 return return_value;
7488}
7489
7490static PyObject *
7491os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param)
7492/*[clinic end generated code: output=36abdb73f81c224f input=c581f9469a5327dd]*/
7493{
Jesus Cea9c822272011-09-10 01:40:52 +02007494 /*
Jesus Cea54b01492011-09-10 01:53:19 +02007495 ** sched_setscheduler() returns 0 in Linux, but the previous
7496 ** scheduling policy under Solaris/Illumos, and others.
7497 ** On error, -1 is returned in all Operating Systems.
Jesus Cea9c822272011-09-10 01:40:52 +02007498 */
Larry Hastings2f936352014-08-05 14:04:04 +10007499 if (sched_setscheduler(pid, policy, param) == -1)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007500 return posix_error();
7501 Py_RETURN_NONE;
7502}
Larry Hastings2f936352014-08-05 14:04:04 +10007503#endif /* HAVE_SCHED_SETSCHEDULER*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007504
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007505
7506#ifdef HAVE_SCHED_SETPARAM
Larry Hastings2f936352014-08-05 14:04:04 +10007507/*[clinic input]
7508os.sched_getparam
7509 pid: pid_t
7510 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007511
Larry Hastings2f936352014-08-05 14:04:04 +10007512Returns scheduling parameters for the process identified by pid.
7513
7514If pid is 0, returns parameters for the calling process.
7515Return value is an instance of sched_param.
7516[clinic start generated code]*/
7517
7518PyDoc_STRVAR(os_sched_getparam__doc__,
7519"sched_getparam($module, pid, /)\n"
7520"--\n"
7521"\n"
7522"Returns scheduling parameters for the process identified by pid.\n"
7523"\n"
7524"If pid is 0, returns parameters for the calling process.\n"
7525"Return value is an instance of sched_param.");
7526
7527#define OS_SCHED_GETPARAM_METHODDEF \
7528 {"sched_getparam", (PyCFunction)os_sched_getparam, METH_VARARGS, os_sched_getparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007529
7530static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007531os_sched_getparam_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007532
Larry Hastings2f936352014-08-05 14:04:04 +10007533static PyObject *
7534os_sched_getparam(PyModuleDef *module, PyObject *args)
7535{
7536 PyObject *return_value = NULL;
7537 pid_t pid;
7538
7539 if (!PyArg_ParseTuple(args,
7540 "" _Py_PARSE_PID ":sched_getparam",
7541 &pid))
7542 goto exit;
7543 return_value = os_sched_getparam_impl(module, pid);
7544
7545exit:
7546 return return_value;
7547}
7548
7549static PyObject *
7550os_sched_getparam_impl(PyModuleDef *module, pid_t pid)
7551/*[clinic end generated code: output=b33acc8db004a8c9 input=18a1ef9c2efae296]*/
7552{
7553 struct sched_param param;
7554 PyObject *result;
7555 PyObject *priority;
7556
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007557 if (sched_getparam(pid, &param))
7558 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007559 result = PyStructSequence_New(&SchedParamType);
7560 if (!result)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007561 return NULL;
7562 priority = PyLong_FromLong(param.sched_priority);
7563 if (!priority) {
Larry Hastings2f936352014-08-05 14:04:04 +10007564 Py_DECREF(result);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007565 return NULL;
7566 }
Larry Hastings2f936352014-08-05 14:04:04 +10007567 PyStructSequence_SET_ITEM(result, 0, priority);
7568 return result;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007569}
7570
Larry Hastings2f936352014-08-05 14:04:04 +10007571
7572/*[clinic input]
7573os.sched_setparam
7574 pid: pid_t
7575 param: sched_param
7576 /
7577
7578Set scheduling parameters for the process identified by pid.
7579
7580If pid is 0, sets parameters for the calling process.
7581param should be an instance of sched_param.
7582[clinic start generated code]*/
7583
7584PyDoc_STRVAR(os_sched_setparam__doc__,
7585"sched_setparam($module, pid, param, /)\n"
7586"--\n"
7587"\n"
7588"Set scheduling parameters for the process identified by pid.\n"
7589"\n"
7590"If pid is 0, sets parameters for the calling process.\n"
7591"param should be an instance of sched_param.");
7592
7593#define OS_SCHED_SETPARAM_METHODDEF \
7594 {"sched_setparam", (PyCFunction)os_sched_setparam, METH_VARARGS, os_sched_setparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007595
7596static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007597os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param);
7598
7599static PyObject *
7600os_sched_setparam(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007601{
Larry Hastings2f936352014-08-05 14:04:04 +10007602 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007603 pid_t pid;
7604 struct sched_param param;
7605
Larry Hastings2f936352014-08-05 14:04:04 +10007606 if (!PyArg_ParseTuple(args,
7607 "" _Py_PARSE_PID "O&:sched_setparam",
7608 &pid, convert_sched_param, &param))
7609 goto exit;
7610 return_value = os_sched_setparam_impl(module, pid, &param);
7611
7612exit:
7613 return return_value;
7614}
7615
7616static PyObject *
7617os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param)
7618/*[clinic end generated code: output=488bdf5bcbe0d4e8 input=6b8d6dfcecdc21bd]*/
7619{
7620 if (sched_setparam(pid, param))
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007621 return posix_error();
7622 Py_RETURN_NONE;
7623}
Larry Hastings2f936352014-08-05 14:04:04 +10007624#endif /* HAVE_SCHED_SETPARAM */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007625
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007626
7627#ifdef HAVE_SCHED_RR_GET_INTERVAL
Larry Hastings2f936352014-08-05 14:04:04 +10007628/*[clinic input]
7629os.sched_rr_get_interval -> double
7630 pid: pid_t
7631 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007632
Larry Hastings2f936352014-08-05 14:04:04 +10007633Return the round-robin quantum for the process identified by pid, in seconds.
7634
7635Value returned is a float.
7636[clinic start generated code]*/
7637
7638PyDoc_STRVAR(os_sched_rr_get_interval__doc__,
7639"sched_rr_get_interval($module, pid, /)\n"
7640"--\n"
7641"\n"
7642"Return the round-robin quantum for the process identified by pid, in seconds.\n"
7643"\n"
7644"Value returned is a float.");
7645
7646#define OS_SCHED_RR_GET_INTERVAL_METHODDEF \
7647 {"sched_rr_get_interval", (PyCFunction)os_sched_rr_get_interval, METH_VARARGS, os_sched_rr_get_interval__doc__},
7648
7649static double
7650os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007651
7652static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007653os_sched_rr_get_interval(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007654{
Larry Hastings2f936352014-08-05 14:04:04 +10007655 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007656 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007657 double _return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007658
Larry Hastings2f936352014-08-05 14:04:04 +10007659 if (!PyArg_ParseTuple(args,
7660 "" _Py_PARSE_PID ":sched_rr_get_interval",
7661 &pid))
7662 goto exit;
7663 _return_value = os_sched_rr_get_interval_impl(module, pid);
7664 if ((_return_value == -1.0) && PyErr_Occurred())
7665 goto exit;
7666 return_value = PyFloat_FromDouble(_return_value);
7667
7668exit:
7669 return return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007670}
7671
Larry Hastings2f936352014-08-05 14:04:04 +10007672static double
7673os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid)
7674/*[clinic end generated code: output=5b3b8d1f27fb2c0a input=2a973da15cca6fae]*/
7675{
7676 struct timespec interval;
7677 if (sched_rr_get_interval(pid, &interval)) {
7678 posix_error();
7679 return -1.0;
7680 }
7681 return (double)interval.tv_sec + 1e-9*interval.tv_nsec;
7682}
7683#endif /* HAVE_SCHED_RR_GET_INTERVAL */
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007684
Larry Hastings2f936352014-08-05 14:04:04 +10007685
7686/*[clinic input]
7687os.sched_yield
7688
7689Voluntarily relinquish the CPU.
7690[clinic start generated code]*/
7691
7692PyDoc_STRVAR(os_sched_yield__doc__,
7693"sched_yield($module, /)\n"
7694"--\n"
7695"\n"
7696"Voluntarily relinquish the CPU.");
7697
7698#define OS_SCHED_YIELD_METHODDEF \
7699 {"sched_yield", (PyCFunction)os_sched_yield, METH_NOARGS, os_sched_yield__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007700
7701static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007702os_sched_yield_impl(PyModuleDef *module);
7703
7704static PyObject *
7705os_sched_yield(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7706{
7707 return os_sched_yield_impl(module);
7708}
7709
7710static PyObject *
7711os_sched_yield_impl(PyModuleDef *module)
7712/*[clinic end generated code: output=9d2e5f29f1370324 input=e54d6f98189391d4]*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007713{
7714 if (sched_yield())
7715 return posix_error();
7716 Py_RETURN_NONE;
7717}
7718
Benjamin Peterson2740af82011-08-02 17:41:34 -05007719#ifdef HAVE_SCHED_SETAFFINITY
Antoine Pitrou84869872012-08-04 16:16:35 +02007720/* The minimum number of CPUs allocated in a cpu_set_t */
7721static const int NCPUS_START = sizeof(unsigned long) * CHAR_BIT;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007722
Larry Hastings2f936352014-08-05 14:04:04 +10007723/*[clinic input]
7724os.sched_setaffinity
7725 pid: pid_t
7726 mask : object
7727 /
7728
7729Set the CPU affinity of the process identified by pid to mask.
7730
7731mask should be an iterable of integers identifying CPUs.
7732[clinic start generated code]*/
7733
7734PyDoc_STRVAR(os_sched_setaffinity__doc__,
7735"sched_setaffinity($module, pid, mask, /)\n"
7736"--\n"
7737"\n"
7738"Set the CPU affinity of the process identified by pid to mask.\n"
7739"\n"
7740"mask should be an iterable of integers identifying CPUs.");
7741
7742#define OS_SCHED_SETAFFINITY_METHODDEF \
7743 {"sched_setaffinity", (PyCFunction)os_sched_setaffinity, METH_VARARGS, os_sched_setaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007744
7745static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007746os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask);
7747
7748static PyObject *
7749os_sched_setaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007750{
Larry Hastings2f936352014-08-05 14:04:04 +10007751 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007752 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007753 PyObject *mask;
7754
7755 if (!PyArg_ParseTuple(args,
7756 "" _Py_PARSE_PID "O:sched_setaffinity",
7757 &pid, &mask))
7758 goto exit;
7759 return_value = os_sched_setaffinity_impl(module, pid, mask);
7760
7761exit:
7762 return return_value;
7763}
7764
7765static PyObject *
7766os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask)
7767/*[clinic end generated code: output=5199929738130196 input=a0791a597c7085ba]*/
7768{
Antoine Pitrou84869872012-08-04 16:16:35 +02007769 int ncpus;
7770 size_t setsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007771 cpu_set_t *cpu_set = NULL;
7772 PyObject *iterator = NULL, *item;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007773
Larry Hastings2f936352014-08-05 14:04:04 +10007774 iterator = PyObject_GetIter(mask);
Antoine Pitrou84869872012-08-04 16:16:35 +02007775 if (iterator == NULL)
7776 return NULL;
7777
7778 ncpus = NCPUS_START;
7779 setsize = CPU_ALLOC_SIZE(ncpus);
Larry Hastings2f936352014-08-05 14:04:04 +10007780 cpu_set = CPU_ALLOC(ncpus);
7781 if (cpu_set == NULL) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007782 PyErr_NoMemory();
7783 goto error;
7784 }
Larry Hastings2f936352014-08-05 14:04:04 +10007785 CPU_ZERO_S(setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007786
7787 while ((item = PyIter_Next(iterator))) {
7788 long cpu;
7789 if (!PyLong_Check(item)) {
7790 PyErr_Format(PyExc_TypeError,
7791 "expected an iterator of ints, "
7792 "but iterator yielded %R",
7793 Py_TYPE(item));
7794 Py_DECREF(item);
7795 goto error;
7796 }
7797 cpu = PyLong_AsLong(item);
7798 Py_DECREF(item);
7799 if (cpu < 0) {
7800 if (!PyErr_Occurred())
7801 PyErr_SetString(PyExc_ValueError, "negative CPU number");
7802 goto error;
7803 }
7804 if (cpu > INT_MAX - 1) {
7805 PyErr_SetString(PyExc_OverflowError, "CPU number too large");
7806 goto error;
7807 }
7808 if (cpu >= ncpus) {
7809 /* Grow CPU mask to fit the CPU number */
7810 int newncpus = ncpus;
7811 cpu_set_t *newmask;
7812 size_t newsetsize;
7813 while (newncpus <= cpu) {
7814 if (newncpus > INT_MAX / 2)
7815 newncpus = cpu + 1;
7816 else
7817 newncpus = newncpus * 2;
7818 }
7819 newmask = CPU_ALLOC(newncpus);
7820 if (newmask == NULL) {
7821 PyErr_NoMemory();
7822 goto error;
7823 }
7824 newsetsize = CPU_ALLOC_SIZE(newncpus);
7825 CPU_ZERO_S(newsetsize, newmask);
Larry Hastings2f936352014-08-05 14:04:04 +10007826 memcpy(newmask, cpu_set, setsize);
7827 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007828 setsize = newsetsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007829 cpu_set = newmask;
Antoine Pitrou84869872012-08-04 16:16:35 +02007830 ncpus = newncpus;
7831 }
Larry Hastings2f936352014-08-05 14:04:04 +10007832 CPU_SET_S(cpu, setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007833 }
7834 Py_CLEAR(iterator);
7835
Larry Hastings2f936352014-08-05 14:04:04 +10007836 if (sched_setaffinity(pid, setsize, cpu_set)) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007837 posix_error();
7838 goto error;
7839 }
Larry Hastings2f936352014-08-05 14:04:04 +10007840 CPU_FREE(cpu_set);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007841 Py_RETURN_NONE;
Antoine Pitrou84869872012-08-04 16:16:35 +02007842
7843error:
Larry Hastings2f936352014-08-05 14:04:04 +10007844 if (cpu_set)
7845 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007846 Py_XDECREF(iterator);
7847 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007848}
7849
Larry Hastings2f936352014-08-05 14:04:04 +10007850
7851/*[clinic input]
7852os.sched_getaffinity
7853 pid: pid_t
7854 /
7855
7856Return the affinity of the process identified by pid.
7857
7858The affinity is returned as a set of CPU identifiers.
7859[clinic start generated code]*/
7860
7861PyDoc_STRVAR(os_sched_getaffinity__doc__,
7862"sched_getaffinity($module, pid, /)\n"
7863"--\n"
7864"\n"
7865"Return the affinity of the process identified by pid.\n"
7866"\n"
7867"The affinity is returned as a set of CPU identifiers.");
7868
7869#define OS_SCHED_GETAFFINITY_METHODDEF \
7870 {"sched_getaffinity", (PyCFunction)os_sched_getaffinity, METH_VARARGS, os_sched_getaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007871
7872static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007873os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid);
7874
7875static PyObject *
7876os_sched_getaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007877{
Larry Hastings2f936352014-08-05 14:04:04 +10007878 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007879 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007880
7881 if (!PyArg_ParseTuple(args,
7882 "" _Py_PARSE_PID ":sched_getaffinity",
7883 &pid))
7884 goto exit;
7885 return_value = os_sched_getaffinity_impl(module, pid);
7886
7887exit:
7888 return return_value;
7889}
7890
7891static PyObject *
7892os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid)
7893/*[clinic end generated code: output=7b273b0fca9830f0 input=eaf161936874b8a1]*/
7894{
Antoine Pitrou84869872012-08-04 16:16:35 +02007895 int cpu, ncpus, count;
7896 size_t setsize;
7897 cpu_set_t *mask = NULL;
7898 PyObject *res = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007899
Antoine Pitrou84869872012-08-04 16:16:35 +02007900 ncpus = NCPUS_START;
7901 while (1) {
7902 setsize = CPU_ALLOC_SIZE(ncpus);
7903 mask = CPU_ALLOC(ncpus);
7904 if (mask == NULL)
7905 return PyErr_NoMemory();
7906 if (sched_getaffinity(pid, setsize, mask) == 0)
7907 break;
7908 CPU_FREE(mask);
7909 if (errno != EINVAL)
7910 return posix_error();
7911 if (ncpus > INT_MAX / 2) {
7912 PyErr_SetString(PyExc_OverflowError, "could not allocate "
7913 "a large enough CPU set");
7914 return NULL;
7915 }
7916 ncpus = ncpus * 2;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007917 }
Antoine Pitrou84869872012-08-04 16:16:35 +02007918
7919 res = PySet_New(NULL);
7920 if (res == NULL)
7921 goto error;
7922 for (cpu = 0, count = CPU_COUNT_S(setsize, mask); count; cpu++) {
7923 if (CPU_ISSET_S(cpu, setsize, mask)) {
7924 PyObject *cpu_num = PyLong_FromLong(cpu);
7925 --count;
7926 if (cpu_num == NULL)
7927 goto error;
7928 if (PySet_Add(res, cpu_num)) {
7929 Py_DECREF(cpu_num);
7930 goto error;
7931 }
7932 Py_DECREF(cpu_num);
7933 }
7934 }
7935 CPU_FREE(mask);
7936 return res;
7937
7938error:
7939 if (mask)
7940 CPU_FREE(mask);
7941 Py_XDECREF(res);
7942 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007943}
7944
Benjamin Peterson2740af82011-08-02 17:41:34 -05007945#endif /* HAVE_SCHED_SETAFFINITY */
7946
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007947#endif /* HAVE_SCHED_H */
7948
Larry Hastings2f936352014-08-05 14:04:04 +10007949#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7950#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7951#endif /* OS_SCHED_GET_PRIORITY_MAX_METHODDEF */
7952
7953#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7954#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7955#endif /* OS_SCHED_GET_PRIORITY_MIN_METHODDEF */
7956
7957#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
7958#define OS_SCHED_GETSCHEDULER_METHODDEF
7959#endif /* OS_SCHED_GETSCHEDULER_METHODDEF */
7960
7961#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
7962#define OS_SCHED_SETSCHEDULER_METHODDEF
7963#endif /* OS_SCHED_SETSCHEDULER_METHODDEF */
7964
7965#ifndef OS_SCHED_GETPARAM_METHODDEF
7966#define OS_SCHED_GETPARAM_METHODDEF
7967#endif /* OS_SCHED_GETPARAM_METHODDEF */
7968
7969#ifndef OS_SCHED_SETPARAM_METHODDEF
7970#define OS_SCHED_SETPARAM_METHODDEF
7971#endif /* OS_SCHED_SETPARAM_METHODDEF */
7972
7973#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
7974#define OS_SCHED_RR_GET_INTERVAL_METHODDEF
7975#endif /* OS_SCHED_RR_GET_INTERVAL_METHODDEF */
7976
7977#ifndef OS_SCHED_YIELD_METHODDEF
7978#define OS_SCHED_YIELD_METHODDEF
7979#endif /* OS_SCHED_YIELD_METHODDEF */
7980
7981#ifndef OS_SCHED_SETAFFINITY_METHODDEF
7982#define OS_SCHED_SETAFFINITY_METHODDEF
7983#endif /* OS_SCHED_SETAFFINITY_METHODDEF */
7984
7985#ifndef OS_SCHED_GETAFFINITY_METHODDEF
7986#define OS_SCHED_GETAFFINITY_METHODDEF
7987#endif /* OS_SCHED_GETAFFINITY_METHODDEF */
7988
7989
Neal Norwitzb59798b2003-03-21 01:43:31 +00007990/* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
Neal Norwitz2deaddb2003-03-21 03:08:31 +00007991/* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
7992#if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
Neal Norwitzb59798b2003-03-21 01:43:31 +00007993#define DEV_PTY_FILE "/dev/ptc"
7994#define HAVE_DEV_PTMX
7995#else
7996#define DEV_PTY_FILE "/dev/ptmx"
7997#endif
7998
Martin v. Löwis24a880b2002-12-31 12:55:15 +00007999#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
Fred Drake8cef4cf2000-06-28 16:40:38 +00008000#ifdef HAVE_PTY_H
8001#include <pty.h>
8002#else
8003#ifdef HAVE_LIBUTIL_H
8004#include <libutil.h>
Ronald Oussoren755740f2010-02-07 19:56:39 +00008005#else
8006#ifdef HAVE_UTIL_H
8007#include <util.h>
8008#endif /* HAVE_UTIL_H */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008009#endif /* HAVE_LIBUTIL_H */
8010#endif /* HAVE_PTY_H */
Martin v. Löwis14e73b12003-01-01 09:51:12 +00008011#ifdef HAVE_STROPTS_H
8012#include <stropts.h>
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008013#endif
8014#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008015
Larry Hastings2f936352014-08-05 14:04:04 +10008016
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008017#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
Larry Hastings2f936352014-08-05 14:04:04 +10008018/*[clinic input]
8019os.openpty
8020
8021Open a pseudo-terminal.
8022
8023Return a tuple of (master_fd, slave_fd) containing open file descriptors
8024for both the master and slave ends.
8025[clinic start generated code]*/
8026
8027PyDoc_STRVAR(os_openpty__doc__,
8028"openpty($module, /)\n"
8029"--\n"
8030"\n"
8031"Open a pseudo-terminal.\n"
8032"\n"
8033"Return a tuple of (master_fd, slave_fd) containing open file descriptors\n"
8034"for both the master and slave ends.");
8035
8036#define OS_OPENPTY_METHODDEF \
8037 {"openpty", (PyCFunction)os_openpty, METH_NOARGS, os_openpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008038
8039static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008040os_openpty_impl(PyModuleDef *module);
8041
8042static PyObject *
8043os_openpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8044{
8045 return os_openpty_impl(module);
8046}
8047
8048static PyObject *
8049os_openpty_impl(PyModuleDef *module)
8050/*[clinic end generated code: output=b12d3c1735468464 input=f3d99fd99e762907]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008051{
Victor Stinnerdaf45552013-08-28 00:53:59 +02008052 int master_fd = -1, slave_fd = -1;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008053#ifndef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008054 char * slave_name;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008055#endif
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008056#if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008057 PyOS_sighandler_t sig_saved;
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008058#ifdef sun
Victor Stinner8c62be82010-05-06 00:08:46 +00008059 extern char *ptsname(int fildes);
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008060#endif
8061#endif
Thomas Wouters70c21a12000-07-14 14:28:33 +00008062
Thomas Wouters70c21a12000-07-14 14:28:33 +00008063#ifdef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008064 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008065 goto posix_error;
8066
8067 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8068 goto error;
8069 if (_Py_set_inheritable(slave_fd, 0, NULL) < 0)
8070 goto error;
8071
Neal Norwitzb59798b2003-03-21 01:43:31 +00008072#elif defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008073 slave_name = _getpty(&master_fd, O_RDWR, 0666, 0);
8074 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008075 goto posix_error;
8076 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8077 goto error;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008078
Victor Stinnerdaf45552013-08-28 00:53:59 +02008079 slave_fd = _Py_open(slave_name, O_RDWR);
Victor Stinner8c62be82010-05-06 00:08:46 +00008080 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008081 goto posix_error;
8082
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008083#else
Victor Stinner000de532013-11-25 23:19:58 +01008084 master_fd = open(DEV_PTY_FILE, O_RDWR | O_NOCTTY); /* open master */
Victor Stinner8c62be82010-05-06 00:08:46 +00008085 if (master_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008086 goto posix_error;
8087
Victor Stinner8c62be82010-05-06 00:08:46 +00008088 sig_saved = PyOS_setsig(SIGCHLD, SIG_DFL);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008089
Victor Stinner8c62be82010-05-06 00:08:46 +00008090 /* change permission of slave */
8091 if (grantpt(master_fd) < 0) {
8092 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008093 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008094 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008095
Victor Stinner8c62be82010-05-06 00:08:46 +00008096 /* unlock slave */
8097 if (unlockpt(master_fd) < 0) {
8098 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008099 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008100 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008101
Victor Stinner8c62be82010-05-06 00:08:46 +00008102 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008103
Victor Stinner8c62be82010-05-06 00:08:46 +00008104 slave_name = ptsname(master_fd); /* get name of slave */
8105 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008106 goto posix_error;
8107
8108 slave_fd = _Py_open(slave_name, O_RDWR | O_NOCTTY); /* open slave */
Victor Stinner8c62be82010-05-06 00:08:46 +00008109 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008110 goto posix_error;
Victor Stinner000de532013-11-25 23:19:58 +01008111
8112 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8113 goto posix_error;
8114
Neal Norwitzb59798b2003-03-21 01:43:31 +00008115#if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
Victor Stinner8c62be82010-05-06 00:08:46 +00008116 ioctl(slave_fd, I_PUSH, "ptem"); /* push ptem */
8117 ioctl(slave_fd, I_PUSH, "ldterm"); /* push ldterm */
Neal Norwitz6700e472002-12-31 16:16:07 +00008118#ifndef __hpux
Victor Stinner8c62be82010-05-06 00:08:46 +00008119 ioctl(slave_fd, I_PUSH, "ttcompat"); /* push ttcompat */
Neal Norwitz6700e472002-12-31 16:16:07 +00008120#endif /* __hpux */
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008121#endif /* HAVE_CYGWIN */
Thomas Wouters1e0c2f42000-07-24 16:06:23 +00008122#endif /* HAVE_OPENPTY */
Thomas Wouters70c21a12000-07-14 14:28:33 +00008123
Victor Stinner8c62be82010-05-06 00:08:46 +00008124 return Py_BuildValue("(ii)", master_fd, slave_fd);
Thomas Wouters70c21a12000-07-14 14:28:33 +00008125
Victor Stinnerdaf45552013-08-28 00:53:59 +02008126posix_error:
8127 posix_error();
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008128#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008129error:
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008130#endif
Victor Stinnerdaf45552013-08-28 00:53:59 +02008131 if (master_fd != -1)
8132 close(master_fd);
8133 if (slave_fd != -1)
8134 close(slave_fd);
8135 return NULL;
Fred Drake8cef4cf2000-06-28 16:40:38 +00008136}
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008137#endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008138
Larry Hastings2f936352014-08-05 14:04:04 +10008139
Fred Drake8cef4cf2000-06-28 16:40:38 +00008140#ifdef HAVE_FORKPTY
Larry Hastings2f936352014-08-05 14:04:04 +10008141/*[clinic input]
8142os.forkpty
8143
8144Fork a new process with a new pseudo-terminal as controlling tty.
8145
8146Returns a tuple of (pid, master_fd).
8147Like fork(), return pid of 0 to the child process,
8148and pid of child to the parent process.
8149To both, return fd of newly opened pseudo-terminal.
8150[clinic start generated code]*/
8151
8152PyDoc_STRVAR(os_forkpty__doc__,
8153"forkpty($module, /)\n"
8154"--\n"
8155"\n"
8156"Fork a new process with a new pseudo-terminal as controlling tty.\n"
8157"\n"
8158"Returns a tuple of (pid, master_fd).\n"
8159"Like fork(), return pid of 0 to the child process,\n"
8160"and pid of child to the parent process.\n"
8161"To both, return fd of newly opened pseudo-terminal.");
8162
8163#define OS_FORKPTY_METHODDEF \
8164 {"forkpty", (PyCFunction)os_forkpty, METH_NOARGS, os_forkpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008165
8166static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008167os_forkpty_impl(PyModuleDef *module);
8168
8169static PyObject *
8170os_forkpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8171{
8172 return os_forkpty_impl(module);
8173}
8174
8175static PyObject *
8176os_forkpty_impl(PyModuleDef *module)
8177/*[clinic end generated code: output=d4f82958d2ed5cad input=f1f7f4bae3966010]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008178{
Victor Stinner8c62be82010-05-06 00:08:46 +00008179 int master_fd = -1, result = 0;
8180 pid_t pid;
Tim Peters5aa91602002-01-30 05:46:57 +00008181
Victor Stinner8c62be82010-05-06 00:08:46 +00008182 _PyImport_AcquireLock();
8183 pid = forkpty(&master_fd, NULL, NULL, NULL);
8184 if (pid == 0) {
8185 /* child: this clobbers and resets the import lock. */
8186 PyOS_AfterFork();
8187 } else {
8188 /* parent: release the import lock. */
8189 result = _PyImport_ReleaseLock();
8190 }
8191 if (pid == -1)
8192 return posix_error();
8193 if (result < 0) {
8194 /* Don't clobber the OSError if the fork failed. */
8195 PyErr_SetString(PyExc_RuntimeError,
8196 "not holding the import lock");
8197 return NULL;
8198 }
8199 return Py_BuildValue("(Ni)", PyLong_FromPid(pid), master_fd);
Fred Drake8cef4cf2000-06-28 16:40:38 +00008200}
Larry Hastings2f936352014-08-05 14:04:04 +10008201#endif /* HAVE_FORKPTY */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008202
Ross Lagerwall7807c352011-03-17 20:20:30 +02008203
Guido van Rossumad0ee831995-03-01 10:34:45 +00008204#ifdef HAVE_GETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10008205/*[clinic input]
8206os.getegid
8207
8208Return the current process's effective group id.
8209[clinic start generated code]*/
8210
8211PyDoc_STRVAR(os_getegid__doc__,
8212"getegid($module, /)\n"
8213"--\n"
8214"\n"
8215"Return the current process\'s effective group id.");
8216
8217#define OS_GETEGID_METHODDEF \
8218 {"getegid", (PyCFunction)os_getegid, METH_NOARGS, os_getegid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008219
Barry Warsaw53699e91996-12-10 23:23:01 +00008220static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008221os_getegid_impl(PyModuleDef *module);
8222
8223static PyObject *
8224os_getegid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8225{
8226 return os_getegid_impl(module);
8227}
8228
8229static PyObject *
8230os_getegid_impl(PyModuleDef *module)
8231/*[clinic end generated code: output=fd12c346fa41cccb input=1596f79ad1107d5d]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008232{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008233 return _PyLong_FromGid(getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008234}
Larry Hastings2f936352014-08-05 14:04:04 +10008235#endif /* HAVE_GETEGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008236
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008237
Guido van Rossumad0ee831995-03-01 10:34:45 +00008238#ifdef HAVE_GETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10008239/*[clinic input]
8240os.geteuid
8241
8242Return the current process's effective user id.
8243[clinic start generated code]*/
8244
8245PyDoc_STRVAR(os_geteuid__doc__,
8246"geteuid($module, /)\n"
8247"--\n"
8248"\n"
8249"Return the current process\'s effective user id.");
8250
8251#define OS_GETEUID_METHODDEF \
8252 {"geteuid", (PyCFunction)os_geteuid, METH_NOARGS, os_geteuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008253
Barry Warsaw53699e91996-12-10 23:23:01 +00008254static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008255os_geteuid_impl(PyModuleDef *module);
8256
8257static PyObject *
8258os_geteuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8259{
8260 return os_geteuid_impl(module);
8261}
8262
8263static PyObject *
8264os_geteuid_impl(PyModuleDef *module)
8265/*[clinic end generated code: output=03d98e07f4bc03d4 input=4644c662d3bd9f19]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008266{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008267 return _PyLong_FromUid(geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008268}
Larry Hastings2f936352014-08-05 14:04:04 +10008269#endif /* HAVE_GETEUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008270
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008271
Guido van Rossumad0ee831995-03-01 10:34:45 +00008272#ifdef HAVE_GETGID
Larry Hastings2f936352014-08-05 14:04:04 +10008273/*[clinic input]
8274os.getgid
8275
8276Return the current process's group id.
8277[clinic start generated code]*/
8278
8279PyDoc_STRVAR(os_getgid__doc__,
8280"getgid($module, /)\n"
8281"--\n"
8282"\n"
8283"Return the current process\'s group id.");
8284
8285#define OS_GETGID_METHODDEF \
8286 {"getgid", (PyCFunction)os_getgid, METH_NOARGS, os_getgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008287
Barry Warsaw53699e91996-12-10 23:23:01 +00008288static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008289os_getgid_impl(PyModuleDef *module);
8290
8291static PyObject *
8292os_getgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8293{
8294 return os_getgid_impl(module);
8295}
8296
8297static PyObject *
8298os_getgid_impl(PyModuleDef *module)
8299/*[clinic end generated code: output=07b0356121b8098d input=58796344cd87c0f6]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008300{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008301 return _PyLong_FromGid(getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008302}
Larry Hastings2f936352014-08-05 14:04:04 +10008303#endif /* HAVE_GETGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008304
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008305
Larry Hastings2f936352014-08-05 14:04:04 +10008306/*[clinic input]
8307os.getpid
8308
8309Return the current process id.
8310[clinic start generated code]*/
8311
8312PyDoc_STRVAR(os_getpid__doc__,
8313"getpid($module, /)\n"
8314"--\n"
8315"\n"
8316"Return the current process id.");
8317
8318#define OS_GETPID_METHODDEF \
8319 {"getpid", (PyCFunction)os_getpid, METH_NOARGS, os_getpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008320
Barry Warsaw53699e91996-12-10 23:23:01 +00008321static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008322os_getpid_impl(PyModuleDef *module);
8323
8324static PyObject *
8325os_getpid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8326{
8327 return os_getpid_impl(module);
8328}
8329
8330static PyObject *
8331os_getpid_impl(PyModuleDef *module)
8332/*[clinic end generated code: output=d63a01a3cebc573d input=5a9a00f0ab68aa00]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008333{
Victor Stinner8c62be82010-05-06 00:08:46 +00008334 return PyLong_FromPid(getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00008335}
8336
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008337#ifdef HAVE_GETGROUPLIST
Larry Hastings2f936352014-08-05 14:04:04 +10008338
8339/* AC 3.5: funny apple logic below */
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008340PyDoc_STRVAR(posix_getgrouplist__doc__,
8341"getgrouplist(user, group) -> list of groups to which a user belongs\n\n\
8342Returns a list of groups to which a user belongs.\n\n\
8343 user: username to lookup\n\
8344 group: base group id of the user");
8345
8346static PyObject *
8347posix_getgrouplist(PyObject *self, PyObject *args)
8348{
8349#ifdef NGROUPS_MAX
8350#define MAX_GROUPS NGROUPS_MAX
8351#else
8352 /* defined to be 16 on Solaris7, so this should be a small number */
8353#define MAX_GROUPS 64
8354#endif
8355
8356 const char *user;
8357 int i, ngroups;
8358 PyObject *list;
8359#ifdef __APPLE__
8360 int *groups, basegid;
8361#else
8362 gid_t *groups, basegid;
8363#endif
8364 ngroups = MAX_GROUPS;
8365
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008366#ifdef __APPLE__
8367 if (!PyArg_ParseTuple(args, "si:getgrouplist", &user, &basegid))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008368 return NULL;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008369#else
8370 if (!PyArg_ParseTuple(args, "sO&:getgrouplist", &user,
8371 _Py_Gid_Converter, &basegid))
8372 return NULL;
8373#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008374
8375#ifdef __APPLE__
8376 groups = PyMem_Malloc(ngroups * sizeof(int));
8377#else
8378 groups = PyMem_Malloc(ngroups * sizeof(gid_t));
8379#endif
8380 if (groups == NULL)
8381 return PyErr_NoMemory();
8382
8383 if (getgrouplist(user, basegid, groups, &ngroups) == -1) {
8384 PyMem_Del(groups);
8385 return posix_error();
8386 }
8387
8388 list = PyList_New(ngroups);
8389 if (list == NULL) {
8390 PyMem_Del(groups);
8391 return NULL;
8392 }
8393
8394 for (i = 0; i < ngroups; i++) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008395#ifdef __APPLE__
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008396 PyObject *o = PyLong_FromUnsignedLong((unsigned long)groups[i]);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008397#else
8398 PyObject *o = _PyLong_FromGid(groups[i]);
8399#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008400 if (o == NULL) {
8401 Py_DECREF(list);
8402 PyMem_Del(groups);
8403 return NULL;
8404 }
8405 PyList_SET_ITEM(list, i, o);
8406 }
8407
8408 PyMem_Del(groups);
8409
8410 return list;
8411}
Larry Hastings2f936352014-08-05 14:04:04 +10008412#endif /* HAVE_GETGROUPLIST */
8413
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008414
Fred Drakec9680921999-12-13 16:37:25 +00008415#ifdef HAVE_GETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10008416/*[clinic input]
8417os.getgroups
8418
8419Return list of supplemental group IDs for the process.
8420[clinic start generated code]*/
8421
8422PyDoc_STRVAR(os_getgroups__doc__,
8423"getgroups($module, /)\n"
8424"--\n"
8425"\n"
8426"Return list of supplemental group IDs for the process.");
8427
8428#define OS_GETGROUPS_METHODDEF \
8429 {"getgroups", (PyCFunction)os_getgroups, METH_NOARGS, os_getgroups__doc__},
Fred Drakec9680921999-12-13 16:37:25 +00008430
8431static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008432os_getgroups_impl(PyModuleDef *module);
8433
8434static PyObject *
8435os_getgroups(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8436{
8437 return os_getgroups_impl(module);
8438}
8439
8440static PyObject *
8441os_getgroups_impl(PyModuleDef *module)
8442/*[clinic end generated code: output=d9a3559b2e6f4ab8 input=d3f109412e6a155c]*/
Fred Drakec9680921999-12-13 16:37:25 +00008443{
8444 PyObject *result = NULL;
8445
Fred Drakec9680921999-12-13 16:37:25 +00008446#ifdef NGROUPS_MAX
8447#define MAX_GROUPS NGROUPS_MAX
8448#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008449 /* defined to be 16 on Solaris7, so this should be a small number */
Fred Drakec9680921999-12-13 16:37:25 +00008450#define MAX_GROUPS 64
8451#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008452 gid_t grouplist[MAX_GROUPS];
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008453
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008454 /* On MacOSX getgroups(2) can return more than MAX_GROUPS results
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008455 * This is a helper variable to store the intermediate result when
8456 * that happens.
8457 *
8458 * To keep the code readable the OSX behaviour is unconditional,
8459 * according to the POSIX spec this should be safe on all unix-y
8460 * systems.
8461 */
8462 gid_t* alt_grouplist = grouplist;
Victor Stinner8c62be82010-05-06 00:08:46 +00008463 int n;
Fred Drakec9680921999-12-13 16:37:25 +00008464
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008465#ifdef __APPLE__
8466 /* Issue #17557: As of OS X 10.8, getgroups(2) no longer raises EINVAL if
8467 * there are more groups than can fit in grouplist. Therefore, on OS X
8468 * always first call getgroups with length 0 to get the actual number
8469 * of groups.
8470 */
8471 n = getgroups(0, NULL);
8472 if (n < 0) {
8473 return posix_error();
8474 } else if (n <= MAX_GROUPS) {
8475 /* groups will fit in existing array */
8476 alt_grouplist = grouplist;
8477 } else {
8478 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8479 if (alt_grouplist == NULL) {
8480 errno = EINVAL;
8481 return posix_error();
8482 }
8483 }
8484
8485 n = getgroups(n, alt_grouplist);
8486 if (n == -1) {
8487 if (alt_grouplist != grouplist) {
8488 PyMem_Free(alt_grouplist);
8489 }
8490 return posix_error();
8491 }
8492#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008493 n = getgroups(MAX_GROUPS, grouplist);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008494 if (n < 0) {
8495 if (errno == EINVAL) {
8496 n = getgroups(0, NULL);
8497 if (n == -1) {
8498 return posix_error();
8499 }
8500 if (n == 0) {
8501 /* Avoid malloc(0) */
8502 alt_grouplist = grouplist;
8503 } else {
8504 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8505 if (alt_grouplist == NULL) {
8506 errno = EINVAL;
8507 return posix_error();
8508 }
8509 n = getgroups(n, alt_grouplist);
8510 if (n == -1) {
8511 PyMem_Free(alt_grouplist);
8512 return posix_error();
8513 }
8514 }
8515 } else {
8516 return posix_error();
8517 }
8518 }
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008519#endif
8520
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008521 result = PyList_New(n);
8522 if (result != NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008523 int i;
8524 for (i = 0; i < n; ++i) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008525 PyObject *o = _PyLong_FromGid(alt_grouplist[i]);
Victor Stinner8c62be82010-05-06 00:08:46 +00008526 if (o == NULL) {
Stefan Krah0e803b32010-11-26 16:16:47 +00008527 Py_DECREF(result);
8528 result = NULL;
8529 break;
Fred Drakec9680921999-12-13 16:37:25 +00008530 }
Victor Stinner8c62be82010-05-06 00:08:46 +00008531 PyList_SET_ITEM(result, i, o);
Fred Drakec9680921999-12-13 16:37:25 +00008532 }
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008533 }
8534
8535 if (alt_grouplist != grouplist) {
8536 PyMem_Free(alt_grouplist);
Victor Stinner8c62be82010-05-06 00:08:46 +00008537 }
Neal Norwitze241ce82003-02-17 18:17:05 +00008538
Fred Drakec9680921999-12-13 16:37:25 +00008539 return result;
8540}
Larry Hastings2f936352014-08-05 14:04:04 +10008541#endif /* HAVE_GETGROUPS */
Fred Drakec9680921999-12-13 16:37:25 +00008542
Antoine Pitroub7572f02009-12-02 20:46:48 +00008543#ifdef HAVE_INITGROUPS
8544PyDoc_STRVAR(posix_initgroups__doc__,
8545"initgroups(username, gid) -> None\n\n\
8546Call the system initgroups() to initialize the group access list with all of\n\
8547the groups of which the specified username is a member, plus the specified\n\
8548group id.");
8549
Larry Hastings2f936352014-08-05 14:04:04 +10008550/* AC 3.5: funny apple logic */
Antoine Pitroub7572f02009-12-02 20:46:48 +00008551static PyObject *
8552posix_initgroups(PyObject *self, PyObject *args)
8553{
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008554 PyObject *oname;
Victor Stinner8c62be82010-05-06 00:08:46 +00008555 char *username;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008556 int res;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008557#ifdef __APPLE__
8558 int gid;
8559#else
8560 gid_t gid;
8561#endif
Antoine Pitroub7572f02009-12-02 20:46:48 +00008562
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008563#ifdef __APPLE__
8564 if (!PyArg_ParseTuple(args, "O&i:initgroups",
8565 PyUnicode_FSConverter, &oname,
8566 &gid))
8567#else
8568 if (!PyArg_ParseTuple(args, "O&O&:initgroups",
8569 PyUnicode_FSConverter, &oname,
8570 _Py_Gid_Converter, &gid))
8571#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008572 return NULL;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008573 username = PyBytes_AS_STRING(oname);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008574
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008575 res = initgroups(username, gid);
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008576 Py_DECREF(oname);
8577 if (res == -1)
Victor Stinner8c62be82010-05-06 00:08:46 +00008578 return PyErr_SetFromErrno(PyExc_OSError);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008579
Victor Stinner8c62be82010-05-06 00:08:46 +00008580 Py_INCREF(Py_None);
8581 return Py_None;
Antoine Pitroub7572f02009-12-02 20:46:48 +00008582}
Larry Hastings2f936352014-08-05 14:04:04 +10008583#endif /* HAVE_INITGROUPS */
8584
Antoine Pitroub7572f02009-12-02 20:46:48 +00008585
Martin v. Löwis606edc12002-06-13 21:09:11 +00008586#ifdef HAVE_GETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10008587/*[clinic input]
8588os.getpgid
8589
8590 pid: pid_t
8591
8592Call the system call getpgid(), and return the result.
8593[clinic start generated code]*/
8594
8595PyDoc_STRVAR(os_getpgid__doc__,
8596"getpgid($module, /, pid)\n"
8597"--\n"
8598"\n"
8599"Call the system call getpgid(), and return the result.");
8600
8601#define OS_GETPGID_METHODDEF \
8602 {"getpgid", (PyCFunction)os_getpgid, METH_VARARGS|METH_KEYWORDS, os_getpgid__doc__},
Martin v. Löwis606edc12002-06-13 21:09:11 +00008603
8604static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008605os_getpgid_impl(PyModuleDef *module, pid_t pid);
8606
8607static PyObject *
8608os_getpgid(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis606edc12002-06-13 21:09:11 +00008609{
Larry Hastings2f936352014-08-05 14:04:04 +10008610 PyObject *return_value = NULL;
8611 static char *_keywords[] = {"pid", NULL};
8612 pid_t pid;
8613
8614 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
8615 "" _Py_PARSE_PID ":getpgid", _keywords,
8616 &pid))
8617 goto exit;
8618 return_value = os_getpgid_impl(module, pid);
8619
8620exit:
8621 return return_value;
8622}
8623
8624static PyObject *
8625os_getpgid_impl(PyModuleDef *module, pid_t pid)
8626/*[clinic end generated code: output=3db4ed686179160d input=39d710ae3baaf1c7]*/
8627{
8628 pid_t pgid = getpgid(pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00008629 if (pgid < 0)
8630 return posix_error();
8631 return PyLong_FromPid(pgid);
Martin v. Löwis606edc12002-06-13 21:09:11 +00008632}
8633#endif /* HAVE_GETPGID */
8634
8635
Guido van Rossumb6775db1994-08-01 11:34:53 +00008636#ifdef HAVE_GETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008637/*[clinic input]
8638os.getpgrp
8639
8640Return the current process group id.
8641[clinic start generated code]*/
8642
8643PyDoc_STRVAR(os_getpgrp__doc__,
8644"getpgrp($module, /)\n"
8645"--\n"
8646"\n"
8647"Return the current process group id.");
8648
8649#define OS_GETPGRP_METHODDEF \
8650 {"getpgrp", (PyCFunction)os_getpgrp, METH_NOARGS, os_getpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008651
Barry Warsaw53699e91996-12-10 23:23:01 +00008652static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008653os_getpgrp_impl(PyModuleDef *module);
8654
8655static PyObject *
8656os_getpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8657{
8658 return os_getpgrp_impl(module);
8659}
8660
8661static PyObject *
8662os_getpgrp_impl(PyModuleDef *module)
8663/*[clinic end generated code: output=3b0d3663ea054277 input=6846fb2bb9a3705e]*/
Guido van Rossum04814471991-06-04 20:23:49 +00008664{
Guido van Rossumb6775db1994-08-01 11:34:53 +00008665#ifdef GETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008666 return PyLong_FromPid(getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008667#else /* GETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008668 return PyLong_FromPid(getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008669#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00008670}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008671#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00008672
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008673
Guido van Rossumb6775db1994-08-01 11:34:53 +00008674#ifdef HAVE_SETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008675/*[clinic input]
8676os.setpgrp
8677
8678Make the current process the leader of its process group.
8679[clinic start generated code]*/
8680
8681PyDoc_STRVAR(os_setpgrp__doc__,
8682"setpgrp($module, /)\n"
8683"--\n"
8684"\n"
8685"Make the current process the leader of its process group.");
8686
8687#define OS_SETPGRP_METHODDEF \
8688 {"setpgrp", (PyCFunction)os_setpgrp, METH_NOARGS, os_setpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008689
Barry Warsaw53699e91996-12-10 23:23:01 +00008690static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008691os_setpgrp_impl(PyModuleDef *module);
8692
8693static PyObject *
8694os_setpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8695{
8696 return os_setpgrp_impl(module);
8697}
8698
8699static PyObject *
8700os_setpgrp_impl(PyModuleDef *module)
8701/*[clinic end generated code: output=8fbb0ee29ef6fb2d input=1f0619fcb5731e7e]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00008702{
Guido van Rossum64933891994-10-20 21:56:42 +00008703#ifdef SETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008704 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008705#else /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008706 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008707#endif /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008708 return posix_error();
8709 Py_INCREF(Py_None);
8710 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00008711}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008712#endif /* HAVE_SETPGRP */
8713
Guido van Rossumad0ee831995-03-01 10:34:45 +00008714#ifdef HAVE_GETPPID
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008715
8716#ifdef MS_WINDOWS
8717#include <tlhelp32.h>
8718
8719static PyObject*
8720win32_getppid()
8721{
8722 HANDLE snapshot;
8723 pid_t mypid;
8724 PyObject* result = NULL;
8725 BOOL have_record;
8726 PROCESSENTRY32 pe;
8727
8728 mypid = getpid(); /* This function never fails */
8729
8730 snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
8731 if (snapshot == INVALID_HANDLE_VALUE)
8732 return PyErr_SetFromWindowsErr(GetLastError());
8733
8734 pe.dwSize = sizeof(pe);
8735 have_record = Process32First(snapshot, &pe);
8736 while (have_record) {
8737 if (mypid == (pid_t)pe.th32ProcessID) {
8738 /* We could cache the ulong value in a static variable. */
8739 result = PyLong_FromPid((pid_t)pe.th32ParentProcessID);
8740 break;
8741 }
8742
8743 have_record = Process32Next(snapshot, &pe);
8744 }
8745
8746 /* If our loop exits and our pid was not found (result will be NULL)
8747 * then GetLastError will return ERROR_NO_MORE_FILES. This is an
8748 * error anyway, so let's raise it. */
8749 if (!result)
8750 result = PyErr_SetFromWindowsErr(GetLastError());
8751
8752 CloseHandle(snapshot);
8753
8754 return result;
8755}
8756#endif /*MS_WINDOWS*/
8757
Larry Hastings2f936352014-08-05 14:04:04 +10008758
8759/*[clinic input]
8760os.getppid
8761
8762Return the parent's process id.
8763
8764If the parent process has already exited, Windows machines will still
8765return its id; others systems will return the id of the 'init' process (1).
8766[clinic start generated code]*/
8767
8768PyDoc_STRVAR(os_getppid__doc__,
8769"getppid($module, /)\n"
8770"--\n"
8771"\n"
8772"Return the parent\'s process id.\n"
8773"\n"
8774"If the parent process has already exited, Windows machines will still\n"
8775"return its id; others systems will return the id of the \'init\' process (1).");
8776
8777#define OS_GETPPID_METHODDEF \
8778 {"getppid", (PyCFunction)os_getppid, METH_NOARGS, os_getppid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008779
Barry Warsaw53699e91996-12-10 23:23:01 +00008780static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008781os_getppid_impl(PyModuleDef *module);
8782
8783static PyObject *
8784os_getppid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8785{
8786 return os_getppid_impl(module);
8787}
8788
8789static PyObject *
8790os_getppid_impl(PyModuleDef *module)
8791/*[clinic end generated code: output=9ff3b387781edf3a input=e637cb87539c030e]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008792{
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008793#ifdef MS_WINDOWS
8794 return win32_getppid();
8795#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008796 return PyLong_FromPid(getppid());
Guido van Rossumad0ee831995-03-01 10:34:45 +00008797#endif
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008798}
8799#endif /* HAVE_GETPPID */
Guido van Rossum85e3b011991-06-03 12:42:10 +00008800
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008801
Fred Drake12c6e2d1999-12-14 21:25:03 +00008802#ifdef HAVE_GETLOGIN
Larry Hastings2f936352014-08-05 14:04:04 +10008803/*[clinic input]
8804os.getlogin
8805
8806Return the actual login name.
8807[clinic start generated code]*/
8808
8809PyDoc_STRVAR(os_getlogin__doc__,
8810"getlogin($module, /)\n"
8811"--\n"
8812"\n"
8813"Return the actual login name.");
8814
8815#define OS_GETLOGIN_METHODDEF \
8816 {"getlogin", (PyCFunction)os_getlogin, METH_NOARGS, os_getlogin__doc__},
Fred Drake12c6e2d1999-12-14 21:25:03 +00008817
8818static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008819os_getlogin_impl(PyModuleDef *module);
8820
8821static PyObject *
8822os_getlogin(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8823{
8824 return os_getlogin_impl(module);
8825}
8826
8827static PyObject *
8828os_getlogin_impl(PyModuleDef *module)
8829/*[clinic end generated code: output=ab6211dab104cbb2 input=2a21ab1e917163df]*/
Fred Drake12c6e2d1999-12-14 21:25:03 +00008830{
Victor Stinner8c62be82010-05-06 00:08:46 +00008831 PyObject *result = NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008832#ifdef MS_WINDOWS
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008833 wchar_t user_name[UNLEN + 1];
Victor Stinner63941882011-09-29 00:42:28 +02008834 DWORD num_chars = Py_ARRAY_LENGTH(user_name);
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008835
8836 if (GetUserNameW(user_name, &num_chars)) {
8837 /* num_chars is the number of unicode chars plus null terminator */
8838 result = PyUnicode_FromWideChar(user_name, num_chars - 1);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008839 }
8840 else
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008841 result = PyErr_SetFromWindowsErr(GetLastError());
8842#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008843 char *name;
8844 int old_errno = errno;
Fred Drake12c6e2d1999-12-14 21:25:03 +00008845
Victor Stinner8c62be82010-05-06 00:08:46 +00008846 errno = 0;
8847 name = getlogin();
8848 if (name == NULL) {
8849 if (errno)
Victor Stinnere039ffe2010-08-15 09:33:08 +00008850 posix_error();
Fred Drake12c6e2d1999-12-14 21:25:03 +00008851 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008852 PyErr_SetString(PyExc_OSError, "unable to determine login name");
Victor Stinner8c62be82010-05-06 00:08:46 +00008853 }
8854 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008855 result = PyUnicode_DecodeFSDefault(name);
Victor Stinner8c62be82010-05-06 00:08:46 +00008856 errno = old_errno;
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008857#endif
Fred Drake12c6e2d1999-12-14 21:25:03 +00008858 return result;
8859}
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008860#endif /* HAVE_GETLOGIN */
Fred Drake12c6e2d1999-12-14 21:25:03 +00008861
Larry Hastings2f936352014-08-05 14:04:04 +10008862
Guido van Rossumad0ee831995-03-01 10:34:45 +00008863#ifdef HAVE_GETUID
Larry Hastings2f936352014-08-05 14:04:04 +10008864/*[clinic input]
8865os.getuid
8866
8867Return the current process's user id.
8868[clinic start generated code]*/
8869
8870PyDoc_STRVAR(os_getuid__doc__,
8871"getuid($module, /)\n"
8872"--\n"
8873"\n"
8874"Return the current process\'s user id.");
8875
8876#define OS_GETUID_METHODDEF \
8877 {"getuid", (PyCFunction)os_getuid, METH_NOARGS, os_getuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008878
Barry Warsaw53699e91996-12-10 23:23:01 +00008879static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008880os_getuid_impl(PyModuleDef *module);
8881
8882static PyObject *
8883os_getuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8884{
8885 return os_getuid_impl(module);
8886}
8887
8888static PyObject *
8889os_getuid_impl(PyModuleDef *module)
8890/*[clinic end generated code: output=77e0dcf2e37d1e89 input=b53c8b35f110a516]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008891{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008892 return _PyLong_FromUid(getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008893}
Larry Hastings2f936352014-08-05 14:04:04 +10008894#endif /* HAVE_GETUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008895
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008896
Brian Curtineb24d742010-04-12 17:16:38 +00008897#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008898#define HAVE_KILL
8899#endif /* MS_WINDOWS */
8900
8901#ifdef HAVE_KILL
8902/*[clinic input]
8903os.kill
8904
8905 pid: pid_t
8906 signal: Py_ssize_t
8907 /
8908
8909Kill a process with a signal.
8910[clinic start generated code]*/
8911
8912PyDoc_STRVAR(os_kill__doc__,
8913"kill($module, pid, signal, /)\n"
8914"--\n"
8915"\n"
8916"Kill a process with a signal.");
8917
8918#define OS_KILL_METHODDEF \
8919 {"kill", (PyCFunction)os_kill, METH_VARARGS, os_kill__doc__},
Brian Curtineb24d742010-04-12 17:16:38 +00008920
8921static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008922os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal);
8923
8924static PyObject *
8925os_kill(PyModuleDef *module, PyObject *args)
8926{
8927 PyObject *return_value = NULL;
8928 pid_t pid;
8929 Py_ssize_t signal;
8930
8931 if (!PyArg_ParseTuple(args,
8932 "" _Py_PARSE_PID "n:kill",
8933 &pid, &signal))
8934 goto exit;
8935 return_value = os_kill_impl(module, pid, signal);
8936
8937exit:
8938 return return_value;
8939}
8940
8941static PyObject *
8942os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal)
8943/*[clinic end generated code: output=2f5c77920ed575e6 input=61a36b86ca275ab9]*/
8944#ifndef MS_WINDOWS
8945{
8946 if (kill(pid, (int)signal) == -1)
8947 return posix_error();
8948 Py_RETURN_NONE;
8949}
8950#else /* !MS_WINDOWS */
Brian Curtineb24d742010-04-12 17:16:38 +00008951{
Amaury Forgeot d'Arc0a589c92010-05-15 20:35:12 +00008952 PyObject *result;
Larry Hastings2f936352014-08-05 14:04:04 +10008953 DWORD sig = (DWORD)signal;
8954 DWORD err;
Victor Stinner8c62be82010-05-06 00:08:46 +00008955 HANDLE handle;
Brian Curtineb24d742010-04-12 17:16:38 +00008956
Victor Stinner8c62be82010-05-06 00:08:46 +00008957 /* Console processes which share a common console can be sent CTRL+C or
8958 CTRL+BREAK events, provided they handle said events. */
8959 if (sig == CTRL_C_EVENT || sig == CTRL_BREAK_EVENT) {
Richard Oudkerkac0ad882013-06-05 23:29:30 +01008960 if (GenerateConsoleCtrlEvent(sig, (DWORD)pid) == 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008961 err = GetLastError();
8962 PyErr_SetFromWindowsErr(err);
8963 }
8964 else
8965 Py_RETURN_NONE;
8966 }
Brian Curtineb24d742010-04-12 17:16:38 +00008967
Victor Stinner8c62be82010-05-06 00:08:46 +00008968 /* If the signal is outside of what GenerateConsoleCtrlEvent can use,
8969 attempt to open and terminate the process. */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01008970 handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, (DWORD)pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00008971 if (handle == NULL) {
8972 err = GetLastError();
8973 return PyErr_SetFromWindowsErr(err);
8974 }
Brian Curtineb24d742010-04-12 17:16:38 +00008975
Victor Stinner8c62be82010-05-06 00:08:46 +00008976 if (TerminateProcess(handle, sig) == 0) {
8977 err = GetLastError();
8978 result = PyErr_SetFromWindowsErr(err);
8979 } else {
8980 Py_INCREF(Py_None);
8981 result = Py_None;
8982 }
Brian Curtineb24d742010-04-12 17:16:38 +00008983
Victor Stinner8c62be82010-05-06 00:08:46 +00008984 CloseHandle(handle);
8985 return result;
Brian Curtineb24d742010-04-12 17:16:38 +00008986}
Larry Hastings2f936352014-08-05 14:04:04 +10008987#endif /* !MS_WINDOWS */
8988#endif /* HAVE_KILL */
8989
8990
8991#ifdef HAVE_KILLPG
8992/*[clinic input]
8993os.killpg
8994
8995 pgid: pid_t
8996 signal: int
8997 /
8998
8999Kill a process group with a signal.
9000[clinic start generated code]*/
9001
9002PyDoc_STRVAR(os_killpg__doc__,
9003"killpg($module, pgid, signal, /)\n"
9004"--\n"
9005"\n"
9006"Kill a process group with a signal.");
9007
9008#define OS_KILLPG_METHODDEF \
9009 {"killpg", (PyCFunction)os_killpg, METH_VARARGS, os_killpg__doc__},
9010
9011static PyObject *
9012os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal);
9013
9014static PyObject *
9015os_killpg(PyModuleDef *module, PyObject *args)
9016{
9017 PyObject *return_value = NULL;
9018 pid_t pgid;
9019 int signal;
9020
9021 if (!PyArg_ParseTuple(args,
9022 "" _Py_PARSE_PID "i:killpg",
9023 &pgid, &signal))
9024 goto exit;
9025 return_value = os_killpg_impl(module, pgid, signal);
9026
9027exit:
9028 return return_value;
9029}
9030
9031static PyObject *
9032os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal)
9033/*[clinic end generated code: output=0e05215d1c007e01 input=38b5449eb8faec19]*/
9034{
9035 /* XXX some man pages make the `pgid` parameter an int, others
9036 a pid_t. Since getpgrp() returns a pid_t, we assume killpg should
9037 take the same type. Moreover, pid_t is always at least as wide as
9038 int (else compilation of this module fails), which is safe. */
9039 if (killpg(pgid, signal) == -1)
9040 return posix_error();
9041 Py_RETURN_NONE;
9042}
9043#endif /* HAVE_KILLPG */
9044
Brian Curtineb24d742010-04-12 17:16:38 +00009045
Guido van Rossumc0125471996-06-28 18:55:32 +00009046#ifdef HAVE_PLOCK
Guido van Rossumc0125471996-06-28 18:55:32 +00009047#ifdef HAVE_SYS_LOCK_H
9048#include <sys/lock.h>
9049#endif
9050
Larry Hastings2f936352014-08-05 14:04:04 +10009051/*[clinic input]
9052os.plock
9053 op: int
9054 /
9055
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009056Lock program segments into memory.");
Larry Hastings2f936352014-08-05 14:04:04 +10009057[clinic start generated code]*/
9058
9059PyDoc_STRVAR(os_plock__doc__,
9060"plock($module, op, /)\n"
9061"--\n"
9062"\n"
9063"Lock program segments into memory.\");");
9064
9065#define OS_PLOCK_METHODDEF \
9066 {"plock", (PyCFunction)os_plock, METH_VARARGS, os_plock__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009067
Barry Warsaw53699e91996-12-10 23:23:01 +00009068static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009069os_plock_impl(PyModuleDef *module, int op);
9070
9071static PyObject *
9072os_plock(PyModuleDef *module, PyObject *args)
Guido van Rossumc0125471996-06-28 18:55:32 +00009073{
Larry Hastings2f936352014-08-05 14:04:04 +10009074 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009075 int op;
Larry Hastings2f936352014-08-05 14:04:04 +10009076
9077 if (!PyArg_ParseTuple(args,
9078 "i:plock",
9079 &op))
9080 goto exit;
9081 return_value = os_plock_impl(module, op);
9082
9083exit:
9084 return return_value;
9085}
9086
9087static PyObject *
9088os_plock_impl(PyModuleDef *module, int op)
9089/*[clinic end generated code: output=2744fe4b6e5f4dbc input=e6e5e348e1525f60]*/
9090{
Victor Stinner8c62be82010-05-06 00:08:46 +00009091 if (plock(op) == -1)
9092 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009093 Py_RETURN_NONE;
Guido van Rossumc0125471996-06-28 18:55:32 +00009094}
Larry Hastings2f936352014-08-05 14:04:04 +10009095#endif /* HAVE_PLOCK */
9096
Guido van Rossumc0125471996-06-28 18:55:32 +00009097
Guido van Rossumb6775db1994-08-01 11:34:53 +00009098#ifdef HAVE_SETUID
Larry Hastings2f936352014-08-05 14:04:04 +10009099/*[clinic input]
9100os.setuid
9101
9102 uid: uid_t
9103 /
9104
9105Set the current process's user id.
9106[clinic start generated code]*/
9107
9108PyDoc_STRVAR(os_setuid__doc__,
9109"setuid($module, uid, /)\n"
9110"--\n"
9111"\n"
9112"Set the current process\'s user id.");
9113
9114#define OS_SETUID_METHODDEF \
9115 {"setuid", (PyCFunction)os_setuid, METH_VARARGS, os_setuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009116
Barry Warsaw53699e91996-12-10 23:23:01 +00009117static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009118os_setuid_impl(PyModuleDef *module, uid_t uid);
9119
9120static PyObject *
9121os_setuid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009122{
Larry Hastings2f936352014-08-05 14:04:04 +10009123 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009124 uid_t uid;
Larry Hastings2f936352014-08-05 14:04:04 +10009125
9126 if (!PyArg_ParseTuple(args,
9127 "O&:setuid",
9128 _Py_Uid_Converter, &uid))
9129 goto exit;
9130 return_value = os_setuid_impl(module, uid);
9131
9132exit:
9133 return return_value;
9134}
9135
9136static PyObject *
9137os_setuid_impl(PyModuleDef *module, uid_t uid)
9138/*[clinic end generated code: output=aea344bc22ccf400 input=c921a3285aa22256]*/
9139{
Victor Stinner8c62be82010-05-06 00:08:46 +00009140 if (setuid(uid) < 0)
9141 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009142 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009143}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009144#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009145
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009146
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009147#ifdef HAVE_SETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10009148/*[clinic input]
9149os.seteuid
9150
9151 euid: uid_t
9152 /
9153
9154Set the current process's effective user id.
9155[clinic start generated code]*/
9156
9157PyDoc_STRVAR(os_seteuid__doc__,
9158"seteuid($module, euid, /)\n"
9159"--\n"
9160"\n"
9161"Set the current process\'s effective user id.");
9162
9163#define OS_SETEUID_METHODDEF \
9164 {"seteuid", (PyCFunction)os_seteuid, METH_VARARGS, os_seteuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009165
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009166static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009167os_seteuid_impl(PyModuleDef *module, uid_t euid);
9168
9169static PyObject *
9170os_seteuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009171{
Larry Hastings2f936352014-08-05 14:04:04 +10009172 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009173 uid_t euid;
Larry Hastings2f936352014-08-05 14:04:04 +10009174
9175 if (!PyArg_ParseTuple(args,
9176 "O&:seteuid",
9177 _Py_Uid_Converter, &euid))
9178 goto exit;
9179 return_value = os_seteuid_impl(module, euid);
9180
9181exit:
9182 return return_value;
9183}
9184
9185static PyObject *
9186os_seteuid_impl(PyModuleDef *module, uid_t euid)
9187/*[clinic end generated code: output=6e824cce4f3b8a5d input=ba93d927e4781aa9]*/
9188{
9189 if (seteuid(euid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009190 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009191 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009192}
9193#endif /* HAVE_SETEUID */
9194
Larry Hastings2f936352014-08-05 14:04:04 +10009195
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009196#ifdef HAVE_SETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10009197/*[clinic input]
9198os.setegid
9199
9200 egid: gid_t
9201 /
9202
9203Set the current process's effective group id.
9204[clinic start generated code]*/
9205
9206PyDoc_STRVAR(os_setegid__doc__,
9207"setegid($module, egid, /)\n"
9208"--\n"
9209"\n"
9210"Set the current process\'s effective group id.");
9211
9212#define OS_SETEGID_METHODDEF \
9213 {"setegid", (PyCFunction)os_setegid, METH_VARARGS, os_setegid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009214
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009215static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009216os_setegid_impl(PyModuleDef *module, gid_t egid);
9217
9218static PyObject *
9219os_setegid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009220{
Larry Hastings2f936352014-08-05 14:04:04 +10009221 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009222 gid_t egid;
Larry Hastings2f936352014-08-05 14:04:04 +10009223
9224 if (!PyArg_ParseTuple(args,
9225 "O&:setegid",
9226 _Py_Gid_Converter, &egid))
9227 goto exit;
9228 return_value = os_setegid_impl(module, egid);
9229
9230exit:
9231 return return_value;
9232}
9233
9234static PyObject *
9235os_setegid_impl(PyModuleDef *module, gid_t egid)
9236/*[clinic end generated code: output=80a32263a4d56a9c input=4080526d0ccd6ce3]*/
9237{
9238 if (setegid(egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009239 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009240 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009241}
9242#endif /* HAVE_SETEGID */
9243
Larry Hastings2f936352014-08-05 14:04:04 +10009244
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009245#ifdef HAVE_SETREUID
Larry Hastings2f936352014-08-05 14:04:04 +10009246/*[clinic input]
9247os.setreuid
9248
9249 ruid: uid_t
9250 euid: uid_t
9251 /
9252
9253Set the current process's real and effective user ids.
9254[clinic start generated code]*/
9255
9256PyDoc_STRVAR(os_setreuid__doc__,
9257"setreuid($module, ruid, euid, /)\n"
9258"--\n"
9259"\n"
9260"Set the current process\'s real and effective user ids.");
9261
9262#define OS_SETREUID_METHODDEF \
9263 {"setreuid", (PyCFunction)os_setreuid, METH_VARARGS, os_setreuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009264
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009265static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009266os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid);
9267
9268static PyObject *
9269os_setreuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009270{
Larry Hastings2f936352014-08-05 14:04:04 +10009271 PyObject *return_value = NULL;
9272 uid_t ruid;
9273 uid_t euid;
9274
9275 if (!PyArg_ParseTuple(args,
9276 "O&O&:setreuid",
9277 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid))
9278 goto exit;
9279 return_value = os_setreuid_impl(module, ruid, euid);
9280
9281exit:
9282 return return_value;
9283}
9284
9285static PyObject *
9286os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid)
9287/*[clinic end generated code: output=d7f226f943dad739 input=0ca8978de663880c]*/
9288{
Victor Stinner8c62be82010-05-06 00:08:46 +00009289 if (setreuid(ruid, euid) < 0) {
9290 return posix_error();
9291 } else {
9292 Py_INCREF(Py_None);
9293 return Py_None;
9294 }
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009295}
9296#endif /* HAVE_SETREUID */
9297
Larry Hastings2f936352014-08-05 14:04:04 +10009298
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009299#ifdef HAVE_SETREGID
Larry Hastings2f936352014-08-05 14:04:04 +10009300/*[clinic input]
9301os.setregid
9302
9303 rgid: gid_t
9304 egid: gid_t
9305 /
9306
9307Set the current process's real and effective group ids.
9308[clinic start generated code]*/
9309
9310PyDoc_STRVAR(os_setregid__doc__,
9311"setregid($module, rgid, egid, /)\n"
9312"--\n"
9313"\n"
9314"Set the current process\'s real and effective group ids.");
9315
9316#define OS_SETREGID_METHODDEF \
9317 {"setregid", (PyCFunction)os_setregid, METH_VARARGS, os_setregid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009318
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009319static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009320os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid);
9321
9322static PyObject *
9323os_setregid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009324{
Larry Hastings2f936352014-08-05 14:04:04 +10009325 PyObject *return_value = NULL;
9326 gid_t rgid;
9327 gid_t egid;
9328
9329 if (!PyArg_ParseTuple(args,
9330 "O&O&:setregid",
9331 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid))
9332 goto exit;
9333 return_value = os_setregid_impl(module, rgid, egid);
9334
9335exit:
9336 return return_value;
9337}
9338
9339static PyObject *
9340os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid)
9341/*[clinic end generated code: output=a82d9ab70f8e6562 input=c59499f72846db78]*/
9342{
9343 if (setregid(rgid, egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009344 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009345 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009346}
9347#endif /* HAVE_SETREGID */
9348
Larry Hastings2f936352014-08-05 14:04:04 +10009349
Guido van Rossumb6775db1994-08-01 11:34:53 +00009350#ifdef HAVE_SETGID
Larry Hastings2f936352014-08-05 14:04:04 +10009351/*[clinic input]
9352os.setgid
9353 gid: gid_t
9354 /
9355
9356Set the current process's group id.
9357[clinic start generated code]*/
9358
9359PyDoc_STRVAR(os_setgid__doc__,
9360"setgid($module, gid, /)\n"
9361"--\n"
9362"\n"
9363"Set the current process\'s group id.");
9364
9365#define OS_SETGID_METHODDEF \
9366 {"setgid", (PyCFunction)os_setgid, METH_VARARGS, os_setgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009367
Barry Warsaw53699e91996-12-10 23:23:01 +00009368static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009369os_setgid_impl(PyModuleDef *module, gid_t gid);
9370
9371static PyObject *
9372os_setgid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009373{
Larry Hastings2f936352014-08-05 14:04:04 +10009374 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009375 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10009376
9377 if (!PyArg_ParseTuple(args,
9378 "O&:setgid",
9379 _Py_Gid_Converter, &gid))
9380 goto exit;
9381 return_value = os_setgid_impl(module, gid);
9382
9383exit:
9384 return return_value;
9385}
9386
9387static PyObject *
9388os_setgid_impl(PyModuleDef *module, gid_t gid)
9389/*[clinic end generated code: output=08287886db435f23 input=27d30c4059045dc6]*/
9390{
Victor Stinner8c62be82010-05-06 00:08:46 +00009391 if (setgid(gid) < 0)
9392 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009393 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009394}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009395#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009396
Larry Hastings2f936352014-08-05 14:04:04 +10009397
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009398#ifdef HAVE_SETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10009399/*[clinic input]
9400os.setgroups
9401
9402 groups: object
9403 /
9404
9405Set the groups of the current process to list.
9406[clinic start generated code]*/
9407
9408PyDoc_STRVAR(os_setgroups__doc__,
9409"setgroups($module, groups, /)\n"
9410"--\n"
9411"\n"
9412"Set the groups of the current process to list.");
9413
9414#define OS_SETGROUPS_METHODDEF \
9415 {"setgroups", (PyCFunction)os_setgroups, METH_O, os_setgroups__doc__},
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009416
9417static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009418os_setgroups(PyModuleDef *module, PyObject *groups)
9419/*[clinic end generated code: output=0b8de65d5b3cda94 input=fa742ca3daf85a7e]*/
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009420{
Victor Stinner8c62be82010-05-06 00:08:46 +00009421 int i, len;
9422 gid_t grouplist[MAX_GROUPS];
Tim Peters5aa91602002-01-30 05:46:57 +00009423
Victor Stinner8c62be82010-05-06 00:08:46 +00009424 if (!PySequence_Check(groups)) {
9425 PyErr_SetString(PyExc_TypeError, "setgroups argument must be a sequence");
9426 return NULL;
9427 }
9428 len = PySequence_Size(groups);
9429 if (len > MAX_GROUPS) {
9430 PyErr_SetString(PyExc_ValueError, "too many groups");
9431 return NULL;
9432 }
9433 for(i = 0; i < len; i++) {
9434 PyObject *elem;
9435 elem = PySequence_GetItem(groups, i);
9436 if (!elem)
9437 return NULL;
9438 if (!PyLong_Check(elem)) {
9439 PyErr_SetString(PyExc_TypeError,
9440 "groups must be integers");
9441 Py_DECREF(elem);
9442 return NULL;
9443 } else {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009444 if (!_Py_Gid_Converter(elem, &grouplist[i])) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009445 Py_DECREF(elem);
9446 return NULL;
9447 }
9448 }
9449 Py_DECREF(elem);
9450 }
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009451
Victor Stinner8c62be82010-05-06 00:08:46 +00009452 if (setgroups(len, grouplist) < 0)
9453 return posix_error();
9454 Py_INCREF(Py_None);
9455 return Py_None;
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009456}
9457#endif /* HAVE_SETGROUPS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009458
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009459#if defined(HAVE_WAIT3) || defined(HAVE_WAIT4)
9460static PyObject *
Victor Stinner4195b5c2012-02-08 23:03:19 +01009461wait_helper(pid_t pid, int status, struct rusage *ru)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009462{
Victor Stinner8c62be82010-05-06 00:08:46 +00009463 PyObject *result;
9464 static PyObject *struct_rusage;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02009465 _Py_IDENTIFIER(struct_rusage);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009466
Victor Stinner8c62be82010-05-06 00:08:46 +00009467 if (pid == -1)
9468 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009469
Victor Stinner8c62be82010-05-06 00:08:46 +00009470 if (struct_rusage == NULL) {
9471 PyObject *m = PyImport_ImportModuleNoBlock("resource");
9472 if (m == NULL)
9473 return NULL;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02009474 struct_rusage = _PyObject_GetAttrId(m, &PyId_struct_rusage);
Victor Stinner8c62be82010-05-06 00:08:46 +00009475 Py_DECREF(m);
9476 if (struct_rusage == NULL)
9477 return NULL;
9478 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009479
Victor Stinner8c62be82010-05-06 00:08:46 +00009480 /* XXX(nnorwitz): Copied (w/mods) from resource.c, there should be only one. */
9481 result = PyStructSequence_New((PyTypeObject*) struct_rusage);
9482 if (!result)
9483 return NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009484
9485#ifndef doubletime
9486#define doubletime(TV) ((double)(TV).tv_sec + (TV).tv_usec * 0.000001)
9487#endif
9488
Victor Stinner8c62be82010-05-06 00:08:46 +00009489 PyStructSequence_SET_ITEM(result, 0,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009490 PyFloat_FromDouble(doubletime(ru->ru_utime)));
Victor Stinner8c62be82010-05-06 00:08:46 +00009491 PyStructSequence_SET_ITEM(result, 1,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009492 PyFloat_FromDouble(doubletime(ru->ru_stime)));
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009493#define SET_INT(result, index, value)\
Victor Stinner8c62be82010-05-06 00:08:46 +00009494 PyStructSequence_SET_ITEM(result, index, PyLong_FromLong(value))
9495 SET_INT(result, 2, ru->ru_maxrss);
9496 SET_INT(result, 3, ru->ru_ixrss);
9497 SET_INT(result, 4, ru->ru_idrss);
9498 SET_INT(result, 5, ru->ru_isrss);
9499 SET_INT(result, 6, ru->ru_minflt);
9500 SET_INT(result, 7, ru->ru_majflt);
9501 SET_INT(result, 8, ru->ru_nswap);
9502 SET_INT(result, 9, ru->ru_inblock);
9503 SET_INT(result, 10, ru->ru_oublock);
9504 SET_INT(result, 11, ru->ru_msgsnd);
9505 SET_INT(result, 12, ru->ru_msgrcv);
9506 SET_INT(result, 13, ru->ru_nsignals);
9507 SET_INT(result, 14, ru->ru_nvcsw);
9508 SET_INT(result, 15, ru->ru_nivcsw);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009509#undef SET_INT
9510
Victor Stinner8c62be82010-05-06 00:08:46 +00009511 if (PyErr_Occurred()) {
9512 Py_DECREF(result);
9513 return NULL;
9514 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009515
Victor Stinner8c62be82010-05-06 00:08:46 +00009516 return Py_BuildValue("NiN", PyLong_FromPid(pid), status, result);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009517}
9518#endif /* HAVE_WAIT3 || HAVE_WAIT4 */
9519
Larry Hastings2f936352014-08-05 14:04:04 +10009520
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009521#ifdef HAVE_WAIT3
Larry Hastings2f936352014-08-05 14:04:04 +10009522/*[clinic input]
9523os.wait3
9524
9525 options: int
9526Wait for completion of a child process.
9527
9528Returns a tuple of information about the child process:
9529 (pid, status, rusage)
9530[clinic start generated code]*/
9531
9532PyDoc_STRVAR(os_wait3__doc__,
9533"wait3($module, /, options)\n"
9534"--\n"
9535"\n"
9536"Wait for completion of a child process.\n"
9537"\n"
9538"Returns a tuple of information about the child process:\n"
9539" (pid, status, rusage)");
9540
9541#define OS_WAIT3_METHODDEF \
9542 {"wait3", (PyCFunction)os_wait3, METH_VARARGS|METH_KEYWORDS, os_wait3__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009543
9544static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009545os_wait3_impl(PyModuleDef *module, int options);
9546
9547static PyObject *
9548os_wait3(PyModuleDef *module, PyObject *args, PyObject *kwargs)
9549{
9550 PyObject *return_value = NULL;
9551 static char *_keywords[] = {"options", NULL};
9552 int options;
9553
9554 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9555 "i:wait3", _keywords,
9556 &options))
9557 goto exit;
9558 return_value = os_wait3_impl(module, options);
9559
9560exit:
9561 return return_value;
9562}
9563
9564static PyObject *
9565os_wait3_impl(PyModuleDef *module, int options)
9566/*[clinic end generated code: output=1f2a63b6a93cbb57 input=8ac4c56956b61710]*/
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009567{
Victor Stinner8c62be82010-05-06 00:08:46 +00009568 pid_t pid;
Victor Stinner8c62be82010-05-06 00:08:46 +00009569 struct rusage ru;
9570 WAIT_TYPE status;
9571 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009572
Victor Stinner8c62be82010-05-06 00:08:46 +00009573 Py_BEGIN_ALLOW_THREADS
9574 pid = wait3(&status, options, &ru);
9575 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009576
Victor Stinner4195b5c2012-02-08 23:03:19 +01009577 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009578}
9579#endif /* HAVE_WAIT3 */
9580
Larry Hastings2f936352014-08-05 14:04:04 +10009581
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009582#ifdef HAVE_WAIT4
Larry Hastings2f936352014-08-05 14:04:04 +10009583/*[clinic input]
9584
9585os.wait4
9586
9587 pid: pid_t
9588 options: int
9589
9590Wait for completion of a specific child process.
9591
9592Returns a tuple of information about the child process:
9593 (pid, status, rusage)
9594[clinic start generated code]*/
9595
9596PyDoc_STRVAR(os_wait4__doc__,
9597"wait4($module, /, pid, options)\n"
9598"--\n"
9599"\n"
9600"Wait for completion of a specific child process.\n"
9601"\n"
9602"Returns a tuple of information about the child process:\n"
9603" (pid, status, rusage)");
9604
9605#define OS_WAIT4_METHODDEF \
9606 {"wait4", (PyCFunction)os_wait4, METH_VARARGS|METH_KEYWORDS, os_wait4__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009607
9608static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009609os_wait4_impl(PyModuleDef *module, pid_t pid, int options);
9610
9611static PyObject *
9612os_wait4(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009613{
Larry Hastings2f936352014-08-05 14:04:04 +10009614 PyObject *return_value = NULL;
9615 static char *_keywords[] = {"pid", "options", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00009616 pid_t pid;
9617 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009618
9619 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9620 "" _Py_PARSE_PID "i:wait4", _keywords,
9621 &pid, &options))
9622 goto exit;
9623 return_value = os_wait4_impl(module, pid, options);
9624
9625exit:
9626 return return_value;
9627}
9628
9629static PyObject *
9630os_wait4_impl(PyModuleDef *module, pid_t pid, int options)
9631/*[clinic end generated code: output=20dfb05289d37dc6 input=d11deed0750600ba]*/
9632{
Victor Stinner8c62be82010-05-06 00:08:46 +00009633 struct rusage ru;
9634 WAIT_TYPE status;
9635 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009636
Victor Stinner8c62be82010-05-06 00:08:46 +00009637 Py_BEGIN_ALLOW_THREADS
9638 pid = wait4(pid, &status, options, &ru);
9639 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009640
Victor Stinner4195b5c2012-02-08 23:03:19 +01009641 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009642}
9643#endif /* HAVE_WAIT4 */
9644
Larry Hastings2f936352014-08-05 14:04:04 +10009645
Ross Lagerwall7807c352011-03-17 20:20:30 +02009646#if defined(HAVE_WAITID) && !defined(__APPLE__)
Larry Hastings2f936352014-08-05 14:04:04 +10009647/*[clinic input]
9648os.waitid
9649
9650 idtype: idtype_t
9651 Must be one of be P_PID, P_PGID or P_ALL.
9652 id: id_t
9653 The id to wait on.
9654 options: int
9655 Constructed from the ORing of one or more of WEXITED, WSTOPPED
9656 or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.
9657 /
9658
9659Returns the result of waiting for a process or processes.
9660
9661Returns either waitid_result or None if WNOHANG is specified and there are
9662no children in a waitable state.
9663[clinic start generated code]*/
9664
9665PyDoc_STRVAR(os_waitid__doc__,
9666"waitid($module, idtype, id, options, /)\n"
9667"--\n"
9668"\n"
9669"Returns the result of waiting for a process or processes.\n"
9670"\n"
9671" idtype\n"
9672" Must be one of be P_PID, P_PGID or P_ALL.\n"
9673" id\n"
9674" The id to wait on.\n"
9675" options\n"
9676" Constructed from the ORing of one or more of WEXITED, WSTOPPED\n"
9677" or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.\n"
9678"\n"
9679"Returns either waitid_result or None if WNOHANG is specified and there are\n"
9680"no children in a waitable state.");
9681
9682#define OS_WAITID_METHODDEF \
9683 {"waitid", (PyCFunction)os_waitid, METH_VARARGS, os_waitid__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02009684
9685static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009686os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options);
9687
9688static PyObject *
9689os_waitid(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02009690{
Larry Hastings2f936352014-08-05 14:04:04 +10009691 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009692 idtype_t idtype;
9693 id_t id;
Larry Hastings2f936352014-08-05 14:04:04 +10009694 int options;
9695
9696 if (!PyArg_ParseTuple(args,
9697 "i" _Py_PARSE_PID "i:waitid",
9698 &idtype, &id, &options))
9699 goto exit;
9700 return_value = os_waitid_impl(module, idtype, id, options);
9701
9702exit:
9703 return return_value;
9704}
9705
9706static PyObject *
9707os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options)
9708/*[clinic end generated code: output=fb44bf97f01021b2 input=d8e7f76e052b7920]*/
9709{
9710 PyObject *result;
9711 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009712 siginfo_t si;
9713 si.si_pid = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10009714
Ross Lagerwall7807c352011-03-17 20:20:30 +02009715 Py_BEGIN_ALLOW_THREADS
9716 res = waitid(idtype, id, &si, options);
9717 Py_END_ALLOW_THREADS
9718 if (res == -1)
9719 return posix_error();
9720
9721 if (si.si_pid == 0)
9722 Py_RETURN_NONE;
9723
9724 result = PyStructSequence_New(&WaitidResultType);
9725 if (!result)
9726 return NULL;
9727
9728 PyStructSequence_SET_ITEM(result, 0, PyLong_FromPid(si.si_pid));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009729 PyStructSequence_SET_ITEM(result, 1, _PyLong_FromUid(si.si_uid));
Ross Lagerwall7807c352011-03-17 20:20:30 +02009730 PyStructSequence_SET_ITEM(result, 2, PyLong_FromLong((long)(si.si_signo)));
9731 PyStructSequence_SET_ITEM(result, 3, PyLong_FromLong((long)(si.si_status)));
9732 PyStructSequence_SET_ITEM(result, 4, PyLong_FromLong((long)(si.si_code)));
9733 if (PyErr_Occurred()) {
9734 Py_DECREF(result);
9735 return NULL;
9736 }
9737
9738 return result;
9739}
Larry Hastings2f936352014-08-05 14:04:04 +10009740#endif /* defined(HAVE_WAITID) && !defined(__APPLE__) */
Ross Lagerwall7807c352011-03-17 20:20:30 +02009741
Larry Hastings2f936352014-08-05 14:04:04 +10009742
9743#if defined(HAVE_WAITPID)
9744/*[clinic input]
9745os.waitpid
9746 pid: pid_t
9747 options: int
9748 /
9749
9750Wait for completion of a given child process.
9751
9752Returns a tuple of information regarding the child process:
9753 (pid, status)
9754
9755The options argument is ignored on Windows.
9756[clinic start generated code]*/
9757
9758PyDoc_STRVAR(os_waitpid__doc__,
9759"waitpid($module, pid, options, /)\n"
9760"--\n"
9761"\n"
9762"Wait for completion of a given child process.\n"
9763"\n"
9764"Returns a tuple of information regarding the child process:\n"
9765" (pid, status)\n"
9766"\n"
9767"The options argument is ignored on Windows.");
9768
9769#define OS_WAITPID_METHODDEF \
9770 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009771
Barry Warsaw53699e91996-12-10 23:23:01 +00009772static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009773os_waitpid_impl(PyModuleDef *module, pid_t pid, int options);
9774
9775static PyObject *
9776os_waitpid(PyModuleDef *module, PyObject *args)
Guido van Rossum85e3b011991-06-03 12:42:10 +00009777{
Larry Hastings2f936352014-08-05 14:04:04 +10009778 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009779 pid_t pid;
9780 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009781
9782 if (!PyArg_ParseTuple(args,
9783 "" _Py_PARSE_PID "i:waitpid",
9784 &pid, &options))
9785 goto exit;
9786 return_value = os_waitpid_impl(module, pid, options);
9787
9788exit:
9789 return return_value;
9790}
9791
9792static PyObject *
9793os_waitpid_impl(PyModuleDef *module, pid_t pid, int options)
9794/*[clinic end generated code: output=095a6b00af70b7ac input=0bf1666b8758fda3]*/
9795{
Victor Stinner8c62be82010-05-06 00:08:46 +00009796 WAIT_TYPE status;
9797 WAIT_STATUS_INT(status) = 0;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00009798
Victor Stinner8c62be82010-05-06 00:08:46 +00009799 Py_BEGIN_ALLOW_THREADS
9800 pid = waitpid(pid, &status, options);
9801 Py_END_ALLOW_THREADS
9802 if (pid == -1)
9803 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009804
Victor Stinner8c62be82010-05-06 00:08:46 +00009805 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum21803b81992-08-09 12:55:27 +00009806}
Tim Petersab034fa2002-02-01 11:27:43 +00009807#elif defined(HAVE_CWAIT)
Tim Petersab034fa2002-02-01 11:27:43 +00009808/* MS C has a variant of waitpid() that's usable for most purposes. */
Larry Hastings2f936352014-08-05 14:04:04 +10009809/*[clinic input]
9810os.waitpid
9811 pid: Py_intptr_t
9812 options: int
9813 /
9814
9815Wait for completion of a given process.
9816
9817Returns a tuple of information regarding the process:
9818 (pid, status << 8)
9819
9820The options argument is ignored on Windows.
9821[clinic start generated code]*/
9822
9823PyDoc_STRVAR(os_waitpid__doc__,
9824"waitpid($module, pid, options, /)\n"
9825"--\n"
9826"\n"
9827"Wait for completion of a given process.\n"
9828"\n"
9829"Returns a tuple of information regarding the process:\n"
9830" (pid, status << 8)\n"
9831"\n"
9832"The options argument is ignored on Windows.");
9833
9834#define OS_WAITPID_METHODDEF \
9835 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Tim Petersab034fa2002-02-01 11:27:43 +00009836
9837static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009838os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options);
Tim Petersab034fa2002-02-01 11:27:43 +00009839
Larry Hastings2f936352014-08-05 14:04:04 +10009840static PyObject *
9841os_waitpid(PyModuleDef *module, PyObject *args)
9842{
9843 PyObject *return_value = NULL;
9844 Py_intptr_t pid;
9845 int options;
9846
9847 if (!PyArg_ParseTuple(args,
9848 "" _Py_PARSE_INTPTR "i:waitpid",
9849 &pid, &options))
9850 goto exit;
9851 return_value = os_waitpid_impl(module, pid, options);
9852
9853exit:
9854 return return_value;
9855}
9856
9857static PyObject *
9858os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options)
9859/*[clinic end generated code: output=c20b95b15ad44a3a input=444c8f51cca5b862]*/
9860{
9861 int status;
9862
Victor Stinner8c62be82010-05-06 00:08:46 +00009863 Py_BEGIN_ALLOW_THREADS
9864 pid = _cwait(&status, pid, options);
9865 Py_END_ALLOW_THREADS
9866 if (pid == -1)
9867 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009868
Victor Stinner8c62be82010-05-06 00:08:46 +00009869 /* shift the status left a byte so this is more like the POSIX waitpid */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01009870 return Py_BuildValue(_Py_PARSE_INTPTR "i", pid, status << 8);
Tim Petersab034fa2002-02-01 11:27:43 +00009871}
Larry Hastings2f936352014-08-05 14:04:04 +10009872#endif
9873
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009874
Guido van Rossumad0ee831995-03-01 10:34:45 +00009875#ifdef HAVE_WAIT
Larry Hastings2f936352014-08-05 14:04:04 +10009876/*[clinic input]
9877os.wait
9878
9879Wait for completion of a child process.
9880
9881Returns a tuple of information about the child process:
9882 (pid, status)
9883[clinic start generated code]*/
9884
9885PyDoc_STRVAR(os_wait__doc__,
9886"wait($module, /)\n"
9887"--\n"
9888"\n"
9889"Wait for completion of a child process.\n"
9890"\n"
9891"Returns a tuple of information about the child process:\n"
9892" (pid, status)");
9893
9894#define OS_WAIT_METHODDEF \
9895 {"wait", (PyCFunction)os_wait, METH_NOARGS, os_wait__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009896
Barry Warsaw53699e91996-12-10 23:23:01 +00009897static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009898os_wait_impl(PyModuleDef *module);
9899
9900static PyObject *
9901os_wait(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
9902{
9903 return os_wait_impl(module);
9904}
9905
9906static PyObject *
9907os_wait_impl(PyModuleDef *module)
9908/*[clinic end generated code: output=2a83a9d164e7e6a8 input=03b0182d4a4700ce]*/
Guido van Rossum21803b81992-08-09 12:55:27 +00009909{
Victor Stinner8c62be82010-05-06 00:08:46 +00009910 pid_t pid;
9911 WAIT_TYPE status;
9912 WAIT_STATUS_INT(status) = 0;
Neal Norwitze241ce82003-02-17 18:17:05 +00009913
Victor Stinner8c62be82010-05-06 00:08:46 +00009914 Py_BEGIN_ALLOW_THREADS
9915 pid = wait(&status);
9916 Py_END_ALLOW_THREADS
9917 if (pid == -1)
9918 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009919
Victor Stinner8c62be82010-05-06 00:08:46 +00009920 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum85e3b011991-06-03 12:42:10 +00009921}
Larry Hastings2f936352014-08-05 14:04:04 +10009922#endif /* HAVE_WAIT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00009923
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009924
Larry Hastings9cf065c2012-06-22 16:30:09 -07009925#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
9926PyDoc_STRVAR(readlink__doc__,
9927"readlink(path, *, dir_fd=None) -> path\n\n\
9928Return a string representing the path to which the symbolic link points.\n\
9929\n\
9930If dir_fd is not None, it should be a file descriptor open to a directory,\n\
9931 and path should be relative; path will then be relative to that directory.\n\
9932dir_fd may not be implemented on your platform.\n\
9933 If it is unavailable, using it will raise a NotImplementedError.");
Mark Hammondc2e85bd2002-10-03 05:10:39 +00009934#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009935
Guido van Rossumb6775db1994-08-01 11:34:53 +00009936#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009937
Larry Hastings2f936352014-08-05 14:04:04 +10009938/* AC 3.5: merge win32 and not together */
Barry Warsaw53699e91996-12-10 23:23:01 +00009939static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07009940posix_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009941{
Larry Hastings9cf065c2012-06-22 16:30:09 -07009942 path_t path;
9943 int dir_fd = DEFAULT_DIR_FD;
9944 char buffer[MAXPATHLEN];
9945 ssize_t length;
9946 PyObject *return_value = NULL;
9947 static char *keywords[] = {"path", "dir_fd", NULL};
Thomas Wouters89f507f2006-12-13 04:49:30 +00009948
Larry Hastings9cf065c2012-06-22 16:30:09 -07009949 memset(&path, 0, sizeof(path));
Victor Stinner292c8352012-10-30 02:17:38 +01009950 path.function_name = "readlink";
Larry Hastings9cf065c2012-06-22 16:30:09 -07009951 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O&|$O&:readlink", keywords,
9952 path_converter, &path,
Larry Hastings2f936352014-08-05 14:04:04 +10009953 READLINKAT_DIR_FD_CONVERTER, &dir_fd))
Victor Stinner8c62be82010-05-06 00:08:46 +00009954 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00009955
Victor Stinner8c62be82010-05-06 00:08:46 +00009956 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07009957#ifdef HAVE_READLINKAT
9958 if (dir_fd != DEFAULT_DIR_FD)
9959 length = readlinkat(dir_fd, path.narrow, buffer, sizeof(buffer));
Victor Stinnera45598a2010-05-14 16:35:39 +00009960 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07009961#endif
9962 length = readlink(path.narrow, buffer, sizeof(buffer));
9963 Py_END_ALLOW_THREADS
9964
9965 if (length < 0) {
Victor Stinner292c8352012-10-30 02:17:38 +01009966 return_value = path_error(&path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009967 goto exit;
9968 }
9969
9970 if (PyUnicode_Check(path.object))
9971 return_value = PyUnicode_DecodeFSDefaultAndSize(buffer, length);
9972 else
9973 return_value = PyBytes_FromStringAndSize(buffer, length);
9974exit:
9975 path_cleanup(&path);
9976 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009977}
Larry Hastings9cf065c2012-06-22 16:30:09 -07009978
Guido van Rossumb6775db1994-08-01 11:34:53 +00009979#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009980
Larry Hastings2f936352014-08-05 14:04:04 +10009981#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
9982
9983static PyObject *
9984win_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
9985{
9986 wchar_t *path;
9987 DWORD n_bytes_returned;
9988 DWORD io_result;
9989 PyObject *po, *result;
9990 int dir_fd;
9991 HANDLE reparse_point_handle;
9992
9993 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
9994 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
9995 wchar_t *print_name;
9996
9997 static char *keywords[] = {"path", "dir_fd", NULL};
9998
9999 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "U|$O&:readlink", keywords,
10000 &po,
10001 dir_fd_unavailable, &dir_fd
10002 ))
10003 return NULL;
10004
10005 path = PyUnicode_AsUnicode(po);
10006 if (path == NULL)
10007 return NULL;
10008
10009 /* First get a handle to the reparse point */
10010 Py_BEGIN_ALLOW_THREADS
10011 reparse_point_handle = CreateFileW(
10012 path,
10013 0,
10014 0,
10015 0,
10016 OPEN_EXISTING,
10017 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS,
10018 0);
10019 Py_END_ALLOW_THREADS
10020
10021 if (reparse_point_handle==INVALID_HANDLE_VALUE)
10022 return win32_error_object("readlink", po);
10023
10024 Py_BEGIN_ALLOW_THREADS
10025 /* New call DeviceIoControl to read the reparse point */
10026 io_result = DeviceIoControl(
10027 reparse_point_handle,
10028 FSCTL_GET_REPARSE_POINT,
10029 0, 0, /* in buffer */
10030 target_buffer, sizeof(target_buffer),
10031 &n_bytes_returned,
10032 0 /* we're not using OVERLAPPED_IO */
10033 );
10034 CloseHandle(reparse_point_handle);
10035 Py_END_ALLOW_THREADS
10036
10037 if (io_result==0)
10038 return win32_error_object("readlink", po);
10039
10040 if (rdb->ReparseTag != IO_REPARSE_TAG_SYMLINK)
10041 {
10042 PyErr_SetString(PyExc_ValueError,
10043 "not a symbolic link");
10044 return NULL;
10045 }
10046 print_name = rdb->SymbolicLinkReparseBuffer.PathBuffer +
10047 rdb->SymbolicLinkReparseBuffer.PrintNameOffset;
10048
10049 result = PyUnicode_FromWideChar(print_name,
10050 rdb->SymbolicLinkReparseBuffer.PrintNameLength/2);
10051 return result;
10052}
10053
10054#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
10055
10056
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010057
Larry Hastings9cf065c2012-06-22 16:30:09 -070010058#ifdef HAVE_SYMLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070010059
10060#if defined(MS_WINDOWS)
10061
10062/* Grab CreateSymbolicLinkW dynamically from kernel32 */
10063static DWORD (CALLBACK *Py_CreateSymbolicLinkW)(LPWSTR, LPWSTR, DWORD) = NULL;
10064static DWORD (CALLBACK *Py_CreateSymbolicLinkA)(LPSTR, LPSTR, DWORD) = NULL;
Victor Stinner31b3b922013-06-05 01:49:17 +020010065
Larry Hastings9cf065c2012-06-22 16:30:09 -070010066static int
Victor Stinner31b3b922013-06-05 01:49:17 +020010067check_CreateSymbolicLink(void)
Larry Hastings9cf065c2012-06-22 16:30:09 -070010068{
10069 HINSTANCE hKernel32;
10070 /* only recheck */
10071 if (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA)
10072 return 1;
10073 hKernel32 = GetModuleHandleW(L"KERNEL32");
10074 *(FARPROC*)&Py_CreateSymbolicLinkW = GetProcAddress(hKernel32,
10075 "CreateSymbolicLinkW");
10076 *(FARPROC*)&Py_CreateSymbolicLinkA = GetProcAddress(hKernel32,
10077 "CreateSymbolicLinkA");
10078 return (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA);
10079}
10080
Victor Stinner31b3b922013-06-05 01:49:17 +020010081/* Remove the last portion of the path */
10082static void
10083_dirnameW(WCHAR *path)
10084{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010085 WCHAR *ptr;
10086
10087 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010088 for(ptr = path + wcslen(path); ptr != path; ptr--) {
Victor Stinner072318b2013-06-05 02:07:46 +020010089 if (*ptr == L'\\' || *ptr == L'/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010090 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010091 }
10092 *ptr = 0;
10093}
10094
Victor Stinner31b3b922013-06-05 01:49:17 +020010095/* Remove the last portion of the path */
10096static void
10097_dirnameA(char *path)
10098{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010099 char *ptr;
10100
10101 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010102 for(ptr = path + strlen(path); ptr != path; ptr--) {
10103 if (*ptr == '\\' || *ptr == '/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010104 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010105 }
10106 *ptr = 0;
10107}
10108
Victor Stinner31b3b922013-06-05 01:49:17 +020010109/* Is this path absolute? */
10110static int
10111_is_absW(const WCHAR *path)
10112{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010113 return path[0] == L'\\' || path[0] == L'/' || path[1] == L':';
10114
10115}
10116
Victor Stinner31b3b922013-06-05 01:49:17 +020010117/* Is this path absolute? */
10118static int
10119_is_absA(const char *path)
10120{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010121 return path[0] == '\\' || path[0] == '/' || path[1] == ':';
10122
10123}
10124
Victor Stinner31b3b922013-06-05 01:49:17 +020010125/* join root and rest with a backslash */
10126static void
10127_joinW(WCHAR *dest_path, const WCHAR *root, const WCHAR *rest)
10128{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010129 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010130
Victor Stinner31b3b922013-06-05 01:49:17 +020010131 if (_is_absW(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010132 wcscpy(dest_path, rest);
10133 return;
10134 }
10135
10136 root_len = wcslen(root);
10137
10138 wcscpy(dest_path, root);
10139 if(root_len) {
Victor Stinner31b3b922013-06-05 01:49:17 +020010140 dest_path[root_len] = L'\\';
10141 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010142 }
10143 wcscpy(dest_path+root_len, rest);
10144}
10145
Victor Stinner31b3b922013-06-05 01:49:17 +020010146/* join root and rest with a backslash */
10147static void
10148_joinA(char *dest_path, const char *root, const char *rest)
10149{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010150 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010151
Victor Stinner31b3b922013-06-05 01:49:17 +020010152 if (_is_absA(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010153 strcpy(dest_path, rest);
10154 return;
10155 }
10156
10157 root_len = strlen(root);
10158
10159 strcpy(dest_path, root);
10160 if(root_len) {
10161 dest_path[root_len] = '\\';
Victor Stinner31b3b922013-06-05 01:49:17 +020010162 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010163 }
10164 strcpy(dest_path+root_len, rest);
10165}
10166
Victor Stinner31b3b922013-06-05 01:49:17 +020010167/* Return True if the path at src relative to dest is a directory */
10168static int
10169_check_dirW(WCHAR *src, WCHAR *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010170{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010171 WIN32_FILE_ATTRIBUTE_DATA src_info;
10172 WCHAR dest_parent[MAX_PATH];
10173 WCHAR src_resolved[MAX_PATH] = L"";
10174
10175 /* dest_parent = os.path.dirname(dest) */
10176 wcscpy(dest_parent, dest);
10177 _dirnameW(dest_parent);
10178 /* src_resolved = os.path.join(dest_parent, src) */
10179 _joinW(src_resolved, dest_parent, src);
10180 return (
10181 GetFileAttributesExW(src_resolved, GetFileExInfoStandard, &src_info)
10182 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10183 );
10184}
10185
Victor Stinner31b3b922013-06-05 01:49:17 +020010186/* Return True if the path at src relative to dest is a directory */
10187static int
10188_check_dirA(char *src, char *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010189{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010190 WIN32_FILE_ATTRIBUTE_DATA src_info;
10191 char dest_parent[MAX_PATH];
10192 char src_resolved[MAX_PATH] = "";
10193
10194 /* dest_parent = os.path.dirname(dest) */
10195 strcpy(dest_parent, dest);
Victor Stinner5a436762013-06-05 00:37:12 +020010196 _dirnameA(dest_parent);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010197 /* src_resolved = os.path.join(dest_parent, src) */
Victor Stinner5a436762013-06-05 00:37:12 +020010198 _joinA(src_resolved, dest_parent, src);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010199 return (
10200 GetFileAttributesExA(src_resolved, GetFileExInfoStandard, &src_info)
10201 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10202 );
10203}
Larry Hastings9cf065c2012-06-22 16:30:09 -070010204#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010205
Larry Hastings2f936352014-08-05 14:04:04 +100010206
10207/*[clinic input]
10208os.symlink
10209 src: path_t
10210 dst: path_t
10211 target_is_directory: bool = False
10212 *
10213 dir_fd: dir_fd(requires='symlinkat')=None
10214
10215# "symlink(src, dst, target_is_directory=False, *, dir_fd=None)\n\n\
10216
10217Create a symbolic link pointing to src named dst.
10218
10219target_is_directory is required on Windows if the target is to be
10220 interpreted as a directory. (On Windows, symlink requires
10221 Windows 6.0 or greater, and raises a NotImplementedError otherwise.)
10222 target_is_directory is ignored on non-Windows platforms.
10223
10224If dir_fd is not None, it should be a file descriptor open to a directory,
10225 and path should be relative; path will then be relative to that directory.
10226dir_fd may not be implemented on your platform.
10227 If it is unavailable, using it will raise a NotImplementedError.
10228
10229[clinic start generated code]*/
10230
10231PyDoc_STRVAR(os_symlink__doc__,
10232"symlink($module, /, src, dst, target_is_directory=False, *, dir_fd=None)\n"
10233"--\n"
10234"\n"
10235"Create a symbolic link pointing to src named dst.\n"
10236"\n"
10237"target_is_directory is required on Windows if the target is to be\n"
10238" interpreted as a directory. (On Windows, symlink requires\n"
10239" Windows 6.0 or greater, and raises a NotImplementedError otherwise.)\n"
10240" target_is_directory is ignored on non-Windows platforms.\n"
10241"\n"
10242"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10243" and path should be relative; path will then be relative to that directory.\n"
10244"dir_fd may not be implemented on your platform.\n"
10245" If it is unavailable, using it will raise a NotImplementedError.");
10246
10247#define OS_SYMLINK_METHODDEF \
10248 {"symlink", (PyCFunction)os_symlink, METH_VARARGS|METH_KEYWORDS, os_symlink__doc__},
10249
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010250static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010251os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd);
10252
10253static PyObject *
10254os_symlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010255{
Larry Hastings2f936352014-08-05 14:04:04 +100010256 PyObject *return_value = NULL;
10257 static char *_keywords[] = {"src", "dst", "target_is_directory", "dir_fd", NULL};
10258 path_t src = PATH_T_INITIALIZE("symlink", "src", 0, 0);
10259 path_t dst = PATH_T_INITIALIZE("symlink", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010260 int target_is_directory = 0;
Larry Hastings2f936352014-08-05 14:04:04 +100010261 int dir_fd = DEFAULT_DIR_FD;
10262
10263 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10264 "O&O&|p$O&:symlink", _keywords,
10265 path_converter, &src, path_converter, &dst, &target_is_directory, SYMLINKAT_DIR_FD_CONVERTER, &dir_fd))
10266 goto exit;
10267 return_value = os_symlink_impl(module, &src, &dst, target_is_directory, dir_fd);
10268
10269exit:
10270 /* Cleanup for src */
10271 path_cleanup(&src);
10272 /* Cleanup for dst */
10273 path_cleanup(&dst);
10274
10275 return return_value;
10276}
10277
10278static PyObject *
10279os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd)
10280/*[clinic end generated code: output=1a31e6d88aafe9b6 input=e820ec4472547bc3]*/
10281{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010282#ifdef MS_WINDOWS
10283 DWORD result;
10284#else
10285 int result;
10286#endif
10287
Larry Hastings9cf065c2012-06-22 16:30:09 -070010288#ifdef MS_WINDOWS
10289 if (!check_CreateSymbolicLink()) {
10290 PyErr_SetString(PyExc_NotImplementedError,
10291 "CreateSymbolicLink functions not found");
Larry Hastings2f936352014-08-05 14:04:04 +100010292 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010293 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010294 if (!win32_can_symlink) {
10295 PyErr_SetString(PyExc_OSError, "symbolic link privilege not held");
Larry Hastings2f936352014-08-05 14:04:04 +100010296 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010297 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010298#endif
10299
Larry Hastings2f936352014-08-05 14:04:04 +100010300 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070010301 PyErr_SetString(PyExc_ValueError,
10302 "symlink: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +100010303 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010304 }
10305
10306#ifdef MS_WINDOWS
Jason R. Coombs3a092862013-05-27 23:21:28 -040010307
Larry Hastings9cf065c2012-06-22 16:30:09 -070010308 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010309 if (dst->wide) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010310 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010311 target_is_directory |= _check_dirW(src->wide, dst->wide);
10312 result = Py_CreateSymbolicLinkW(dst->wide, src->wide,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010313 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010314 }
10315 else {
10316 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010317 target_is_directory |= _check_dirA(src->narrow, dst->narrow);
10318 result = Py_CreateSymbolicLinkA(dst->narrow, src->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010319 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010320 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010321 Py_END_ALLOW_THREADS
10322
Larry Hastings2f936352014-08-05 14:04:04 +100010323 if (!result)
10324 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010325
10326#else
10327
10328 Py_BEGIN_ALLOW_THREADS
10329#if HAVE_SYMLINKAT
10330 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010331 result = symlinkat(src->narrow, dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010332 else
10333#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010334 result = symlink(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010335 Py_END_ALLOW_THREADS
10336
Larry Hastings2f936352014-08-05 14:04:04 +100010337 if (result)
10338 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010339#endif
10340
Larry Hastings2f936352014-08-05 14:04:04 +100010341 Py_RETURN_NONE;
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010342}
10343#endif /* HAVE_SYMLINK */
10344
Larry Hastings9cf065c2012-06-22 16:30:09 -070010345
Brian Curtind40e6f72010-07-08 21:39:08 +000010346
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010347
Larry Hastings605a62d2012-06-24 04:33:36 -070010348static PyStructSequence_Field times_result_fields[] = {
10349 {"user", "user time"},
10350 {"system", "system time"},
10351 {"children_user", "user time of children"},
10352 {"children_system", "system time of children"},
10353 {"elapsed", "elapsed time since an arbitrary point in the past"},
10354 {NULL}
10355};
10356
10357PyDoc_STRVAR(times_result__doc__,
10358"times_result: Result from os.times().\n\n\
10359This object may be accessed either as a tuple of\n\
10360 (user, system, children_user, children_system, elapsed),\n\
10361or via the attributes user, system, children_user, children_system,\n\
10362and elapsed.\n\
10363\n\
10364See os.times for more information.");
10365
10366static PyStructSequence_Desc times_result_desc = {
10367 "times_result", /* name */
10368 times_result__doc__, /* doc */
10369 times_result_fields,
10370 5
10371};
10372
10373static PyTypeObject TimesResultType;
10374
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010375#ifdef MS_WINDOWS
10376#define HAVE_TIMES /* mandatory, for the method table */
10377#endif
Larry Hastings605a62d2012-06-24 04:33:36 -070010378
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010379#ifdef HAVE_TIMES
Larry Hastings605a62d2012-06-24 04:33:36 -070010380
10381static PyObject *
10382build_times_result(double user, double system,
10383 double children_user, double children_system,
10384 double elapsed)
10385{
10386 PyObject *value = PyStructSequence_New(&TimesResultType);
10387 if (value == NULL)
10388 return NULL;
10389
10390#define SET(i, field) \
10391 { \
10392 PyObject *o = PyFloat_FromDouble(field); \
10393 if (!o) { \
10394 Py_DECREF(value); \
10395 return NULL; \
10396 } \
10397 PyStructSequence_SET_ITEM(value, i, o); \
10398 } \
10399
10400 SET(0, user);
10401 SET(1, system);
10402 SET(2, children_user);
10403 SET(3, children_system);
10404 SET(4, elapsed);
10405
10406#undef SET
10407
10408 return value;
10409}
10410
Larry Hastings605a62d2012-06-24 04:33:36 -070010411
Larry Hastings2f936352014-08-05 14:04:04 +100010412#ifndef MS_WINDOWS
10413#define NEED_TICKS_PER_SECOND
10414static long ticks_per_second = -1;
10415#endif /* MS_WINDOWS */
10416
10417/*[clinic input]
10418os.times
10419
10420Return a collection containing process timing information.
10421
10422The object returned behaves like a named tuple with these fields:
10423 (utime, stime, cutime, cstime, elapsed_time)
10424All fields are floating point numbers.
10425[clinic start generated code]*/
10426
10427PyDoc_STRVAR(os_times__doc__,
10428"times($module, /)\n"
10429"--\n"
10430"\n"
10431"Return a collection containing process timing information.\n"
10432"\n"
10433"The object returned behaves like a named tuple with these fields:\n"
10434" (utime, stime, cutime, cstime, elapsed_time)\n"
10435"All fields are floating point numbers.");
10436
10437#define OS_TIMES_METHODDEF \
10438 {"times", (PyCFunction)os_times, METH_NOARGS, os_times__doc__},
10439
Barry Warsaw53699e91996-12-10 23:23:01 +000010440static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010441os_times_impl(PyModuleDef *module);
10442
10443static PyObject *
10444os_times(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10445{
10446 return os_times_impl(module);
10447}
10448
10449static PyObject *
10450os_times_impl(PyModuleDef *module)
10451/*[clinic end generated code: output=b86896d031a9b768 input=2bf9df3d6ab2e48b]*/
10452#ifdef MS_WINDOWS
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010453{
Victor Stinner8c62be82010-05-06 00:08:46 +000010454 FILETIME create, exit, kernel, user;
10455 HANDLE hProc;
10456 hProc = GetCurrentProcess();
10457 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
10458 /* The fields of a FILETIME structure are the hi and lo part
10459 of a 64-bit value expressed in 100 nanosecond units.
10460 1e7 is one second in such units; 1e-7 the inverse.
10461 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
10462 */
Larry Hastings605a62d2012-06-24 04:33:36 -070010463 return build_times_result(
Victor Stinner8c62be82010-05-06 00:08:46 +000010464 (double)(user.dwHighDateTime*429.4967296 +
10465 user.dwLowDateTime*1e-7),
10466 (double)(kernel.dwHighDateTime*429.4967296 +
10467 kernel.dwLowDateTime*1e-7),
10468 (double)0,
10469 (double)0,
10470 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010471}
Larry Hastings2f936352014-08-05 14:04:04 +100010472#else /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010473{
Larry Hastings2f936352014-08-05 14:04:04 +100010474
10475
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010476 struct tms t;
10477 clock_t c;
10478 errno = 0;
10479 c = times(&t);
10480 if (c == (clock_t) -1)
10481 return posix_error();
10482 return build_times_result(
10483 (double)t.tms_utime / ticks_per_second,
10484 (double)t.tms_stime / ticks_per_second,
10485 (double)t.tms_cutime / ticks_per_second,
10486 (double)t.tms_cstime / ticks_per_second,
10487 (double)c / ticks_per_second);
10488}
Larry Hastings2f936352014-08-05 14:04:04 +100010489#endif /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010490#endif /* HAVE_TIMES */
10491
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010492
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010493#ifdef HAVE_GETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010494/*[clinic input]
10495os.getsid
10496
10497 pid: pid_t
10498 /
10499
10500Call the system call getsid(pid) and return the result.
10501[clinic start generated code]*/
10502
10503PyDoc_STRVAR(os_getsid__doc__,
10504"getsid($module, pid, /)\n"
10505"--\n"
10506"\n"
10507"Call the system call getsid(pid) and return the result.");
10508
10509#define OS_GETSID_METHODDEF \
10510 {"getsid", (PyCFunction)os_getsid, METH_VARARGS, os_getsid__doc__},
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010511
10512static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010513os_getsid_impl(PyModuleDef *module, pid_t pid);
10514
10515static PyObject *
10516os_getsid(PyModuleDef *module, PyObject *args)
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010517{
Larry Hastings2f936352014-08-05 14:04:04 +100010518 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010519 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010520
10521 if (!PyArg_ParseTuple(args,
10522 "" _Py_PARSE_PID ":getsid",
10523 &pid))
10524 goto exit;
10525 return_value = os_getsid_impl(module, pid);
10526
10527exit:
10528 return return_value;
10529}
10530
10531static PyObject *
10532os_getsid_impl(PyModuleDef *module, pid_t pid)
10533/*[clinic end generated code: output=ea8390f395f4e0e1 input=eeb2b923a30ce04e]*/
10534{
Victor Stinner8c62be82010-05-06 00:08:46 +000010535 int sid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010536 sid = getsid(pid);
10537 if (sid < 0)
10538 return posix_error();
10539 return PyLong_FromLong((long)sid);
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010540}
10541#endif /* HAVE_GETSID */
10542
10543
Guido van Rossumb6775db1994-08-01 11:34:53 +000010544#ifdef HAVE_SETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010545/*[clinic input]
10546os.setsid
10547
10548Call the system call setsid().
10549[clinic start generated code]*/
10550
10551PyDoc_STRVAR(os_setsid__doc__,
10552"setsid($module, /)\n"
10553"--\n"
10554"\n"
10555"Call the system call setsid().");
10556
10557#define OS_SETSID_METHODDEF \
10558 {"setsid", (PyCFunction)os_setsid, METH_NOARGS, os_setsid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010559
Barry Warsaw53699e91996-12-10 23:23:01 +000010560static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010561os_setsid_impl(PyModuleDef *module);
10562
10563static PyObject *
10564os_setsid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10565{
10566 return os_setsid_impl(module);
10567}
10568
10569static PyObject *
10570os_setsid_impl(PyModuleDef *module)
10571/*[clinic end generated code: output=2a9a1435d8d764d5 input=5fff45858e2f0776]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +000010572{
Victor Stinner8c62be82010-05-06 00:08:46 +000010573 if (setsid() < 0)
10574 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010575 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010576}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010577#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010578
Larry Hastings2f936352014-08-05 14:04:04 +100010579
Guido van Rossumb6775db1994-08-01 11:34:53 +000010580#ifdef HAVE_SETPGID
Larry Hastings2f936352014-08-05 14:04:04 +100010581/*[clinic input]
10582os.setpgid
10583
10584 pid: pid_t
10585 pgrp: pid_t
10586 /
10587
10588Call the system call setpgid(pid, pgrp).
10589[clinic start generated code]*/
10590
10591PyDoc_STRVAR(os_setpgid__doc__,
10592"setpgid($module, pid, pgrp, /)\n"
10593"--\n"
10594"\n"
10595"Call the system call setpgid(pid, pgrp).");
10596
10597#define OS_SETPGID_METHODDEF \
10598 {"setpgid", (PyCFunction)os_setpgid, METH_VARARGS, os_setpgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010599
Barry Warsaw53699e91996-12-10 23:23:01 +000010600static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010601os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp);
10602
10603static PyObject *
10604os_setpgid(PyModuleDef *module, PyObject *args)
Guido van Rossumc2670a01992-09-13 20:07:29 +000010605{
Larry Hastings2f936352014-08-05 14:04:04 +100010606 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010607 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010608 pid_t pgrp;
10609
10610 if (!PyArg_ParseTuple(args,
10611 "" _Py_PARSE_PID "" _Py_PARSE_PID ":setpgid",
10612 &pid, &pgrp))
10613 goto exit;
10614 return_value = os_setpgid_impl(module, pid, pgrp);
10615
10616exit:
10617 return return_value;
10618}
10619
10620static PyObject *
10621os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp)
10622/*[clinic end generated code: output=7ad79b725f890e1f input=fceb395eca572e1a]*/
10623{
Victor Stinner8c62be82010-05-06 00:08:46 +000010624 if (setpgid(pid, pgrp) < 0)
10625 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010626 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010627}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010628#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010629
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010630
Guido van Rossumb6775db1994-08-01 11:34:53 +000010631#ifdef HAVE_TCGETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010632/*[clinic input]
10633os.tcgetpgrp
10634
10635 fd: int
10636 /
10637
10638Return the process group associated with the terminal specified by fd.
10639[clinic start generated code]*/
10640
10641PyDoc_STRVAR(os_tcgetpgrp__doc__,
10642"tcgetpgrp($module, fd, /)\n"
10643"--\n"
10644"\n"
10645"Return the process group associated with the terminal specified by fd.");
10646
10647#define OS_TCGETPGRP_METHODDEF \
10648 {"tcgetpgrp", (PyCFunction)os_tcgetpgrp, METH_VARARGS, os_tcgetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010649
Barry Warsaw53699e91996-12-10 23:23:01 +000010650static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010651os_tcgetpgrp_impl(PyModuleDef *module, int fd);
10652
10653static PyObject *
10654os_tcgetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010655{
Larry Hastings2f936352014-08-05 14:04:04 +100010656 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010657 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100010658
10659 if (!PyArg_ParseTuple(args,
10660 "i:tcgetpgrp",
10661 &fd))
10662 goto exit;
10663 return_value = os_tcgetpgrp_impl(module, fd);
10664
10665exit:
10666 return return_value;
10667}
10668
10669static PyObject *
10670os_tcgetpgrp_impl(PyModuleDef *module, int fd)
10671/*[clinic end generated code: output=abcf52ed4c8d22cb input=7f6c18eac10ada86]*/
10672{
10673 pid_t pgid = tcgetpgrp(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +000010674 if (pgid < 0)
10675 return posix_error();
10676 return PyLong_FromPid(pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +000010677}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010678#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +000010679
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010680
Guido van Rossumb6775db1994-08-01 11:34:53 +000010681#ifdef HAVE_TCSETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010682/*[clinic input]
10683os.tcsetpgrp
10684
10685 fd: int
10686 pgid: pid_t
10687 /
10688
10689Set the process group associated with the terminal specified by fd.
10690[clinic start generated code]*/
10691
10692PyDoc_STRVAR(os_tcsetpgrp__doc__,
10693"tcsetpgrp($module, fd, pgid, /)\n"
10694"--\n"
10695"\n"
10696"Set the process group associated with the terminal specified by fd.");
10697
10698#define OS_TCSETPGRP_METHODDEF \
10699 {"tcsetpgrp", (PyCFunction)os_tcsetpgrp, METH_VARARGS, os_tcsetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010700
Barry Warsaw53699e91996-12-10 23:23:01 +000010701static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010702os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid);
10703
10704static PyObject *
10705os_tcsetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010706{
Larry Hastings2f936352014-08-05 14:04:04 +100010707 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010708 int fd;
10709 pid_t pgid;
Larry Hastings2f936352014-08-05 14:04:04 +100010710
10711 if (!PyArg_ParseTuple(args,
10712 "i" _Py_PARSE_PID ":tcsetpgrp",
10713 &fd, &pgid))
10714 goto exit;
10715 return_value = os_tcsetpgrp_impl(module, fd, pgid);
10716
10717exit:
10718 return return_value;
10719}
10720
10721static PyObject *
10722os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid)
10723/*[clinic end generated code: output=76f9bb8fd00f20f5 input=5bdc997c6a619020]*/
10724{
Victor Stinner8c62be82010-05-06 00:08:46 +000010725 if (tcsetpgrp(fd, pgid) < 0)
10726 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010727 Py_RETURN_NONE;
Guido van Rossum7066dd71992-09-17 17:54:56 +000010728}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010729#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +000010730
Guido van Rossum687dd131993-05-17 08:34:16 +000010731/* Functions acting on file descriptors */
10732
Victor Stinnerdaf45552013-08-28 00:53:59 +020010733#ifdef O_CLOEXEC
10734extern int _Py_open_cloexec_works;
10735#endif
10736
Larry Hastings2f936352014-08-05 14:04:04 +100010737
10738/*[clinic input]
10739os.open -> int
10740 path: path_t
10741 flags: int
10742 mode: int = 0o777
10743 *
10744 dir_fd: dir_fd(requires='openat') = None
10745
10746# "open(path, flags, mode=0o777, *, dir_fd=None)\n\n\
10747
10748Open a file for low level IO. Returns a file descriptor (integer).
10749
10750If dir_fd is not None, it should be a file descriptor open to a directory,
10751 and path should be relative; path will then be relative to that directory.
10752dir_fd may not be implemented on your platform.
10753 If it is unavailable, using it will raise a NotImplementedError.
10754[clinic start generated code]*/
10755
10756PyDoc_STRVAR(os_open__doc__,
10757"open($module, /, path, flags, mode=511, *, dir_fd=None)\n"
10758"--\n"
10759"\n"
10760"Open a file for low level IO. Returns a file descriptor (integer).\n"
10761"\n"
10762"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10763" and path should be relative; path will then be relative to that directory.\n"
10764"dir_fd may not be implemented on your platform.\n"
10765" If it is unavailable, using it will raise a NotImplementedError.");
10766
10767#define OS_OPEN_METHODDEF \
10768 {"open", (PyCFunction)os_open, METH_VARARGS|METH_KEYWORDS, os_open__doc__},
10769
10770static int
10771os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010772
Barry Warsaw53699e91996-12-10 23:23:01 +000010773static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010774os_open(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000010775{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010776 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100010777 static char *_keywords[] = {"path", "flags", "mode", "dir_fd", NULL};
10778 path_t path = PATH_T_INITIALIZE("open", "path", 0, 0);
10779 int flags;
10780 int mode = 511;
10781 int dir_fd = DEFAULT_DIR_FD;
10782 int _return_value;
10783
10784 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10785 "O&i|i$O&:open", _keywords,
10786 path_converter, &path, &flags, &mode, OPENAT_DIR_FD_CONVERTER, &dir_fd))
10787 goto exit;
10788 _return_value = os_open_impl(module, &path, flags, mode, dir_fd);
10789 if ((_return_value == -1) && PyErr_Occurred())
10790 goto exit;
10791 return_value = PyLong_FromLong((long)_return_value);
10792
10793exit:
10794 /* Cleanup for path */
10795 path_cleanup(&path);
10796
10797 return return_value;
10798}
10799
10800static int
10801os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd)
10802/*[clinic end generated code: output=05b68fc4ed5e29c9 input=ad8623b29acd2934]*/
10803{
10804 int fd;
10805
Victor Stinnerdaf45552013-08-28 00:53:59 +020010806#ifdef O_CLOEXEC
10807 int *atomic_flag_works = &_Py_open_cloexec_works;
10808#elif !defined(MS_WINDOWS)
10809 int *atomic_flag_works = NULL;
10810#endif
Mark Hammondc2e85bd2002-10-03 05:10:39 +000010811
Victor Stinnerdaf45552013-08-28 00:53:59 +020010812#ifdef MS_WINDOWS
10813 flags |= O_NOINHERIT;
10814#elif defined(O_CLOEXEC)
10815 flags |= O_CLOEXEC;
10816#endif
10817
Victor Stinner8c62be82010-05-06 00:08:46 +000010818 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -070010819#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100010820 if (path->wide)
10821 fd = _wopen(path->wide, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010822 else
10823#endif
10824#ifdef HAVE_OPENAT
10825 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010826 fd = openat(dir_fd, path->narrow, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010827 else
10828#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010829 fd = open(path->narrow, flags, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +000010830 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +000010831
Larry Hastings9cf065c2012-06-22 16:30:09 -070010832 if (fd == -1) {
Larry Hastings2f936352014-08-05 14:04:04 +100010833 PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
10834 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010835 }
10836
Victor Stinnerdaf45552013-08-28 00:53:59 +020010837#ifndef MS_WINDOWS
10838 if (_Py_set_inheritable(fd, 0, atomic_flag_works) < 0) {
10839 close(fd);
Larry Hastings2f936352014-08-05 14:04:04 +100010840 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020010841 }
10842#endif
10843
Larry Hastings2f936352014-08-05 14:04:04 +100010844 return fd;
10845}
10846
10847
10848/*[clinic input]
10849os.close
10850
10851 fd: int
10852
10853Close a file descriptor.
10854[clinic start generated code]*/
10855
10856PyDoc_STRVAR(os_close__doc__,
10857"close($module, /, fd)\n"
10858"--\n"
10859"\n"
10860"Close a file descriptor.");
10861
10862#define OS_CLOSE_METHODDEF \
10863 {"close", (PyCFunction)os_close, METH_VARARGS|METH_KEYWORDS, os_close__doc__},
10864
10865static PyObject *
10866os_close_impl(PyModuleDef *module, int fd);
10867
10868static PyObject *
10869os_close(PyModuleDef *module, PyObject *args, PyObject *kwargs)
10870{
10871 PyObject *return_value = NULL;
10872 static char *_keywords[] = {"fd", NULL};
10873 int fd;
10874
10875 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10876 "i:close", _keywords,
10877 &fd))
10878 goto exit;
10879 return_value = os_close_impl(module, fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010880
10881exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070010882 return return_value;
10883}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010884
Barry Warsaw53699e91996-12-10 23:23:01 +000010885static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010886os_close_impl(PyModuleDef *module, int fd)
10887/*[clinic end generated code: output=927004e29ad55808 input=2bc42451ca5c3223]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000010888{
Larry Hastings2f936352014-08-05 14:04:04 +100010889 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +000010890 if (!_PyVerify_fd(fd))
10891 return posix_error();
10892 Py_BEGIN_ALLOW_THREADS
10893 res = close(fd);
10894 Py_END_ALLOW_THREADS
10895 if (res < 0)
10896 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010897 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000010898}
10899
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010900
Larry Hastings2f936352014-08-05 14:04:04 +100010901/*[clinic input]
10902os.closerange
10903
10904 fd_low: int
10905 fd_high: int
10906 /
10907
10908Closes all file descriptors in [fd_low, fd_high), ignoring errors.
10909[clinic start generated code]*/
10910
10911PyDoc_STRVAR(os_closerange__doc__,
10912"closerange($module, fd_low, fd_high, /)\n"
10913"--\n"
10914"\n"
10915"Closes all file descriptors in [fd_low, fd_high), ignoring errors.");
10916
10917#define OS_CLOSERANGE_METHODDEF \
10918 {"closerange", (PyCFunction)os_closerange, METH_VARARGS, os_closerange__doc__},
Christian Heimesfdab48e2008-01-20 09:06:41 +000010919
10920static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010921os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high);
10922
10923static PyObject *
10924os_closerange(PyModuleDef *module, PyObject *args)
Christian Heimesfdab48e2008-01-20 09:06:41 +000010925{
Larry Hastings2f936352014-08-05 14:04:04 +100010926 PyObject *return_value = NULL;
10927 int fd_low;
10928 int fd_high;
10929
10930 if (!PyArg_ParseTuple(args,
10931 "ii:closerange",
10932 &fd_low, &fd_high))
10933 goto exit;
10934 return_value = os_closerange_impl(module, fd_low, fd_high);
10935
10936exit:
10937 return return_value;
10938}
10939
10940static PyObject *
10941os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high)
10942/*[clinic end generated code: output=0a929ece386811c3 input=5855a3d053ebd4ec]*/
10943{
10944 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +000010945 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010946 for (i = fd_low; i < fd_high; i++)
Victor Stinner8c62be82010-05-06 00:08:46 +000010947 if (_PyVerify_fd(i))
10948 close(i);
10949 Py_END_ALLOW_THREADS
10950 Py_RETURN_NONE;
Christian Heimesfdab48e2008-01-20 09:06:41 +000010951}
10952
10953
Larry Hastings2f936352014-08-05 14:04:04 +100010954/*[clinic input]
10955os.dup -> int
10956
10957 fd: int
10958 /
10959
10960Return a duplicate of a file descriptor.
10961[clinic start generated code]*/
10962
10963PyDoc_STRVAR(os_dup__doc__,
10964"dup($module, fd, /)\n"
10965"--\n"
10966"\n"
10967"Return a duplicate of a file descriptor.");
10968
10969#define OS_DUP_METHODDEF \
10970 {"dup", (PyCFunction)os_dup, METH_VARARGS, os_dup__doc__},
10971
10972static int
10973os_dup_impl(PyModuleDef *module, int fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010974
Barry Warsaw53699e91996-12-10 23:23:01 +000010975static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010976os_dup(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000010977{
Larry Hastings2f936352014-08-05 14:04:04 +100010978 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010979 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100010980 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020010981
Larry Hastings2f936352014-08-05 14:04:04 +100010982 if (!PyArg_ParseTuple(args,
10983 "i:dup",
10984 &fd))
10985 goto exit;
10986 _return_value = os_dup_impl(module, fd);
10987 if ((_return_value == -1) && PyErr_Occurred())
10988 goto exit;
10989 return_value = PyLong_FromLong((long)_return_value);
Tim Golden23005082013-10-25 11:22:37 +010010990
Larry Hastings2f936352014-08-05 14:04:04 +100010991exit:
10992 return return_value;
10993}
Victor Stinnerdaf45552013-08-28 00:53:59 +020010994
Larry Hastings2f936352014-08-05 14:04:04 +100010995static int
10996os_dup_impl(PyModuleDef *module, int fd)
10997/*[clinic end generated code: output=75943e057b25e1bd input=6f10f7ea97f7852a]*/
10998{
10999 return _Py_dup(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +000011000}
11001
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011002
Larry Hastings2f936352014-08-05 14:04:04 +100011003/*[clinic input]
11004os.dup2
11005 fd: int
11006 fd2: int
11007 inheritable: bool=True
11008
11009Duplicate file descriptor.
11010[clinic start generated code]*/
11011
11012PyDoc_STRVAR(os_dup2__doc__,
11013"dup2($module, /, fd, fd2, inheritable=True)\n"
11014"--\n"
11015"\n"
11016"Duplicate file descriptor.");
11017
11018#define OS_DUP2_METHODDEF \
11019 {"dup2", (PyCFunction)os_dup2, METH_VARARGS|METH_KEYWORDS, os_dup2__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011020
Barry Warsaw53699e91996-12-10 23:23:01 +000011021static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011022os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable);
11023
11024static PyObject *
11025os_dup2(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011026{
Larry Hastings2f936352014-08-05 14:04:04 +100011027 PyObject *return_value = NULL;
11028 static char *_keywords[] = {"fd", "fd2", "inheritable", NULL};
11029 int fd;
11030 int fd2;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011031 int inheritable = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100011032
11033 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11034 "ii|p:dup2", _keywords,
11035 &fd, &fd2, &inheritable))
11036 goto exit;
11037 return_value = os_dup2_impl(module, fd, fd2, inheritable);
11038
11039exit:
11040 return return_value;
11041}
11042
11043static PyObject *
11044os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable)
11045/*[clinic end generated code: output=531e482dd11a99a0 input=76e96f511be0352f]*/
11046{
Victor Stinnerdaf45552013-08-28 00:53:59 +020011047 int res;
11048#if defined(HAVE_DUP3) && \
11049 !(defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC))
11050 /* dup3() is available on Linux 2.6.27+ and glibc 2.9 */
11051 int dup3_works = -1;
11052#endif
11053
Victor Stinner8c62be82010-05-06 00:08:46 +000011054 if (!_PyVerify_fd_dup2(fd, fd2))
11055 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011056
11057#ifdef MS_WINDOWS
11058 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011059 res = dup2(fd, fd2);
Victor Stinnerdaf45552013-08-28 00:53:59 +020011060 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011061 if (res < 0)
11062 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011063
11064 /* Character files like console cannot be make non-inheritable */
11065 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11066 close(fd2);
11067 return NULL;
11068 }
11069
11070#elif defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC)
11071 Py_BEGIN_ALLOW_THREADS
11072 if (!inheritable)
11073 res = fcntl(fd, F_DUP2FD_CLOEXEC, fd2);
11074 else
11075 res = dup2(fd, fd2);
11076 Py_END_ALLOW_THREADS
11077 if (res < 0)
11078 return posix_error();
11079
11080#else
11081
11082#ifdef HAVE_DUP3
11083 if (!inheritable && dup3_works != 0) {
11084 Py_BEGIN_ALLOW_THREADS
11085 res = dup3(fd, fd2, O_CLOEXEC);
11086 Py_END_ALLOW_THREADS
11087 if (res < 0) {
11088 if (dup3_works == -1)
11089 dup3_works = (errno != ENOSYS);
11090 if (dup3_works)
11091 return posix_error();
11092 }
11093 }
11094
11095 if (inheritable || dup3_works == 0)
11096 {
11097#endif
11098 Py_BEGIN_ALLOW_THREADS
11099 res = dup2(fd, fd2);
11100 Py_END_ALLOW_THREADS
11101 if (res < 0)
11102 return posix_error();
11103
11104 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11105 close(fd2);
11106 return NULL;
11107 }
11108#ifdef HAVE_DUP3
11109 }
11110#endif
11111
11112#endif
11113
Larry Hastings2f936352014-08-05 14:04:04 +100011114 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000011115}
11116
Larry Hastings2f936352014-08-05 14:04:04 +100011117
Ross Lagerwall7807c352011-03-17 20:20:30 +020011118#ifdef HAVE_LOCKF
Larry Hastings2f936352014-08-05 14:04:04 +100011119/*[clinic input]
11120os.lockf
11121
11122 fd: int
11123 An open file descriptor.
11124 command: int
11125 One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.
11126 length: Py_off_t
11127 The number of bytes to lock, starting at the current position.
11128 /
11129
11130Apply, test or remove a POSIX lock on an open file descriptor.
11131
11132[clinic start generated code]*/
11133
11134PyDoc_STRVAR(os_lockf__doc__,
11135"lockf($module, fd, command, length, /)\n"
11136"--\n"
11137"\n"
11138"Apply, test or remove a POSIX lock on an open file descriptor.\n"
11139"\n"
11140" fd\n"
11141" An open file descriptor.\n"
11142" command\n"
11143" One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.\n"
11144" length\n"
11145" The number of bytes to lock, starting at the current position.");
11146
11147#define OS_LOCKF_METHODDEF \
11148 {"lockf", (PyCFunction)os_lockf, METH_VARARGS, os_lockf__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011149
11150static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011151os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length);
11152
11153static PyObject *
11154os_lockf(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011155{
Larry Hastings2f936352014-08-05 14:04:04 +100011156 PyObject *return_value = NULL;
11157 int fd;
11158 int command;
11159 Py_off_t length;
11160
11161 if (!PyArg_ParseTuple(args,
11162 "iiO&:lockf",
11163 &fd, &command, Py_off_t_converter, &length))
11164 goto exit;
11165 return_value = os_lockf_impl(module, fd, command, length);
11166
11167exit:
11168 return return_value;
11169}
11170
11171static PyObject *
11172os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length)
11173/*[clinic end generated code: output=1b28346ac7335c0f input=65da41d2106e9b79]*/
11174{
11175 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011176
11177 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011178 res = lockf(fd, command, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011179 Py_END_ALLOW_THREADS
11180
11181 if (res < 0)
11182 return posix_error();
11183
11184 Py_RETURN_NONE;
11185}
Larry Hastings2f936352014-08-05 14:04:04 +100011186#endif /* HAVE_LOCKF */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011187
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011188
Larry Hastings2f936352014-08-05 14:04:04 +100011189/*[clinic input]
11190os.lseek -> Py_off_t
11191
11192 fd: int
11193 position: Py_off_t
11194 how: int
11195 /
11196
11197Set the position of a file descriptor. Return the new position.
11198
11199Return the new cursor position in number of bytes
11200relative to the beginning of the file.
11201[clinic start generated code]*/
11202
11203PyDoc_STRVAR(os_lseek__doc__,
11204"lseek($module, fd, position, how, /)\n"
11205"--\n"
11206"\n"
11207"Set the position of a file descriptor. Return the new position.\n"
11208"\n"
11209"Return the new cursor position in number of bytes\n"
11210"relative to the beginning of the file.");
11211
11212#define OS_LSEEK_METHODDEF \
11213 {"lseek", (PyCFunction)os_lseek, METH_VARARGS, os_lseek__doc__},
11214
11215static Py_off_t
11216os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011217
Barry Warsaw53699e91996-12-10 23:23:01 +000011218static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011219os_lseek(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011220{
Larry Hastings2f936352014-08-05 14:04:04 +100011221 PyObject *return_value = NULL;
11222 int fd;
11223 Py_off_t position;
11224 int how;
11225 Py_off_t _return_value;
11226
11227 if (!PyArg_ParseTuple(args,
11228 "iO&i:lseek",
11229 &fd, Py_off_t_converter, &position, &how))
11230 goto exit;
11231 _return_value = os_lseek_impl(module, fd, position, how);
11232 if ((_return_value == -1) && PyErr_Occurred())
11233 goto exit;
11234 return_value = PyLong_FromPy_off_t(_return_value);
11235
11236exit:
11237 return return_value;
11238}
11239
11240static Py_off_t
11241os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how)
11242/*[clinic end generated code: output=88cfc146f55667af input=902654ad3f96a6d3]*/
11243{
11244 Py_off_t result;
11245
11246 if (!_PyVerify_fd(fd)) {
11247 posix_error();
11248 return -1;
11249 }
Guido van Rossum687dd131993-05-17 08:34:16 +000011250#ifdef SEEK_SET
Victor Stinner8c62be82010-05-06 00:08:46 +000011251 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
11252 switch (how) {
Larry Hastings2f936352014-08-05 14:04:04 +100011253 case 0: how = SEEK_SET; break;
11254 case 1: how = SEEK_CUR; break;
11255 case 2: how = SEEK_END; break;
Victor Stinner8c62be82010-05-06 00:08:46 +000011256 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000011257#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +000011258
Victor Stinner8c62be82010-05-06 00:08:46 +000011259 if (PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100011260 return -1;
Guido van Rossum94f6f721999-01-06 18:42:14 +000011261
Larry Hastings2f936352014-08-05 14:04:04 +100011262 if (!_PyVerify_fd(fd)) {
11263 posix_error();
11264 return -1;
11265 }
Victor Stinner8c62be82010-05-06 00:08:46 +000011266 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011267#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100011268 result = _lseeki64(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011269#else
Larry Hastings2f936352014-08-05 14:04:04 +100011270 result = lseek(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011271#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011272 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011273 if (result < 0)
11274 posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +000011275
Larry Hastings2f936352014-08-05 14:04:04 +100011276 return result;
Guido van Rossum687dd131993-05-17 08:34:16 +000011277}
11278
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011279
Larry Hastings2f936352014-08-05 14:04:04 +100011280/*[clinic input]
11281os.read
11282 fd: int
11283 length: Py_ssize_t
11284 /
11285
11286Read from a file descriptor. Returns a bytes object.
11287[clinic start generated code]*/
11288
11289PyDoc_STRVAR(os_read__doc__,
11290"read($module, fd, length, /)\n"
11291"--\n"
11292"\n"
11293"Read from a file descriptor. Returns a bytes object.");
11294
11295#define OS_READ_METHODDEF \
11296 {"read", (PyCFunction)os_read, METH_VARARGS, os_read__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011297
Barry Warsaw53699e91996-12-10 23:23:01 +000011298static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011299os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length);
11300
11301static PyObject *
11302os_read(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011303{
Larry Hastings2f936352014-08-05 14:04:04 +100011304 PyObject *return_value = NULL;
Victor Stinnerb28ed922014-07-11 17:04:41 +020011305 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011306 Py_ssize_t length;
11307
11308 if (!PyArg_ParseTuple(args,
11309 "in:read",
11310 &fd, &length))
11311 goto exit;
11312 return_value = os_read_impl(module, fd, length);
11313
11314exit:
11315 return return_value;
11316}
11317
11318static PyObject *
11319os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length)
11320/*[clinic end generated code: output=1f3bc27260a24968 input=1df2eaa27c0bf1d3]*/
11321{
Victor Stinner8c62be82010-05-06 00:08:46 +000011322 Py_ssize_t n;
11323 PyObject *buffer;
Larry Hastings2f936352014-08-05 14:04:04 +100011324
11325 if (length < 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +000011326 errno = EINVAL;
11327 return posix_error();
11328 }
Larry Hastings2f936352014-08-05 14:04:04 +100011329 if (!_PyVerify_fd(fd))
11330 return posix_error();
11331
11332#ifdef MS_WINDOWS
11333 #define READ_CAST (int)
11334 if (length > INT_MAX)
11335 length = INT_MAX;
11336#else
11337 #define READ_CAST
11338#endif
11339
11340 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011341 if (buffer == NULL)
11342 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011343 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011344 n = read(fd, PyBytes_AS_STRING(buffer), READ_CAST length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011345 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011346
Victor Stinner8c62be82010-05-06 00:08:46 +000011347 if (n < 0) {
11348 Py_DECREF(buffer);
11349 return posix_error();
11350 }
Larry Hastings2f936352014-08-05 14:04:04 +100011351
11352 if (n != length)
Victor Stinner8c62be82010-05-06 00:08:46 +000011353 _PyBytes_Resize(&buffer, n);
Larry Hastings2f936352014-08-05 14:04:04 +100011354
Victor Stinner8c62be82010-05-06 00:08:46 +000011355 return buffer;
Guido van Rossum687dd131993-05-17 08:34:16 +000011356}
11357
Ross Lagerwall7807c352011-03-17 20:20:30 +020011358#if (defined(HAVE_SENDFILE) && (defined(__FreeBSD__) || defined(__DragonFly__) \
11359 || defined(__APPLE__))) || defined(HAVE_READV) || defined(HAVE_WRITEV)
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011360static Py_ssize_t
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011361iov_setup(struct iovec **iov, Py_buffer **buf, PyObject *seq, int cnt, int type)
11362{
11363 int i, j;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011364 Py_ssize_t blen, total = 0;
11365
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011366 *iov = PyMem_New(struct iovec, cnt);
11367 if (*iov == NULL) {
11368 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011369 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011370 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011371
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011372 *buf = PyMem_New(Py_buffer, cnt);
11373 if (*buf == NULL) {
11374 PyMem_Del(*iov);
11375 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011376 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011377 }
11378
11379 for (i = 0; i < cnt; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011380 PyObject *item = PySequence_GetItem(seq, i);
11381 if (item == NULL)
11382 goto fail;
11383 if (PyObject_GetBuffer(item, &(*buf)[i], type) == -1) {
11384 Py_DECREF(item);
11385 goto fail;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011386 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011387 Py_DECREF(item);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011388 (*iov)[i].iov_base = (*buf)[i].buf;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011389 blen = (*buf)[i].len;
11390 (*iov)[i].iov_len = blen;
11391 total += blen;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011392 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011393 return total;
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011394
11395fail:
11396 PyMem_Del(*iov);
11397 for (j = 0; j < i; j++) {
11398 PyBuffer_Release(&(*buf)[j]);
11399 }
11400 PyMem_Del(*buf);
Victor Stinner57ddf782014-01-08 15:21:28 +010011401 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011402}
11403
11404static void
11405iov_cleanup(struct iovec *iov, Py_buffer *buf, int cnt)
11406{
11407 int i;
11408 PyMem_Del(iov);
11409 for (i = 0; i < cnt; i++) {
11410 PyBuffer_Release(&buf[i]);
11411 }
11412 PyMem_Del(buf);
11413}
11414#endif
11415
Larry Hastings2f936352014-08-05 14:04:04 +100011416
Ross Lagerwall7807c352011-03-17 20:20:30 +020011417#ifdef HAVE_READV
Larry Hastings2f936352014-08-05 14:04:04 +100011418/*[clinic input]
11419os.readv -> Py_ssize_t
11420
11421 fd: int
11422 buffers: object
11423 /
11424
11425Read from a file descriptor fd into an iterable of buffers.
11426
11427The buffers should be mutable buffers accepting bytes.
11428readv will transfer data into each buffer until it is full
11429and then move on to the next buffer in the sequence to hold
11430the rest of the data.
11431
11432readv returns the total number of bytes read,
11433which may be less than the total capacity of all the buffers.
11434[clinic start generated code]*/
11435
11436PyDoc_STRVAR(os_readv__doc__,
11437"readv($module, fd, buffers, /)\n"
11438"--\n"
11439"\n"
11440"Read from a file descriptor fd into an iterable of buffers.\n"
11441"\n"
11442"The buffers should be mutable buffers accepting bytes.\n"
11443"readv will transfer data into each buffer until it is full\n"
11444"and then move on to the next buffer in the sequence to hold\n"
11445"the rest of the data.\n"
11446"\n"
11447"readv returns the total number of bytes read,\n"
11448"which may be less than the total capacity of all the buffers.");
11449
11450#define OS_READV_METHODDEF \
11451 {"readv", (PyCFunction)os_readv, METH_VARARGS, os_readv__doc__},
11452
11453static Py_ssize_t
11454os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011455
11456static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011457os_readv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011458{
Larry Hastings2f936352014-08-05 14:04:04 +100011459 PyObject *return_value = NULL;
11460 int fd;
11461 PyObject *buffers;
11462 Py_ssize_t _return_value;
11463
11464 if (!PyArg_ParseTuple(args,
11465 "iO:readv",
11466 &fd, &buffers))
11467 goto exit;
11468 _return_value = os_readv_impl(module, fd, buffers);
11469 if ((_return_value == -1) && PyErr_Occurred())
11470 goto exit;
11471 return_value = PyLong_FromSsize_t(_return_value);
11472
11473exit:
11474 return return_value;
11475}
11476
11477static Py_ssize_t
11478os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers)
11479/*[clinic end generated code: output=72748b1c32a6e2a1 input=e679eb5dbfa0357d]*/
11480{
11481 int cnt;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011482 Py_ssize_t n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011483 struct iovec *iov;
11484 Py_buffer *buf;
11485
Larry Hastings2f936352014-08-05 14:04:04 +100011486 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011487 PyErr_SetString(PyExc_TypeError,
11488 "readv() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100011489 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011490 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020011491
Larry Hastings2f936352014-08-05 14:04:04 +100011492 cnt = PySequence_Size(buffers);
11493
11494 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_WRITABLE) < 0)
11495 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011496
11497 Py_BEGIN_ALLOW_THREADS
11498 n = readv(fd, iov, cnt);
11499 Py_END_ALLOW_THREADS
11500
11501 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100011502 if (n < 0) {
11503 posix_error();
11504 return -1;
11505 }
Victor Stinner57ddf782014-01-08 15:21:28 +010011506
Larry Hastings2f936352014-08-05 14:04:04 +100011507 return n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011508}
Larry Hastings2f936352014-08-05 14:04:04 +100011509#endif /* HAVE_READV */
11510
Ross Lagerwall7807c352011-03-17 20:20:30 +020011511
11512#ifdef HAVE_PREAD
Larry Hastings2f936352014-08-05 14:04:04 +100011513/*[clinic input]
11514# TODO length should be size_t! but Python doesn't support parsing size_t yet.
11515os.pread
11516
11517 fd: int
11518 length: int
11519 offset: Py_off_t
11520 /
11521
11522Read a number of bytes from a file descriptor starting at a particular offset.
11523
11524Read length bytes from file descriptor fd, starting at offset bytes from
11525the beginning of the file. The file offset remains unchanged.
11526[clinic start generated code]*/
11527
11528PyDoc_STRVAR(os_pread__doc__,
11529"pread($module, fd, length, offset, /)\n"
11530"--\n"
11531"\n"
11532"Read a number of bytes from a file descriptor starting at a particular offset.\n"
11533"\n"
11534"Read length bytes from file descriptor fd, starting at offset bytes from\n"
11535"the beginning of the file. The file offset remains unchanged.");
11536
11537#define OS_PREAD_METHODDEF \
11538 {"pread", (PyCFunction)os_pread, METH_VARARGS, os_pread__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011539
11540static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011541os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset);
11542
11543static PyObject *
11544os_pread(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011545{
Larry Hastings2f936352014-08-05 14:04:04 +100011546 PyObject *return_value = NULL;
11547 int fd;
11548 int length;
11549 Py_off_t offset;
11550
11551 if (!PyArg_ParseTuple(args,
11552 "iiO&:pread",
11553 &fd, &length, Py_off_t_converter, &offset))
11554 goto exit;
11555 return_value = os_pread_impl(module, fd, length, offset);
11556
11557exit:
11558 return return_value;
11559}
11560
11561static PyObject *
11562os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset)
11563/*[clinic end generated code: output=7b62bf6c06e20ae8 input=084948dcbaa35d4c]*/
11564{
Ross Lagerwall7807c352011-03-17 20:20:30 +020011565 Py_ssize_t n;
11566 PyObject *buffer;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011567
Larry Hastings2f936352014-08-05 14:04:04 +100011568 if (length < 0) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011569 errno = EINVAL;
11570 return posix_error();
11571 }
Larry Hastings2f936352014-08-05 14:04:04 +100011572 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011573 if (buffer == NULL)
11574 return NULL;
11575 if (!_PyVerify_fd(fd)) {
11576 Py_DECREF(buffer);
11577 return posix_error();
11578 }
11579 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011580 n = pread(fd, PyBytes_AS_STRING(buffer), length, offset);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011581 Py_END_ALLOW_THREADS
11582 if (n < 0) {
11583 Py_DECREF(buffer);
11584 return posix_error();
11585 }
Larry Hastings2f936352014-08-05 14:04:04 +100011586 if (n != length)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011587 _PyBytes_Resize(&buffer, n);
11588 return buffer;
11589}
Larry Hastings2f936352014-08-05 14:04:04 +100011590#endif /* HAVE_PREAD */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011591
Larry Hastings2f936352014-08-05 14:04:04 +100011592
11593/*[clinic input]
11594os.write -> Py_ssize_t
11595
11596 fd: int
11597 data: Py_buffer
11598 /
11599
11600Write a bytes object to a file descriptor.
11601[clinic start generated code]*/
11602
11603PyDoc_STRVAR(os_write__doc__,
11604"write($module, fd, data, /)\n"
11605"--\n"
11606"\n"
11607"Write a bytes object to a file descriptor.");
11608
11609#define OS_WRITE_METHODDEF \
11610 {"write", (PyCFunction)os_write, METH_VARARGS, os_write__doc__},
11611
11612static Py_ssize_t
11613os_write_impl(PyModuleDef *module, int fd, Py_buffer *data);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011614
11615static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011616os_write(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011617{
Larry Hastings2f936352014-08-05 14:04:04 +100011618 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011619 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011620 Py_buffer data = {NULL, NULL};
11621 Py_ssize_t _return_value;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011622
Larry Hastings2f936352014-08-05 14:04:04 +100011623 if (!PyArg_ParseTuple(args,
11624 "iy*:write",
11625 &fd, &data))
11626 goto exit;
11627 _return_value = os_write_impl(module, fd, &data);
11628 if ((_return_value == -1) && PyErr_Occurred())
11629 goto exit;
11630 return_value = PyLong_FromSsize_t(_return_value);
11631
11632exit:
11633 /* Cleanup for data */
11634 if (data.obj)
11635 PyBuffer_Release(&data);
11636
11637 return return_value;
11638}
11639
11640static Py_ssize_t
11641os_write_impl(PyModuleDef *module, int fd, Py_buffer *data)
11642/*[clinic end generated code: output=aeb96acfdd4d5112 input=3207e28963234f3c]*/
11643{
11644 Py_ssize_t size;
11645 Py_ssize_t len = data->len;
11646
Ross Lagerwall7807c352011-03-17 20:20:30 +020011647 if (!_PyVerify_fd(fd)) {
Larry Hastings2f936352014-08-05 14:04:04 +100011648 posix_error();
11649 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011650 }
Larry Hastings2f936352014-08-05 14:04:04 +100011651
Ross Lagerwall7807c352011-03-17 20:20:30 +020011652 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011653#ifdef MS_WINDOWS
Ross Lagerwall7807c352011-03-17 20:20:30 +020011654 if (len > INT_MAX)
11655 len = INT_MAX;
Larry Hastings2f936352014-08-05 14:04:04 +100011656 size = write(fd, data->buf, (int)len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011657#else
Larry Hastings2f936352014-08-05 14:04:04 +100011658 size = write(fd, data->buf, len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011659#endif
11660 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011661 if (size < 0) {
11662 posix_error();
11663 return -1;
11664 }
11665 return size;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011666}
11667
11668#ifdef HAVE_SENDFILE
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011669PyDoc_STRVAR(posix_sendfile__doc__,
11670"sendfile(out, in, offset, nbytes) -> byteswritten\n\
11671sendfile(out, in, offset, nbytes, headers=None, trailers=None, flags=0)\n\
11672 -> byteswritten\n\
11673Copy nbytes bytes from file descriptor in to file descriptor out.");
11674
Larry Hastings2f936352014-08-05 14:04:04 +100011675/* AC 3.5: don't bother converting, has optional group*/
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011676static PyObject *
11677posix_sendfile(PyObject *self, PyObject *args, PyObject *kwdict)
11678{
11679 int in, out;
11680 Py_ssize_t ret;
11681 off_t offset;
11682
11683#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
11684#ifndef __APPLE__
11685 Py_ssize_t len;
11686#endif
11687 PyObject *headers = NULL, *trailers = NULL;
11688 Py_buffer *hbuf, *tbuf;
11689 off_t sbytes;
11690 struct sf_hdtr sf;
11691 int flags = 0;
Benjamin Petersond8a43b42011-02-26 21:35:16 +000011692 static char *keywords[] = {"out", "in",
11693 "offset", "count",
11694 "headers", "trailers", "flags", NULL};
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011695
Victor Stinner6ce0dbf2013-07-07 16:32:36 +020011696 sf.headers = NULL;
11697 sf.trailers = NULL;
11698
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011699#ifdef __APPLE__
11700 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&O&|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011701 keywords, &out, &in, Py_off_t_converter, &offset, Py_off_t_converter, &sbytes,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011702#else
11703 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&n|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011704 keywords, &out, &in, Py_off_t_converter, &offset, &len,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011705#endif
11706 &headers, &trailers, &flags))
11707 return NULL;
11708 if (headers != NULL) {
11709 if (!PySequence_Check(headers)) {
11710 PyErr_SetString(PyExc_TypeError,
11711 "sendfile() headers must be a sequence or None");
11712 return NULL;
11713 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011714 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011715 sf.hdr_cnt = PySequence_Size(headers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011716 if (sf.hdr_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011717 (i = iov_setup(&(sf.headers), &hbuf,
11718 headers, sf.hdr_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011719 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011720#ifdef __APPLE__
11721 sbytes += i;
11722#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011723 }
11724 }
11725 if (trailers != NULL) {
11726 if (!PySequence_Check(trailers)) {
11727 PyErr_SetString(PyExc_TypeError,
11728 "sendfile() trailers must be a sequence or None");
11729 return NULL;
11730 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011731 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011732 sf.trl_cnt = PySequence_Size(trailers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011733 if (sf.trl_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011734 (i = iov_setup(&(sf.trailers), &tbuf,
11735 trailers, sf.trl_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011736 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011737#ifdef __APPLE__
11738 sbytes += i;
11739#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011740 }
11741 }
11742
11743 Py_BEGIN_ALLOW_THREADS
11744#ifdef __APPLE__
11745 ret = sendfile(in, out, offset, &sbytes, &sf, flags);
11746#else
11747 ret = sendfile(in, out, offset, len, &sf, &sbytes, flags);
11748#endif
11749 Py_END_ALLOW_THREADS
11750
11751 if (sf.headers != NULL)
11752 iov_cleanup(sf.headers, hbuf, sf.hdr_cnt);
11753 if (sf.trailers != NULL)
11754 iov_cleanup(sf.trailers, tbuf, sf.trl_cnt);
11755
11756 if (ret < 0) {
11757 if ((errno == EAGAIN) || (errno == EBUSY)) {
11758 if (sbytes != 0) {
11759 // some data has been sent
11760 goto done;
11761 }
11762 else {
11763 // no data has been sent; upper application is supposed
11764 // to retry on EAGAIN or EBUSY
11765 return posix_error();
11766 }
11767 }
11768 return posix_error();
11769 }
11770 goto done;
11771
11772done:
11773 #if !defined(HAVE_LARGEFILE_SUPPORT)
11774 return Py_BuildValue("l", sbytes);
11775 #else
11776 return Py_BuildValue("L", sbytes);
11777 #endif
11778
11779#else
11780 Py_ssize_t count;
11781 PyObject *offobj;
11782 static char *keywords[] = {"out", "in",
11783 "offset", "count", NULL};
11784 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiOn:sendfile",
11785 keywords, &out, &in, &offobj, &count))
11786 return NULL;
11787#ifdef linux
11788 if (offobj == Py_None) {
11789 Py_BEGIN_ALLOW_THREADS
11790 ret = sendfile(out, in, NULL, count);
11791 Py_END_ALLOW_THREADS
11792 if (ret < 0)
11793 return posix_error();
Giampaolo Rodola'ff1a7352011-04-19 09:47:16 +020011794 return Py_BuildValue("n", ret);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011795 }
11796#endif
Larry Hastings2f936352014-08-05 14:04:04 +100011797 if (!Py_off_t_converter(offobj, &offset))
Antoine Pitroudcc20b82011-02-26 13:38:35 +000011798 return NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011799 Py_BEGIN_ALLOW_THREADS
11800 ret = sendfile(out, in, &offset, count);
11801 Py_END_ALLOW_THREADS
11802 if (ret < 0)
11803 return posix_error();
11804 return Py_BuildValue("n", ret);
11805#endif
11806}
Larry Hastings2f936352014-08-05 14:04:04 +100011807#endif /* HAVE_SENDFILE */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011808
Larry Hastings2f936352014-08-05 14:04:04 +100011809
11810/*[clinic input]
11811os.fstat
11812
11813 fd : int
11814
11815Perform a stat system call on the given file descriptor.
11816
11817Like stat(), but for an open file descriptor.
11818Equivalent to os.stat(fd).
11819[clinic start generated code]*/
11820
11821PyDoc_STRVAR(os_fstat__doc__,
11822"fstat($module, /, fd)\n"
11823"--\n"
11824"\n"
11825"Perform a stat system call on the given file descriptor.\n"
11826"\n"
11827"Like stat(), but for an open file descriptor.\n"
11828"Equivalent to os.stat(fd).");
11829
11830#define OS_FSTAT_METHODDEF \
11831 {"fstat", (PyCFunction)os_fstat, METH_VARARGS|METH_KEYWORDS, os_fstat__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011832
Barry Warsaw53699e91996-12-10 23:23:01 +000011833static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011834os_fstat_impl(PyModuleDef *module, int fd);
11835
11836static PyObject *
11837os_fstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011838{
Larry Hastings2f936352014-08-05 14:04:04 +100011839 PyObject *return_value = NULL;
11840 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000011841 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011842
11843 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11844 "i:fstat", _keywords,
11845 &fd))
11846 goto exit;
11847 return_value = os_fstat_impl(module, fd);
11848
11849exit:
11850 return return_value;
11851}
11852
11853static PyObject *
11854os_fstat_impl(PyModuleDef *module, int fd)
11855/*[clinic end generated code: output=dae4a9678c7bd881 input=27e0e0ebbe5600c9]*/
11856{
Victor Stinner8c62be82010-05-06 00:08:46 +000011857 STRUCT_STAT st;
11858 int res;
Larry Hastings2f936352014-08-05 14:04:04 +100011859
Victor Stinner8c62be82010-05-06 00:08:46 +000011860 Py_BEGIN_ALLOW_THREADS
11861 res = FSTAT(fd, &st);
11862 Py_END_ALLOW_THREADS
11863 if (res != 0) {
Martin v. Löwis14694662006-02-03 12:54:16 +000011864#ifdef MS_WINDOWS
Victor Stinnerb024e842012-10-31 22:24:06 +010011865 return PyErr_SetFromWindowsErr(0);
Martin v. Löwis14694662006-02-03 12:54:16 +000011866#else
Victor Stinner8c62be82010-05-06 00:08:46 +000011867 return posix_error();
Martin v. Löwis14694662006-02-03 12:54:16 +000011868#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011869 }
Tim Peters5aa91602002-01-30 05:46:57 +000011870
Victor Stinner4195b5c2012-02-08 23:03:19 +010011871 return _pystat_fromstructstat(&st);
Guido van Rossum687dd131993-05-17 08:34:16 +000011872}
11873
Larry Hastings2f936352014-08-05 14:04:04 +100011874
11875/*[clinic input]
11876os.isatty -> bool
11877 fd: int
11878 /
11879
11880Return True if the fd is connected to a terminal.
11881
11882Return True if the file descriptor is an open file descriptor
11883connected to the slave end of a terminal.
11884[clinic start generated code]*/
11885
11886PyDoc_STRVAR(os_isatty__doc__,
11887"isatty($module, fd, /)\n"
11888"--\n"
11889"\n"
11890"Return True if the fd is connected to a terminal.\n"
11891"\n"
11892"Return True if the file descriptor is an open file descriptor\n"
11893"connected to the slave end of a terminal.");
11894
11895#define OS_ISATTY_METHODDEF \
11896 {"isatty", (PyCFunction)os_isatty, METH_VARARGS, os_isatty__doc__},
11897
11898static int
11899os_isatty_impl(PyModuleDef *module, int fd);
Skip Montanaro1517d842000-07-19 14:34:14 +000011900
11901static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011902os_isatty(PyModuleDef *module, PyObject *args)
Skip Montanaro1517d842000-07-19 14:34:14 +000011903{
Larry Hastings2f936352014-08-05 14:04:04 +100011904 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011905 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011906 int _return_value;
11907
11908 if (!PyArg_ParseTuple(args,
11909 "i:isatty",
11910 &fd))
11911 goto exit;
11912 _return_value = os_isatty_impl(module, fd);
11913 if ((_return_value == -1) && PyErr_Occurred())
11914 goto exit;
11915 return_value = PyBool_FromLong((long)_return_value);
11916
11917exit:
11918 return return_value;
Skip Montanaro1517d842000-07-19 14:34:14 +000011919}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011920
Larry Hastings2f936352014-08-05 14:04:04 +100011921static int
11922os_isatty_impl(PyModuleDef *module, int fd)
11923/*[clinic end generated code: output=4bfadbfe22715097 input=08ce94aa1eaf7b5e]*/
11924{
11925 if (!_PyVerify_fd(fd))
11926 return 0;
11927 return isatty(fd);
11928}
11929
11930
Guido van Rossuma4916fa1996-05-23 22:58:55 +000011931#ifdef HAVE_PIPE
Larry Hastings2f936352014-08-05 14:04:04 +100011932/*[clinic input]
11933os.pipe
11934
11935Create a pipe.
11936
11937Returns a tuple of two file descriptors:
11938 (read_fd, write_fd)
11939[clinic start generated code]*/
11940
11941PyDoc_STRVAR(os_pipe__doc__,
11942"pipe($module, /)\n"
11943"--\n"
11944"\n"
11945"Create a pipe.\n"
11946"\n"
11947"Returns a tuple of two file descriptors:\n"
11948" (read_fd, write_fd)");
11949
11950#define OS_PIPE_METHODDEF \
11951 {"pipe", (PyCFunction)os_pipe, METH_NOARGS, os_pipe__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011952
Barry Warsaw53699e91996-12-10 23:23:01 +000011953static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011954os_pipe_impl(PyModuleDef *module);
11955
11956static PyObject *
11957os_pipe(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
11958{
11959 return os_pipe_impl(module);
11960}
11961
11962static PyObject *
11963os_pipe_impl(PyModuleDef *module)
11964/*[clinic end generated code: output=0da2479f2266e774 input=02535e8c8fa6c4d4]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000011965{
Victor Stinner8c62be82010-05-06 00:08:46 +000011966 int fds[2];
Victor Stinnerdaf45552013-08-28 00:53:59 +020011967#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000011968 HANDLE read, write;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011969 SECURITY_ATTRIBUTES attr;
Victor Stinner8c62be82010-05-06 00:08:46 +000011970 BOOL ok;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011971#else
11972 int res;
11973#endif
11974
11975#ifdef MS_WINDOWS
11976 attr.nLength = sizeof(attr);
11977 attr.lpSecurityDescriptor = NULL;
11978 attr.bInheritHandle = FALSE;
11979
11980 Py_BEGIN_ALLOW_THREADS
11981 ok = CreatePipe(&read, &write, &attr, 0);
11982 if (ok) {
11983 fds[0] = _open_osfhandle((Py_intptr_t)read, _O_RDONLY);
11984 fds[1] = _open_osfhandle((Py_intptr_t)write, _O_WRONLY);
11985 if (fds[0] == -1 || fds[1] == -1) {
11986 CloseHandle(read);
11987 CloseHandle(write);
11988 ok = 0;
11989 }
11990 }
11991 Py_END_ALLOW_THREADS
11992
Victor Stinner8c62be82010-05-06 00:08:46 +000011993 if (!ok)
Victor Stinnerb024e842012-10-31 22:24:06 +010011994 return PyErr_SetFromWindowsErr(0);
Victor Stinnerdaf45552013-08-28 00:53:59 +020011995#else
11996
11997#ifdef HAVE_PIPE2
11998 Py_BEGIN_ALLOW_THREADS
11999 res = pipe2(fds, O_CLOEXEC);
12000 Py_END_ALLOW_THREADS
12001
12002 if (res != 0 && errno == ENOSYS)
12003 {
12004#endif
12005 Py_BEGIN_ALLOW_THREADS
12006 res = pipe(fds);
12007 Py_END_ALLOW_THREADS
12008
12009 if (res == 0) {
12010 if (_Py_set_inheritable(fds[0], 0, NULL) < 0) {
12011 close(fds[0]);
12012 close(fds[1]);
12013 return NULL;
12014 }
12015 if (_Py_set_inheritable(fds[1], 0, NULL) < 0) {
12016 close(fds[0]);
12017 close(fds[1]);
12018 return NULL;
12019 }
12020 }
12021#ifdef HAVE_PIPE2
12022 }
12023#endif
12024
12025 if (res != 0)
12026 return PyErr_SetFromErrno(PyExc_OSError);
12027#endif /* !MS_WINDOWS */
12028 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum687dd131993-05-17 08:34:16 +000012029}
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012030#endif /* HAVE_PIPE */
12031
Larry Hastings2f936352014-08-05 14:04:04 +100012032
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012033#ifdef HAVE_PIPE2
Larry Hastings2f936352014-08-05 14:04:04 +100012034/*[clinic input]
12035os.pipe2
12036
12037 flags: int
12038 /
12039
12040Create a pipe with flags set atomically.
12041
12042Returns a tuple of two file descriptors:
12043 (read_fd, write_fd)
12044
12045flags can be constructed by ORing together one or more of these values:
12046O_NONBLOCK, O_CLOEXEC.
12047[clinic start generated code]*/
12048
12049PyDoc_STRVAR(os_pipe2__doc__,
12050"pipe2($module, flags, /)\n"
12051"--\n"
12052"\n"
12053"Create a pipe with flags set atomically.\n"
12054"\n"
12055"Returns a tuple of two file descriptors:\n"
12056" (read_fd, write_fd)\n"
12057"\n"
12058"flags can be constructed by ORing together one or more of these values:\n"
12059"O_NONBLOCK, O_CLOEXEC.");
12060
12061#define OS_PIPE2_METHODDEF \
12062 {"pipe2", (PyCFunction)os_pipe2, METH_VARARGS, os_pipe2__doc__},
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012063
12064static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012065os_pipe2_impl(PyModuleDef *module, int flags);
12066
12067static PyObject *
12068os_pipe2(PyModuleDef *module, PyObject *args)
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012069{
Larry Hastings2f936352014-08-05 14:04:04 +100012070 PyObject *return_value = NULL;
Charles-François Natali368f34b2011-06-06 19:49:47 +020012071 int flags;
Larry Hastings2f936352014-08-05 14:04:04 +100012072
12073 if (!PyArg_ParseTuple(args,
12074 "i:pipe2",
12075 &flags))
12076 goto exit;
12077 return_value = os_pipe2_impl(module, flags);
12078
12079exit:
12080 return return_value;
12081}
12082
12083static PyObject *
12084os_pipe2_impl(PyModuleDef *module, int flags)
12085/*[clinic end generated code: output=9e27c799ce19220b input=f261b6e7e63c6817]*/
12086{
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012087 int fds[2];
12088 int res;
12089
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012090 res = pipe2(fds, flags);
12091 if (res != 0)
12092 return posix_error();
12093 return Py_BuildValue("(ii)", fds[0], fds[1]);
12094}
12095#endif /* HAVE_PIPE2 */
12096
Larry Hastings2f936352014-08-05 14:04:04 +100012097
Ross Lagerwall7807c352011-03-17 20:20:30 +020012098#ifdef HAVE_WRITEV
Larry Hastings2f936352014-08-05 14:04:04 +100012099/*[clinic input]
12100os.writev -> Py_ssize_t
12101 fd: int
12102 buffers: object
12103 /
12104
12105Iterate over buffers, and write the contents of each to a file descriptor.
12106
12107Returns the total number of bytes written.
12108buffers must be a sequence of bytes-like objects.
12109[clinic start generated code]*/
12110
12111PyDoc_STRVAR(os_writev__doc__,
12112"writev($module, fd, buffers, /)\n"
12113"--\n"
12114"\n"
12115"Iterate over buffers, and write the contents of each to a file descriptor.\n"
12116"\n"
12117"Returns the total number of bytes written.\n"
12118"buffers must be a sequence of bytes-like objects.");
12119
12120#define OS_WRITEV_METHODDEF \
12121 {"writev", (PyCFunction)os_writev, METH_VARARGS, os_writev__doc__},
12122
12123static Py_ssize_t
12124os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012125
12126static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012127os_writev(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020012128{
Larry Hastings2f936352014-08-05 14:04:04 +100012129 PyObject *return_value = NULL;
12130 int fd;
12131 PyObject *buffers;
12132 Py_ssize_t _return_value;
12133
12134 if (!PyArg_ParseTuple(args,
12135 "iO:writev",
12136 &fd, &buffers))
12137 goto exit;
12138 _return_value = os_writev_impl(module, fd, buffers);
12139 if ((_return_value == -1) && PyErr_Occurred())
12140 goto exit;
12141 return_value = PyLong_FromSsize_t(_return_value);
12142
12143exit:
12144 return return_value;
12145}
12146
12147static Py_ssize_t
12148os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers)
12149/*[clinic end generated code: output=591c662dccbe4951 input=5b8d17fe4189d2fe]*/
12150{
12151 int cnt;
12152 Py_ssize_t result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012153 struct iovec *iov;
12154 Py_buffer *buf;
Larry Hastings2f936352014-08-05 14:04:04 +100012155
12156 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020012157 PyErr_SetString(PyExc_TypeError,
12158 "writev() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100012159 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012160 }
Larry Hastings2f936352014-08-05 14:04:04 +100012161 cnt = PySequence_Size(buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012162
Larry Hastings2f936352014-08-05 14:04:04 +100012163 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_SIMPLE) < 0) {
12164 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012165 }
12166
12167 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012168 result = writev(fd, iov, cnt);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012169 Py_END_ALLOW_THREADS
12170
12171 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100012172 if (result < 0)
12173 posix_error();
Victor Stinner57ddf782014-01-08 15:21:28 +010012174
Georg Brandl306336b2012-06-24 12:55:33 +020012175 return result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012176}
Larry Hastings2f936352014-08-05 14:04:04 +100012177#endif /* HAVE_WRITEV */
12178
12179
12180#ifdef HAVE_PWRITE
12181/*[clinic input]
12182os.pwrite -> Py_ssize_t
12183
12184 fd: int
12185 buffer: Py_buffer
12186 offset: Py_off_t
12187 /
12188
12189Write bytes to a file descriptor starting at a particular offset.
12190
12191Write buffer to fd, starting at offset bytes from the beginning of
12192the file. Returns the number of bytes writte. Does not change the
12193current file offset.
12194[clinic start generated code]*/
12195
12196PyDoc_STRVAR(os_pwrite__doc__,
12197"pwrite($module, fd, buffer, offset, /)\n"
12198"--\n"
12199"\n"
12200"Write bytes to a file descriptor starting at a particular offset.\n"
12201"\n"
12202"Write buffer to fd, starting at offset bytes from the beginning of\n"
12203"the file. Returns the number of bytes writte. Does not change the\n"
12204"current file offset.");
12205
12206#define OS_PWRITE_METHODDEF \
12207 {"pwrite", (PyCFunction)os_pwrite, METH_VARARGS, os_pwrite__doc__},
12208
12209static Py_ssize_t
12210os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset);
12211
12212static PyObject *
12213os_pwrite(PyModuleDef *module, PyObject *args)
12214{
12215 PyObject *return_value = NULL;
12216 int fd;
12217 Py_buffer buffer = {NULL, NULL};
12218 Py_off_t offset;
12219 Py_ssize_t _return_value;
12220
12221 if (!PyArg_ParseTuple(args,
12222 "iy*O&:pwrite",
12223 &fd, &buffer, Py_off_t_converter, &offset))
12224 goto exit;
12225 _return_value = os_pwrite_impl(module, fd, &buffer, offset);
12226 if ((_return_value == -1) && PyErr_Occurred())
12227 goto exit;
12228 return_value = PyLong_FromSsize_t(_return_value);
12229
12230exit:
12231 /* Cleanup for buffer */
12232 if (buffer.obj)
12233 PyBuffer_Release(&buffer);
12234
12235 return return_value;
12236}
12237
12238static Py_ssize_t
12239os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset)
12240/*[clinic end generated code: output=ec9cc5b2238e96a7 input=19903f1b3dd26377]*/
12241{
12242 Py_ssize_t size;
12243
12244 if (!_PyVerify_fd(fd)) {
12245 posix_error();
12246 return -1;
12247 }
12248
12249 Py_BEGIN_ALLOW_THREADS
12250 size = pwrite(fd, buffer->buf, (size_t)buffer->len, offset);
12251 Py_END_ALLOW_THREADS
12252
12253 if (size < 0)
12254 posix_error();
12255 return size;
12256}
12257#endif /* HAVE_PWRITE */
12258
12259
12260#ifdef HAVE_MKFIFO
12261/*[clinic input]
12262os.mkfifo
12263
12264 path: path_t
12265 mode: int=0o666
12266 *
12267 dir_fd: dir_fd(requires='mkfifoat')=None
12268
12269Create a "fifo" (a POSIX named pipe).
12270
12271If dir_fd is not None, it should be a file descriptor open to a directory,
12272 and path should be relative; path will then be relative to that directory.
12273dir_fd may not be implemented on your platform.
12274 If it is unavailable, using it will raise a NotImplementedError.
12275[clinic start generated code]*/
12276
12277PyDoc_STRVAR(os_mkfifo__doc__,
12278"mkfifo($module, /, path, mode=438, *, dir_fd=None)\n"
12279"--\n"
12280"\n"
12281"Create a \"fifo\" (a POSIX named pipe).\n"
12282"\n"
12283"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12284" and path should be relative; path will then be relative to that directory.\n"
12285"dir_fd may not be implemented on your platform.\n"
12286" If it is unavailable, using it will raise a NotImplementedError.");
12287
12288#define OS_MKFIFO_METHODDEF \
12289 {"mkfifo", (PyCFunction)os_mkfifo, METH_VARARGS|METH_KEYWORDS, os_mkfifo__doc__},
12290
12291static PyObject *
12292os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
12293
12294static PyObject *
12295os_mkfifo(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12296{
12297 PyObject *return_value = NULL;
12298 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
12299 path_t path = PATH_T_INITIALIZE("mkfifo", "path", 0, 0);
12300 int mode = 438;
12301 int dir_fd = DEFAULT_DIR_FD;
12302
12303 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12304 "O&|i$O&:mkfifo", _keywords,
12305 path_converter, &path, &mode, MKFIFOAT_DIR_FD_CONVERTER, &dir_fd))
12306 goto exit;
12307 return_value = os_mkfifo_impl(module, &path, mode, dir_fd);
12308
12309exit:
12310 /* Cleanup for path */
12311 path_cleanup(&path);
12312
12313 return return_value;
12314}
12315
12316static PyObject *
12317os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
12318/*[clinic end generated code: output=b3321927546893d0 input=73032e98a36e0e19]*/
12319{
12320 int result;
12321
12322 Py_BEGIN_ALLOW_THREADS
12323#ifdef HAVE_MKFIFOAT
12324 if (dir_fd != DEFAULT_DIR_FD)
12325 result = mkfifoat(dir_fd, path->narrow, mode);
12326 else
Ross Lagerwall7807c352011-03-17 20:20:30 +020012327#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012328 result = mkfifo(path->narrow, mode);
12329 Py_END_ALLOW_THREADS
12330
12331 if (result < 0)
12332 return posix_error();
12333
12334 Py_RETURN_NONE;
12335}
12336#endif /* HAVE_MKFIFO */
12337
12338
12339#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
12340/*[clinic input]
12341os.mknod
12342
12343 path: path_t
12344 mode: int=0o600
12345 device: int=0
12346 *
12347 dir_fd: dir_fd(requires='mknodat')=None
12348
12349Create a node in the file system.
12350
12351Create a node in the file system (file, device special file or named pipe)
12352at path. mode specifies both the permissions to use and the
12353type of node to be created, being combined (bitwise OR) with one of
12354S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,
12355device defines the newly created device special file (probably using
12356os.makedev()). Otherwise device is ignored.
12357
12358If dir_fd is not None, it should be a file descriptor open to a directory,
12359 and path should be relative; path will then be relative to that directory.
12360dir_fd may not be implemented on your platform.
12361 If it is unavailable, using it will raise a NotImplementedError.
12362[clinic start generated code]*/
12363
12364PyDoc_STRVAR(os_mknod__doc__,
12365"mknod($module, /, path, mode=384, device=0, *, dir_fd=None)\n"
12366"--\n"
12367"\n"
12368"Create a node in the file system.\n"
12369"\n"
12370"Create a node in the file system (file, device special file or named pipe)\n"
12371"at path. mode specifies both the permissions to use and the\n"
12372"type of node to be created, being combined (bitwise OR) with one of\n"
12373"S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,\n"
12374"device defines the newly created device special file (probably using\n"
12375"os.makedev()). Otherwise device is ignored.\n"
12376"\n"
12377"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12378" and path should be relative; path will then be relative to that directory.\n"
12379"dir_fd may not be implemented on your platform.\n"
12380" If it is unavailable, using it will raise a NotImplementedError.");
12381
12382#define OS_MKNOD_METHODDEF \
12383 {"mknod", (PyCFunction)os_mknod, METH_VARARGS|METH_KEYWORDS, os_mknod__doc__},
12384
12385static PyObject *
12386os_mknod_impl(PyModuleDef *module, path_t *path, int mode, int device, int dir_fd);
12387
12388static PyObject *
12389os_mknod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12390{
12391 PyObject *return_value = NULL;
12392 static char *_keywords[] = {"path", "mode", "device", "dir_fd", NULL};
12393 path_t path = PATH_T_INITIALIZE("mknod", "path", 0, 0);
12394 int mode = 384;
12395 int device = 0;
12396 int dir_fd = DEFAULT_DIR_FD;
12397
12398 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12399 "O&|ii$O&:mknod", _keywords,
12400 path_converter, &path, &mode, &device, MKNODAT_DIR_FD_CONVERTER, &dir_fd))
12401 goto exit;
12402 return_value = os_mknod_impl(module, &path, mode, device, dir_fd);
12403
12404exit:
12405 /* Cleanup for path */
12406 path_cleanup(&path);
12407
12408 return return_value;
12409}
12410
12411static PyObject *
12412os_mknod_impl(PyModuleDef *module, path_t *path, int mode, int device, int dir_fd)
12413/*[clinic end generated code: output=c688739c15ca7bbb input=30e02126aba9732e]*/
12414{
12415 int result;
12416
12417 Py_BEGIN_ALLOW_THREADS
12418#ifdef HAVE_MKNODAT
12419 if (dir_fd != DEFAULT_DIR_FD)
12420 result = mknodat(dir_fd, path->narrow, mode, device);
12421 else
12422#endif
12423 result = mknod(path->narrow, mode, device);
12424 Py_END_ALLOW_THREADS
12425
12426 if (result < 0)
12427 return posix_error();
12428
12429 Py_RETURN_NONE;
12430}
12431#endif /* defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV) */
12432
12433
12434#ifdef HAVE_DEVICE_MACROS
12435/*[clinic input]
12436os.major -> unsigned_int
12437
12438 device: int
12439 /
12440
12441Extracts a device major number from a raw device number.
12442[clinic start generated code]*/
12443
12444PyDoc_STRVAR(os_major__doc__,
12445"major($module, device, /)\n"
12446"--\n"
12447"\n"
12448"Extracts a device major number from a raw device number.");
12449
12450#define OS_MAJOR_METHODDEF \
12451 {"major", (PyCFunction)os_major, METH_VARARGS, os_major__doc__},
12452
12453static unsigned int
12454os_major_impl(PyModuleDef *module, int device);
12455
12456static PyObject *
12457os_major(PyModuleDef *module, PyObject *args)
12458{
12459 PyObject *return_value = NULL;
12460 int device;
12461 unsigned int _return_value;
12462
12463 if (!PyArg_ParseTuple(args,
12464 "i:major",
12465 &device))
12466 goto exit;
12467 _return_value = os_major_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012468 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012469 goto exit;
12470 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12471
12472exit:
12473 return return_value;
12474}
12475
12476static unsigned int
12477os_major_impl(PyModuleDef *module, int device)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012478/*[clinic end generated code: output=52e6743300dcf4ad input=ea48820b7e10d310]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012479{
12480 return major(device);
12481}
12482
12483
12484/*[clinic input]
12485os.minor -> unsigned_int
12486
12487 device: int
12488 /
12489
12490Extracts a device minor number from a raw device number.
12491[clinic start generated code]*/
12492
12493PyDoc_STRVAR(os_minor__doc__,
12494"minor($module, device, /)\n"
12495"--\n"
12496"\n"
12497"Extracts a device minor number from a raw device number.");
12498
12499#define OS_MINOR_METHODDEF \
12500 {"minor", (PyCFunction)os_minor, METH_VARARGS, os_minor__doc__},
12501
12502static unsigned int
12503os_minor_impl(PyModuleDef *module, int device);
12504
12505static PyObject *
12506os_minor(PyModuleDef *module, PyObject *args)
12507{
12508 PyObject *return_value = NULL;
12509 int device;
12510 unsigned int _return_value;
12511
12512 if (!PyArg_ParseTuple(args,
12513 "i:minor",
12514 &device))
12515 goto exit;
12516 _return_value = os_minor_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012517 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012518 goto exit;
12519 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12520
12521exit:
12522 return return_value;
12523}
12524
12525static unsigned int
12526os_minor_impl(PyModuleDef *module, int device)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012527/*[clinic end generated code: output=aebe4bd7f455b755 input=089733ebbf9754e8]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012528{
12529 return minor(device);
12530}
12531
12532
12533/*[clinic input]
12534os.makedev -> unsigned_int
12535
12536 major: int
12537 minor: int
12538 /
12539
12540Composes a raw device number from the major and minor device numbers.
12541[clinic start generated code]*/
12542
12543PyDoc_STRVAR(os_makedev__doc__,
12544"makedev($module, major, minor, /)\n"
12545"--\n"
12546"\n"
12547"Composes a raw device number from the major and minor device numbers.");
12548
12549#define OS_MAKEDEV_METHODDEF \
12550 {"makedev", (PyCFunction)os_makedev, METH_VARARGS, os_makedev__doc__},
12551
12552static unsigned int
12553os_makedev_impl(PyModuleDef *module, int major, int minor);
12554
12555static PyObject *
12556os_makedev(PyModuleDef *module, PyObject *args)
12557{
12558 PyObject *return_value = NULL;
12559 int major;
12560 int minor;
12561 unsigned int _return_value;
12562
12563 if (!PyArg_ParseTuple(args,
12564 "ii:makedev",
12565 &major, &minor))
12566 goto exit;
12567 _return_value = os_makedev_impl(module, major, minor);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012568 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012569 goto exit;
12570 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12571
12572exit:
12573 return return_value;
12574}
12575
12576static unsigned int
12577os_makedev_impl(PyModuleDef *module, int major, int minor)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012578/*[clinic end generated code: output=5cb79d9c9eac58b0 input=f55bf7cffb028a08]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012579{
12580 return makedev(major, minor);
12581}
12582#endif /* HAVE_DEVICE_MACROS */
12583
12584
12585#ifdef HAVE_FTRUNCATE
12586/*[clinic input]
12587os.ftruncate
12588
12589 fd: int
12590 length: Py_off_t
12591 /
12592
12593Truncate a file, specified by file descriptor, to a specific length.
12594[clinic start generated code]*/
12595
12596PyDoc_STRVAR(os_ftruncate__doc__,
12597"ftruncate($module, fd, length, /)\n"
12598"--\n"
12599"\n"
12600"Truncate a file, specified by file descriptor, to a specific length.");
12601
12602#define OS_FTRUNCATE_METHODDEF \
12603 {"ftruncate", (PyCFunction)os_ftruncate, METH_VARARGS, os_ftruncate__doc__},
12604
12605static PyObject *
12606os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length);
12607
12608static PyObject *
12609os_ftruncate(PyModuleDef *module, PyObject *args)
12610{
12611 PyObject *return_value = NULL;
12612 int fd;
12613 Py_off_t length;
12614
12615 if (!PyArg_ParseTuple(args,
12616 "iO&:ftruncate",
12617 &fd, Py_off_t_converter, &length))
12618 goto exit;
12619 return_value = os_ftruncate_impl(module, fd, length);
12620
12621exit:
12622 return return_value;
12623}
12624
12625static PyObject *
12626os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length)
12627/*[clinic end generated code: output=62326766cb9b76bf input=63b43641e52818f2]*/
12628{
12629 int result;
12630
12631 Py_BEGIN_ALLOW_THREADS
12632 result = ftruncate(fd, length);
12633 Py_END_ALLOW_THREADS
12634 if (result < 0)
12635 return posix_error();
12636 Py_RETURN_NONE;
12637}
12638#endif /* HAVE_FTRUNCATE */
12639
12640
12641#ifdef HAVE_TRUNCATE
12642/*[clinic input]
12643os.truncate
12644 path: path_t(allow_fd='PATH_HAVE_FTRUNCATE')
12645 length: Py_off_t
12646
12647Truncate a file, specified by path, to a specific length.
12648
12649On some platforms, path may also be specified as an open file descriptor.
12650 If this functionality is unavailable, using it raises an exception.
12651[clinic start generated code]*/
12652
12653PyDoc_STRVAR(os_truncate__doc__,
12654"truncate($module, /, path, length)\n"
12655"--\n"
12656"\n"
12657"Truncate a file, specified by path, to a specific length.\n"
12658"\n"
12659"On some platforms, path may also be specified as an open file descriptor.\n"
12660" If this functionality is unavailable, using it raises an exception.");
12661
12662#define OS_TRUNCATE_METHODDEF \
12663 {"truncate", (PyCFunction)os_truncate, METH_VARARGS|METH_KEYWORDS, os_truncate__doc__},
12664
12665static PyObject *
12666os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length);
12667
12668static PyObject *
12669os_truncate(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12670{
12671 PyObject *return_value = NULL;
12672 static char *_keywords[] = {"path", "length", NULL};
12673 path_t path = PATH_T_INITIALIZE("truncate", "path", 0, PATH_HAVE_FTRUNCATE);
12674 Py_off_t length;
12675
12676 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12677 "O&O&:truncate", _keywords,
12678 path_converter, &path, Py_off_t_converter, &length))
12679 goto exit;
12680 return_value = os_truncate_impl(module, &path, length);
12681
12682exit:
12683 /* Cleanup for path */
12684 path_cleanup(&path);
12685
12686 return return_value;
12687}
12688
12689static PyObject *
12690os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length)
12691/*[clinic end generated code: output=6bd76262d2e027c6 input=77229cf0b50a9b77]*/
12692{
12693 int result;
12694
12695 Py_BEGIN_ALLOW_THREADS
12696#ifdef HAVE_FTRUNCATE
12697 if (path->fd != -1)
12698 result = ftruncate(path->fd, length);
12699 else
12700#endif
12701 result = truncate(path->narrow, length);
12702 Py_END_ALLOW_THREADS
12703 if (result < 0)
12704 return path_error(path);
12705
12706 Py_RETURN_NONE;
12707}
12708#endif /* HAVE_TRUNCATE */
12709
Ross Lagerwall7807c352011-03-17 20:20:30 +020012710
12711#ifdef HAVE_POSIX_FALLOCATE
Larry Hastings2f936352014-08-05 14:04:04 +100012712/*[clinic input]
12713os.posix_fallocate
12714
12715 fd: int
12716 offset: Py_off_t
12717 length: Py_off_t
12718 /
12719
12720Ensure a file has allocated at least a particular number of bytes on disk.
12721
12722Ensure that the file specified by fd encompasses a range of bytes
12723starting at offset bytes from the beginning and continuing for length bytes.
12724[clinic start generated code]*/
12725
12726PyDoc_STRVAR(os_posix_fallocate__doc__,
12727"posix_fallocate($module, fd, offset, length, /)\n"
12728"--\n"
12729"\n"
12730"Ensure a file has allocated at least a particular number of bytes on disk.\n"
12731"\n"
12732"Ensure that the file specified by fd encompasses a range of bytes\n"
12733"starting at offset bytes from the beginning and continuing for length bytes.");
12734
12735#define OS_POSIX_FALLOCATE_METHODDEF \
12736 {"posix_fallocate", (PyCFunction)os_posix_fallocate, METH_VARARGS, os_posix_fallocate__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012737
12738static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012739os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012740
Larry Hastings2f936352014-08-05 14:04:04 +100012741static PyObject *
12742os_posix_fallocate(PyModuleDef *module, PyObject *args)
12743{
12744 PyObject *return_value = NULL;
12745 int fd;
12746 Py_off_t offset;
12747 Py_off_t length;
12748
12749 if (!PyArg_ParseTuple(args,
12750 "iO&O&:posix_fallocate",
12751 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length))
12752 goto exit;
12753 return_value = os_posix_fallocate_impl(module, fd, offset, length);
12754
12755exit:
12756 return return_value;
12757}
12758
12759static PyObject *
12760os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length)
12761/*[clinic end generated code: output=0cd702d2065c79db input=d7a2ef0ab2ca52fb]*/
12762{
12763 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012764
12765 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012766 result = posix_fallocate(fd, offset, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012767 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012768 if (result != 0) {
12769 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012770 return posix_error();
12771 }
12772 Py_RETURN_NONE;
12773}
Larry Hastings2f936352014-08-05 14:04:04 +100012774#endif /* HAVE_POSIX_FALLOCATE */
12775
Ross Lagerwall7807c352011-03-17 20:20:30 +020012776
12777#ifdef HAVE_POSIX_FADVISE
Larry Hastings2f936352014-08-05 14:04:04 +100012778/*[clinic input]
12779os.posix_fadvise
12780
12781 fd: int
12782 offset: Py_off_t
12783 length: Py_off_t
12784 advice: int
12785 /
12786
12787Announce an intention to access data in a specific pattern.
12788
12789Announce an intention to access data in a specific pattern, thus allowing
12790the kernel to make optimizations.
12791The advice applies to the region of the file specified by fd starting at
12792offset and continuing for length bytes.
12793advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,
12794POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or
12795POSIX_FADV_DONTNEED.
12796[clinic start generated code]*/
12797
12798PyDoc_STRVAR(os_posix_fadvise__doc__,
12799"posix_fadvise($module, fd, offset, length, advice, /)\n"
12800"--\n"
12801"\n"
12802"Announce an intention to access data in a specific pattern.\n"
12803"\n"
12804"Announce an intention to access data in a specific pattern, thus allowing\n"
12805"the kernel to make optimizations.\n"
12806"The advice applies to the region of the file specified by fd starting at\n"
12807"offset and continuing for length bytes.\n"
12808"advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,\n"
12809"POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or\n"
12810"POSIX_FADV_DONTNEED.");
12811
12812#define OS_POSIX_FADVISE_METHODDEF \
12813 {"posix_fadvise", (PyCFunction)os_posix_fadvise, METH_VARARGS, os_posix_fadvise__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012814
12815static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012816os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012817
Larry Hastings2f936352014-08-05 14:04:04 +100012818static PyObject *
12819os_posix_fadvise(PyModuleDef *module, PyObject *args)
12820{
12821 PyObject *return_value = NULL;
12822 int fd;
12823 Py_off_t offset;
12824 Py_off_t length;
12825 int advice;
12826
12827 if (!PyArg_ParseTuple(args,
12828 "iO&O&i:posix_fadvise",
12829 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length, &advice))
12830 goto exit;
12831 return_value = os_posix_fadvise_impl(module, fd, offset, length, advice);
12832
12833exit:
12834 return return_value;
12835}
12836
12837static PyObject *
12838os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice)
12839/*[clinic end generated code: output=dad93f32c04dd4f7 input=0fbe554edc2f04b5]*/
12840{
12841 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012842
12843 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012844 result = posix_fadvise(fd, offset, length, advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012845 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012846 if (result != 0) {
12847 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012848 return posix_error();
12849 }
12850 Py_RETURN_NONE;
12851}
Larry Hastings2f936352014-08-05 14:04:04 +100012852#endif /* HAVE_POSIX_FADVISE */
Ross Lagerwall7807c352011-03-17 20:20:30 +020012853
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012854#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000012855
Fred Drake762e2061999-08-26 17:23:54 +000012856/* Save putenv() parameters as values here, so we can collect them when they
12857 * get re-set with another call for the same key. */
12858static PyObject *posix_putenv_garbage;
12859
Larry Hastings2f936352014-08-05 14:04:04 +100012860static void
12861posix_putenv_garbage_setitem(PyObject *name, PyObject *value)
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012862{
Larry Hastings2f936352014-08-05 14:04:04 +100012863 /* Install the first arg and newstr in posix_putenv_garbage;
12864 * this will cause previous value to be collected. This has to
12865 * happen after the real putenv() call because the old value
12866 * was still accessible until then. */
12867 if (PyDict_SetItem(posix_putenv_garbage, name, value))
12868 /* really not much we can do; just leak */
12869 PyErr_Clear();
12870 else
12871 Py_DECREF(value);
12872}
12873
12874
Thomas Hellerf78f12a2007-11-08 19:33:05 +000012875#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100012876/*[clinic input]
12877os.putenv
12878
12879 name: unicode
12880 value: unicode
12881 /
12882
12883Change or add an environment variable.
12884[clinic start generated code]*/
12885
12886PyDoc_STRVAR(os_putenv__doc__,
12887"putenv($module, name, value, /)\n"
12888"--\n"
12889"\n"
12890"Change or add an environment variable.");
12891
12892#define OS_PUTENV_METHODDEF \
12893 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
12894
12895static PyObject *
12896os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
12897
12898static PyObject *
12899os_putenv(PyModuleDef *module, PyObject *args)
12900{
12901 PyObject *return_value = NULL;
12902 PyObject *name;
12903 PyObject *value;
Victor Stinner65170952011-11-22 22:16:17 +010012904
Victor Stinner8c62be82010-05-06 00:08:46 +000012905 if (!PyArg_ParseTuple(args,
Larry Hastings2f936352014-08-05 14:04:04 +100012906 "UU:putenv",
12907 &name, &value))
12908 goto exit;
12909 return_value = os_putenv_impl(module, name, value);
Guido van Rossumd48f2521997-12-05 22:19:34 +000012910
Larry Hastings2f936352014-08-05 14:04:04 +100012911exit:
12912 return return_value;
12913}
12914
12915static PyObject *
12916os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
12917/*[clinic end generated code: output=5ce9ef9b15606e7e input=ba586581c2e6105f]*/
12918{
12919 wchar_t *env;
12920
12921 PyObject *unicode = PyUnicode_FromFormat("%U=%U", name, value);
12922 if (unicode == NULL) {
Victor Stinner84ae1182010-05-06 22:05:07 +000012923 PyErr_NoMemory();
Larry Hastings2f936352014-08-05 14:04:04 +100012924 return NULL;
Victor Stinner84ae1182010-05-06 22:05:07 +000012925 }
Larry Hastings2f936352014-08-05 14:04:04 +100012926 if (_MAX_ENV < PyUnicode_GET_LENGTH(unicode)) {
Victor Stinner65170952011-11-22 22:16:17 +010012927 PyErr_Format(PyExc_ValueError,
12928 "the environment variable is longer than %u characters",
12929 _MAX_ENV);
12930 goto error;
12931 }
12932
Larry Hastings2f936352014-08-05 14:04:04 +100012933 env = PyUnicode_AsUnicode(unicode);
12934 if (env == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +020012935 goto error;
Larry Hastings2f936352014-08-05 14:04:04 +100012936 if (_wputenv(env)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000012937 posix_error();
Victor Stinner84ae1182010-05-06 22:05:07 +000012938 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +000012939 }
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012940
Larry Hastings2f936352014-08-05 14:04:04 +100012941 posix_putenv_garbage_setitem(name, unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012942 Py_RETURN_NONE;
12943
12944error:
Larry Hastings2f936352014-08-05 14:04:04 +100012945 Py_DECREF(unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012946 return NULL;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012947}
Larry Hastings2f936352014-08-05 14:04:04 +100012948#else /* MS_WINDOWS */
12949/*[clinic input]
12950os.putenv
Guido van Rossumb6a47161997-09-15 22:54:34 +000012951
Larry Hastings2f936352014-08-05 14:04:04 +100012952 name: FSConverter
12953 value: FSConverter
12954 /
12955
12956Change or add an environment variable.
12957[clinic start generated code]*/
12958
12959PyDoc_STRVAR(os_putenv__doc__,
12960"putenv($module, name, value, /)\n"
12961"--\n"
12962"\n"
12963"Change or add an environment variable.");
12964
12965#define OS_PUTENV_METHODDEF \
12966 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
Guido van Rossumc524d952001-10-19 01:31:59 +000012967
12968static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012969os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
12970
12971static PyObject *
12972os_putenv(PyModuleDef *module, PyObject *args)
Guido van Rossumc524d952001-10-19 01:31:59 +000012973{
Larry Hastings2f936352014-08-05 14:04:04 +100012974 PyObject *return_value = NULL;
12975 PyObject *name = NULL;
12976 PyObject *value = NULL;
12977
12978 if (!PyArg_ParseTuple(args,
12979 "O&O&:putenv",
12980 PyUnicode_FSConverter, &name, PyUnicode_FSConverter, &value))
12981 goto exit;
12982 return_value = os_putenv_impl(module, name, value);
12983
12984exit:
12985 /* Cleanup for name */
12986 Py_XDECREF(name);
12987 /* Cleanup for value */
12988 Py_XDECREF(value);
12989
12990 return return_value;
12991}
12992
12993static PyObject *
12994os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
12995/*[clinic end generated code: output=85ab223393dc7afd input=a97bc6152f688d31]*/
12996{
12997 PyObject *bytes = NULL;
12998 char *env;
12999 char *name_string = PyBytes_AsString(name);
13000 char *value_string = PyBytes_AsString(value);
13001
13002 bytes = PyBytes_FromFormat("%s=%s", name_string, value_string);
13003 if (bytes == NULL) {
13004 PyErr_NoMemory();
13005 return NULL;
13006 }
13007
13008 env = PyBytes_AS_STRING(bytes);
13009 if (putenv(env)) {
13010 Py_DECREF(bytes);
13011 return posix_error();
13012 }
13013
13014 posix_putenv_garbage_setitem(name, bytes);
13015 Py_RETURN_NONE;
13016}
13017#endif /* MS_WINDOWS */
13018#endif /* HAVE_PUTENV */
13019
13020
13021#ifdef HAVE_UNSETENV
13022/*[clinic input]
13023os.unsetenv
13024 name: FSConverter
13025 /
13026
13027Delete an environment variable.
13028[clinic start generated code]*/
13029
13030PyDoc_STRVAR(os_unsetenv__doc__,
13031"unsetenv($module, name, /)\n"
13032"--\n"
13033"\n"
13034"Delete an environment variable.");
13035
13036#define OS_UNSETENV_METHODDEF \
13037 {"unsetenv", (PyCFunction)os_unsetenv, METH_VARARGS, os_unsetenv__doc__},
13038
13039static PyObject *
13040os_unsetenv_impl(PyModuleDef *module, PyObject *name);
13041
13042static PyObject *
13043os_unsetenv(PyModuleDef *module, PyObject *args)
13044{
13045 PyObject *return_value = NULL;
13046 PyObject *name = NULL;
13047
13048 if (!PyArg_ParseTuple(args,
13049 "O&:unsetenv",
13050 PyUnicode_FSConverter, &name))
13051 goto exit;
13052 return_value = os_unsetenv_impl(module, name);
13053
13054exit:
13055 /* Cleanup for name */
13056 Py_XDECREF(name);
13057
13058 return return_value;
13059}
13060
13061static PyObject *
13062os_unsetenv_impl(PyModuleDef *module, PyObject *name)
13063/*[clinic end generated code: output=91318c995f9a0767 input=2bb5288a599c7107]*/
13064{
Victor Stinner984890f2011-11-24 13:53:38 +010013065#ifndef HAVE_BROKEN_UNSETENV
Victor Stinner60b385e2011-11-22 22:01:28 +010013066 int err;
Victor Stinner984890f2011-11-24 13:53:38 +010013067#endif
Victor Stinner84ae1182010-05-06 22:05:07 +000013068
Victor Stinner984890f2011-11-24 13:53:38 +010013069#ifdef HAVE_BROKEN_UNSETENV
13070 unsetenv(PyBytes_AS_STRING(name));
13071#else
Victor Stinner65170952011-11-22 22:16:17 +010013072 err = unsetenv(PyBytes_AS_STRING(name));
Larry Hastings2f936352014-08-05 14:04:04 +100013073 if (err)
Victor Stinner60b385e2011-11-22 22:01:28 +010013074 return posix_error();
Victor Stinner984890f2011-11-24 13:53:38 +010013075#endif
Guido van Rossumc524d952001-10-19 01:31:59 +000013076
Victor Stinner8c62be82010-05-06 00:08:46 +000013077 /* Remove the key from posix_putenv_garbage;
13078 * this will cause it to be collected. This has to
13079 * happen after the real unsetenv() call because the
13080 * old value was still accessible until then.
13081 */
Victor Stinner65170952011-11-22 22:16:17 +010013082 if (PyDict_DelItem(posix_putenv_garbage, name)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013083 /* really not much we can do; just leak */
13084 PyErr_Clear();
13085 }
Victor Stinner84ae1182010-05-06 22:05:07 +000013086 Py_RETURN_NONE;
Guido van Rossumc524d952001-10-19 01:31:59 +000013087}
Larry Hastings2f936352014-08-05 14:04:04 +100013088#endif /* HAVE_UNSETENV */
Guido van Rossumc524d952001-10-19 01:31:59 +000013089
Larry Hastings2f936352014-08-05 14:04:04 +100013090
13091/*[clinic input]
13092os.strerror
13093
13094 code: int
13095 /
13096
13097Translate an error code to a message string.
13098[clinic start generated code]*/
13099
13100PyDoc_STRVAR(os_strerror__doc__,
13101"strerror($module, code, /)\n"
13102"--\n"
13103"\n"
13104"Translate an error code to a message string.");
13105
13106#define OS_STRERROR_METHODDEF \
13107 {"strerror", (PyCFunction)os_strerror, METH_VARARGS, os_strerror__doc__},
Guido van Rossumb6a47161997-09-15 22:54:34 +000013108
Guido van Rossumf68d8e52001-04-14 17:55:09 +000013109static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013110os_strerror_impl(PyModuleDef *module, int code);
13111
13112static PyObject *
13113os_strerror(PyModuleDef *module, PyObject *args)
Guido van Rossumb6a47161997-09-15 22:54:34 +000013114{
Larry Hastings2f936352014-08-05 14:04:04 +100013115 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013116 int code;
Larry Hastings2f936352014-08-05 14:04:04 +100013117
13118 if (!PyArg_ParseTuple(args,
13119 "i:strerror",
13120 &code))
13121 goto exit;
13122 return_value = os_strerror_impl(module, code);
13123
13124exit:
13125 return return_value;
13126}
13127
13128static PyObject *
13129os_strerror_impl(PyModuleDef *module, int code)
13130/*[clinic end generated code: output=8665c70bb2ca4720 input=75a8673d97915a91]*/
13131{
13132 char *message = strerror(code);
Victor Stinner8c62be82010-05-06 00:08:46 +000013133 if (message == NULL) {
13134 PyErr_SetString(PyExc_ValueError,
13135 "strerror() argument out of range");
13136 return NULL;
13137 }
Victor Stinner1b579672011-12-17 05:47:23 +010013138 return PyUnicode_DecodeLocale(message, "surrogateescape");
Guido van Rossumb6a47161997-09-15 22:54:34 +000013139}
Guido van Rossumb6a47161997-09-15 22:54:34 +000013140
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000013141
Guido van Rossumc9641791998-08-04 15:26:23 +000013142#ifdef HAVE_SYS_WAIT_H
Fred Drake106c1a02002-04-23 15:58:02 +000013143#ifdef WCOREDUMP
Larry Hastings2f936352014-08-05 14:04:04 +100013144/*[clinic input]
13145os.WCOREDUMP -> bool
13146
13147 status: int
13148 /
13149
13150Return True if the process returning status was dumped to a core file.
13151[clinic start generated code]*/
13152
13153PyDoc_STRVAR(os_WCOREDUMP__doc__,
13154"WCOREDUMP($module, status, /)\n"
13155"--\n"
13156"\n"
13157"Return True if the process returning status was dumped to a core file.");
13158
13159#define OS_WCOREDUMP_METHODDEF \
13160 {"WCOREDUMP", (PyCFunction)os_WCOREDUMP, METH_VARARGS, os_WCOREDUMP__doc__},
13161
13162static int
13163os_WCOREDUMP_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013164
13165static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013166os_WCOREDUMP(PyModuleDef *module, PyObject *args)
Fred Drake106c1a02002-04-23 15:58:02 +000013167{
Larry Hastings2f936352014-08-05 14:04:04 +100013168 PyObject *return_value = NULL;
13169 int status;
13170 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013171
Larry Hastings2f936352014-08-05 14:04:04 +100013172 if (!PyArg_ParseTuple(args,
13173 "i:WCOREDUMP",
13174 &status))
13175 goto exit;
13176 _return_value = os_WCOREDUMP_impl(module, status);
13177 if ((_return_value == -1) && PyErr_Occurred())
13178 goto exit;
13179 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013180
Larry Hastings2f936352014-08-05 14:04:04 +100013181exit:
13182 return return_value;
13183}
13184
13185static int
13186os_WCOREDUMP_impl(PyModuleDef *module, int status)
13187/*[clinic end generated code: output=e04d55c09c299828 input=8b05e7ab38528d04]*/
13188{
13189 WAIT_TYPE wait_status;
13190 WAIT_STATUS_INT(wait_status) = status;
13191 return WCOREDUMP(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013192}
13193#endif /* WCOREDUMP */
13194
Larry Hastings2f936352014-08-05 14:04:04 +100013195
Fred Drake106c1a02002-04-23 15:58:02 +000013196#ifdef WIFCONTINUED
Larry Hastings2f936352014-08-05 14:04:04 +100013197/*[clinic input]
13198os.WIFCONTINUED -> bool
13199
13200 status: int
13201
13202Return True if a particular process was continued from a job control stop.
13203
13204Return True if the process returning status was continued from a
13205job control stop.
13206[clinic start generated code]*/
13207
13208PyDoc_STRVAR(os_WIFCONTINUED__doc__,
13209"WIFCONTINUED($module, /, status)\n"
13210"--\n"
13211"\n"
13212"Return True if a particular process was continued from a job control stop.\n"
13213"\n"
13214"Return True if the process returning status was continued from a\n"
13215"job control stop.");
13216
13217#define OS_WIFCONTINUED_METHODDEF \
13218 {"WIFCONTINUED", (PyCFunction)os_WIFCONTINUED, METH_VARARGS|METH_KEYWORDS, os_WIFCONTINUED__doc__},
13219
13220static int
13221os_WIFCONTINUED_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013222
13223static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013224os_WIFCONTINUED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drake106c1a02002-04-23 15:58:02 +000013225{
Larry Hastings2f936352014-08-05 14:04:04 +100013226 PyObject *return_value = NULL;
13227 static char *_keywords[] = {"status", NULL};
13228 int status;
13229 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013230
Larry Hastings2f936352014-08-05 14:04:04 +100013231 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13232 "i:WIFCONTINUED", _keywords,
13233 &status))
13234 goto exit;
13235 _return_value = os_WIFCONTINUED_impl(module, status);
13236 if ((_return_value == -1) && PyErr_Occurred())
13237 goto exit;
13238 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013239
Larry Hastings2f936352014-08-05 14:04:04 +100013240exit:
13241 return return_value;
13242}
13243
13244static int
13245os_WIFCONTINUED_impl(PyModuleDef *module, int status)
13246/*[clinic end generated code: output=9c4e6105a4520ab5 input=e777e7d38eb25bd9]*/
13247{
13248 WAIT_TYPE wait_status;
13249 WAIT_STATUS_INT(wait_status) = status;
13250 return WIFCONTINUED(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013251}
13252#endif /* WIFCONTINUED */
13253
Larry Hastings2f936352014-08-05 14:04:04 +100013254
Guido van Rossumc9641791998-08-04 15:26:23 +000013255#ifdef WIFSTOPPED
Larry Hastings2f936352014-08-05 14:04:04 +100013256/*[clinic input]
13257os.WIFSTOPPED -> bool
13258
13259 status: int
13260
13261Return True if the process returning status was stopped.
13262[clinic start generated code]*/
13263
13264PyDoc_STRVAR(os_WIFSTOPPED__doc__,
13265"WIFSTOPPED($module, /, status)\n"
13266"--\n"
13267"\n"
13268"Return True if the process returning status was stopped.");
13269
13270#define OS_WIFSTOPPED_METHODDEF \
13271 {"WIFSTOPPED", (PyCFunction)os_WIFSTOPPED, METH_VARARGS|METH_KEYWORDS, os_WIFSTOPPED__doc__},
13272
13273static int
13274os_WIFSTOPPED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013275
13276static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013277os_WIFSTOPPED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013278{
Larry Hastings2f936352014-08-05 14:04:04 +100013279 PyObject *return_value = NULL;
13280 static char *_keywords[] = {"status", NULL};
13281 int status;
13282 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013283
Larry Hastings2f936352014-08-05 14:04:04 +100013284 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13285 "i:WIFSTOPPED", _keywords,
13286 &status))
13287 goto exit;
13288 _return_value = os_WIFSTOPPED_impl(module, status);
13289 if ((_return_value == -1) && PyErr_Occurred())
13290 goto exit;
13291 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013292
Larry Hastings2f936352014-08-05 14:04:04 +100013293exit:
13294 return return_value;
13295}
13296
13297static int
13298os_WIFSTOPPED_impl(PyModuleDef *module, int status)
13299/*[clinic end generated code: output=e0de2da8ec9593ff input=043cb7f1289ef904]*/
13300{
13301 WAIT_TYPE wait_status;
13302 WAIT_STATUS_INT(wait_status) = status;
13303 return WIFSTOPPED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013304}
13305#endif /* WIFSTOPPED */
13306
Larry Hastings2f936352014-08-05 14:04:04 +100013307
Guido van Rossumc9641791998-08-04 15:26:23 +000013308#ifdef WIFSIGNALED
Larry Hastings2f936352014-08-05 14:04:04 +100013309/*[clinic input]
13310os.WIFSIGNALED -> bool
13311
13312 status: int
13313
13314Return True if the process returning status was terminated by a signal.
13315[clinic start generated code]*/
13316
13317PyDoc_STRVAR(os_WIFSIGNALED__doc__,
13318"WIFSIGNALED($module, /, status)\n"
13319"--\n"
13320"\n"
13321"Return True if the process returning status was terminated by a signal.");
13322
13323#define OS_WIFSIGNALED_METHODDEF \
13324 {"WIFSIGNALED", (PyCFunction)os_WIFSIGNALED, METH_VARARGS|METH_KEYWORDS, os_WIFSIGNALED__doc__},
13325
13326static int
13327os_WIFSIGNALED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013328
13329static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013330os_WIFSIGNALED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013331{
Larry Hastings2f936352014-08-05 14:04:04 +100013332 PyObject *return_value = NULL;
13333 static char *_keywords[] = {"status", NULL};
13334 int status;
13335 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013336
Larry Hastings2f936352014-08-05 14:04:04 +100013337 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13338 "i:WIFSIGNALED", _keywords,
13339 &status))
13340 goto exit;
13341 _return_value = os_WIFSIGNALED_impl(module, status);
13342 if ((_return_value == -1) && PyErr_Occurred())
13343 goto exit;
13344 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013345
Larry Hastings2f936352014-08-05 14:04:04 +100013346exit:
13347 return return_value;
13348}
13349
13350static int
13351os_WIFSIGNALED_impl(PyModuleDef *module, int status)
13352/*[clinic end generated code: output=f14d106558f406be input=d55ba7cc9ce5dc43]*/
13353{
13354 WAIT_TYPE wait_status;
13355 WAIT_STATUS_INT(wait_status) = status;
13356 return WIFSIGNALED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013357}
13358#endif /* WIFSIGNALED */
13359
Larry Hastings2f936352014-08-05 14:04:04 +100013360
Guido van Rossumc9641791998-08-04 15:26:23 +000013361#ifdef WIFEXITED
Larry Hastings2f936352014-08-05 14:04:04 +100013362/*[clinic input]
13363os.WIFEXITED -> bool
13364
13365 status: int
13366
13367Return True if the process returning status exited via the exit() system call.
13368[clinic start generated code]*/
13369
13370PyDoc_STRVAR(os_WIFEXITED__doc__,
13371"WIFEXITED($module, /, status)\n"
13372"--\n"
13373"\n"
13374"Return True if the process returning status exited via the exit() system call.");
13375
13376#define OS_WIFEXITED_METHODDEF \
13377 {"WIFEXITED", (PyCFunction)os_WIFEXITED, METH_VARARGS|METH_KEYWORDS, os_WIFEXITED__doc__},
13378
13379static int
13380os_WIFEXITED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013381
13382static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013383os_WIFEXITED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013384{
Larry Hastings2f936352014-08-05 14:04:04 +100013385 PyObject *return_value = NULL;
13386 static char *_keywords[] = {"status", NULL};
13387 int status;
13388 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013389
Larry Hastings2f936352014-08-05 14:04:04 +100013390 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13391 "i:WIFEXITED", _keywords,
13392 &status))
13393 goto exit;
13394 _return_value = os_WIFEXITED_impl(module, status);
13395 if ((_return_value == -1) && PyErr_Occurred())
13396 goto exit;
13397 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013398
Larry Hastings2f936352014-08-05 14:04:04 +100013399exit:
13400 return return_value;
13401}
13402
13403static int
13404os_WIFEXITED_impl(PyModuleDef *module, int status)
13405/*[clinic end generated code: output=2f76087d53721255 input=d63775a6791586c0]*/
13406{
13407 WAIT_TYPE wait_status;
13408 WAIT_STATUS_INT(wait_status) = status;
13409 return WIFEXITED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013410}
13411#endif /* WIFEXITED */
13412
Larry Hastings2f936352014-08-05 14:04:04 +100013413
Guido van Rossum54ecc3d1999-01-27 17:53:11 +000013414#ifdef WEXITSTATUS
Larry Hastings2f936352014-08-05 14:04:04 +100013415/*[clinic input]
13416os.WEXITSTATUS -> int
13417
13418 status: int
13419
13420Return the process return code from status.
13421[clinic start generated code]*/
13422
13423PyDoc_STRVAR(os_WEXITSTATUS__doc__,
13424"WEXITSTATUS($module, /, status)\n"
13425"--\n"
13426"\n"
13427"Return the process return code from status.");
13428
13429#define OS_WEXITSTATUS_METHODDEF \
13430 {"WEXITSTATUS", (PyCFunction)os_WEXITSTATUS, METH_VARARGS|METH_KEYWORDS, os_WEXITSTATUS__doc__},
13431
13432static int
13433os_WEXITSTATUS_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013434
13435static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013436os_WEXITSTATUS(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013437{
Larry Hastings2f936352014-08-05 14:04:04 +100013438 PyObject *return_value = NULL;
13439 static char *_keywords[] = {"status", NULL};
13440 int status;
13441 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013442
Larry Hastings2f936352014-08-05 14:04:04 +100013443 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13444 "i:WEXITSTATUS", _keywords,
13445 &status))
13446 goto exit;
13447 _return_value = os_WEXITSTATUS_impl(module, status);
13448 if ((_return_value == -1) && PyErr_Occurred())
13449 goto exit;
13450 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013451
Larry Hastings2f936352014-08-05 14:04:04 +100013452exit:
13453 return return_value;
13454}
13455
13456static int
13457os_WEXITSTATUS_impl(PyModuleDef *module, int status)
13458/*[clinic end generated code: output=13b6c270e2a326b1 input=e1fb4944e377585b]*/
13459{
13460 WAIT_TYPE wait_status;
13461 WAIT_STATUS_INT(wait_status) = status;
13462 return WEXITSTATUS(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013463}
13464#endif /* WEXITSTATUS */
13465
Larry Hastings2f936352014-08-05 14:04:04 +100013466
Guido van Rossumc9641791998-08-04 15:26:23 +000013467#ifdef WTERMSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013468/*[clinic input]
13469os.WTERMSIG -> int
13470
13471 status: int
13472
13473Return the signal that terminated the process that provided the status value.
13474[clinic start generated code]*/
13475
13476PyDoc_STRVAR(os_WTERMSIG__doc__,
13477"WTERMSIG($module, /, status)\n"
13478"--\n"
13479"\n"
13480"Return the signal that terminated the process that provided the status value.");
13481
13482#define OS_WTERMSIG_METHODDEF \
13483 {"WTERMSIG", (PyCFunction)os_WTERMSIG, METH_VARARGS|METH_KEYWORDS, os_WTERMSIG__doc__},
13484
13485static int
13486os_WTERMSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013487
13488static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013489os_WTERMSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013490{
Larry Hastings2f936352014-08-05 14:04:04 +100013491 PyObject *return_value = NULL;
13492 static char *_keywords[] = {"status", NULL};
13493 int status;
13494 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013495
Larry Hastings2f936352014-08-05 14:04:04 +100013496 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13497 "i:WTERMSIG", _keywords,
13498 &status))
13499 goto exit;
13500 _return_value = os_WTERMSIG_impl(module, status);
13501 if ((_return_value == -1) && PyErr_Occurred())
13502 goto exit;
13503 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013504
Larry Hastings2f936352014-08-05 14:04:04 +100013505exit:
13506 return return_value;
13507}
13508
13509static int
13510os_WTERMSIG_impl(PyModuleDef *module, int status)
13511/*[clinic end generated code: output=bf1fd4b002d0a9ed input=727fd7f84ec3f243]*/
13512{
13513 WAIT_TYPE wait_status;
13514 WAIT_STATUS_INT(wait_status) = status;
13515 return WTERMSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013516}
13517#endif /* WTERMSIG */
13518
Larry Hastings2f936352014-08-05 14:04:04 +100013519
Guido van Rossumc9641791998-08-04 15:26:23 +000013520#ifdef WSTOPSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013521/*[clinic input]
13522os.WSTOPSIG -> int
13523
13524 status: int
13525
13526Return the signal that stopped the process that provided the status value.
13527[clinic start generated code]*/
13528
13529PyDoc_STRVAR(os_WSTOPSIG__doc__,
13530"WSTOPSIG($module, /, status)\n"
13531"--\n"
13532"\n"
13533"Return the signal that stopped the process that provided the status value.");
13534
13535#define OS_WSTOPSIG_METHODDEF \
13536 {"WSTOPSIG", (PyCFunction)os_WSTOPSIG, METH_VARARGS|METH_KEYWORDS, os_WSTOPSIG__doc__},
13537
13538static int
13539os_WSTOPSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013540
13541static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013542os_WSTOPSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013543{
Larry Hastings2f936352014-08-05 14:04:04 +100013544 PyObject *return_value = NULL;
13545 static char *_keywords[] = {"status", NULL};
13546 int status;
13547 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013548
Larry Hastings2f936352014-08-05 14:04:04 +100013549 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13550 "i:WSTOPSIG", _keywords,
13551 &status))
13552 goto exit;
13553 _return_value = os_WSTOPSIG_impl(module, status);
13554 if ((_return_value == -1) && PyErr_Occurred())
13555 goto exit;
13556 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013557
Larry Hastings2f936352014-08-05 14:04:04 +100013558exit:
13559 return return_value;
13560}
13561
13562static int
13563os_WSTOPSIG_impl(PyModuleDef *module, int status)
13564/*[clinic end generated code: output=92e1647d29ee0549 input=46ebf1d1b293c5c1]*/
13565{
13566 WAIT_TYPE wait_status;
13567 WAIT_STATUS_INT(wait_status) = status;
13568 return WSTOPSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013569}
13570#endif /* WSTOPSIG */
Guido van Rossumc9641791998-08-04 15:26:23 +000013571#endif /* HAVE_SYS_WAIT_H */
13572
13573
Larry Hastings2f936352014-08-05 14:04:04 +100013574#ifndef OS_WCOREDUMP_METHODDEF
13575#define OS_WCOREDUMP_METHODDEF
13576#endif /* OS_WCOREDUMP_METHODDEF */
13577
13578#ifndef OS_WIFCONTINUED_METHODDEF
13579#define OS_WIFCONTINUED_METHODDEF
13580#endif /* OS_WIFCONTINUED_METHODDEF */
13581
13582#ifndef OS_WIFSTOPPED_METHODDEF
13583#define OS_WIFSTOPPED_METHODDEF
13584#endif /* OS_WIFSTOPPED_METHODDEF */
13585
13586#ifndef OS_WIFSIGNALED_METHODDEF
13587#define OS_WIFSIGNALED_METHODDEF
13588#endif /* OS_WIFSIGNALED_METHODDEF */
13589
13590#ifndef OS_WIFEXITED_METHODDEF
13591#define OS_WIFEXITED_METHODDEF
13592#endif /* OS_WIFEXITED_METHODDEF */
13593
13594#ifndef OS_WEXITSTATUS_METHODDEF
13595#define OS_WEXITSTATUS_METHODDEF
13596#endif /* OS_WEXITSTATUS_METHODDEF */
13597
13598#ifndef OS_WTERMSIG_METHODDEF
13599#define OS_WTERMSIG_METHODDEF
13600#endif /* OS_WTERMSIG_METHODDEF */
13601
13602#ifndef OS_WSTOPSIG_METHODDEF
13603#define OS_WSTOPSIG_METHODDEF
13604#endif /* OS_WSTOPSIG_METHODDEF */
13605
13606
Thomas Wouters477c8d52006-05-27 19:21:47 +000013607#if defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossumd5753e11999-10-19 13:29:23 +000013608#ifdef _SCO_DS
13609/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
13610 needed definitions in sys/statvfs.h */
13611#define _SVID3
13612#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000013613#include <sys/statvfs.h>
13614
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013615static PyObject*
13616_pystatvfs_fromstructstatvfs(struct statvfs st) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013617 PyObject *v = PyStructSequence_New(&StatVFSResultType);
13618 if (v == NULL)
13619 return NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013620
13621#if !defined(HAVE_LARGEFILE_SUPPORT)
Victor Stinner8c62be82010-05-06 00:08:46 +000013622 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13623 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13624 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long) st.f_blocks));
13625 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long) st.f_bfree));
13626 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong((long) st.f_bavail));
13627 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong((long) st.f_files));
13628 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong((long) st.f_ffree));
13629 PyStructSequence_SET_ITEM(v, 7, PyLong_FromLong((long) st.f_favail));
13630 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13631 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013632#else
Victor Stinner8c62be82010-05-06 00:08:46 +000013633 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13634 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13635 PyStructSequence_SET_ITEM(v, 2,
13636 PyLong_FromLongLong((PY_LONG_LONG) st.f_blocks));
13637 PyStructSequence_SET_ITEM(v, 3,
13638 PyLong_FromLongLong((PY_LONG_LONG) st.f_bfree));
13639 PyStructSequence_SET_ITEM(v, 4,
13640 PyLong_FromLongLong((PY_LONG_LONG) st.f_bavail));
13641 PyStructSequence_SET_ITEM(v, 5,
13642 PyLong_FromLongLong((PY_LONG_LONG) st.f_files));
13643 PyStructSequence_SET_ITEM(v, 6,
13644 PyLong_FromLongLong((PY_LONG_LONG) st.f_ffree));
13645 PyStructSequence_SET_ITEM(v, 7,
13646 PyLong_FromLongLong((PY_LONG_LONG) st.f_favail));
13647 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13648 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013649#endif
Victor Stinnerf0a7bac2013-10-30 18:55:24 +010013650 if (PyErr_Occurred()) {
13651 Py_DECREF(v);
13652 return NULL;
13653 }
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013654
Victor Stinner8c62be82010-05-06 00:08:46 +000013655 return v;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013656}
13657
Larry Hastings2f936352014-08-05 14:04:04 +100013658
13659/*[clinic input]
13660os.fstatvfs
13661 fd: int
13662 /
13663
13664Perform an fstatvfs system call on the given fd.
13665
13666Equivalent to statvfs(fd).
13667[clinic start generated code]*/
13668
13669PyDoc_STRVAR(os_fstatvfs__doc__,
13670"fstatvfs($module, fd, /)\n"
13671"--\n"
13672"\n"
13673"Perform an fstatvfs system call on the given fd.\n"
13674"\n"
13675"Equivalent to statvfs(fd).");
13676
13677#define OS_FSTATVFS_METHODDEF \
13678 {"fstatvfs", (PyCFunction)os_fstatvfs, METH_VARARGS, os_fstatvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013679
13680static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013681os_fstatvfs_impl(PyModuleDef *module, int fd);
13682
13683static PyObject *
13684os_fstatvfs(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013685{
Larry Hastings2f936352014-08-05 14:04:04 +100013686 PyObject *return_value = NULL;
13687 int fd;
13688
13689 if (!PyArg_ParseTuple(args,
13690 "i:fstatvfs",
13691 &fd))
13692 goto exit;
13693 return_value = os_fstatvfs_impl(module, fd);
13694
13695exit:
13696 return return_value;
13697}
13698
13699static PyObject *
13700os_fstatvfs_impl(PyModuleDef *module, int fd)
13701/*[clinic end generated code: output=0e32bf07f946ec0d input=d8122243ac50975e]*/
13702{
13703 int result;
Victor Stinner8c62be82010-05-06 00:08:46 +000013704 struct statvfs st;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013705
Victor Stinner8c62be82010-05-06 00:08:46 +000013706 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013707 result = fstatvfs(fd, &st);
Victor Stinner8c62be82010-05-06 00:08:46 +000013708 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013709 if (result != 0)
Victor Stinner8c62be82010-05-06 00:08:46 +000013710 return posix_error();
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013711
Victor Stinner8c62be82010-05-06 00:08:46 +000013712 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013713}
Larry Hastings2f936352014-08-05 14:04:04 +100013714#endif /* defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H) */
Guido van Rossum94f6f721999-01-06 18:42:14 +000013715
13716
Thomas Wouters477c8d52006-05-27 19:21:47 +000013717#if defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013718#include <sys/statvfs.h>
Larry Hastings2f936352014-08-05 14:04:04 +100013719/*[clinic input]
13720os.statvfs
Guido van Rossum94f6f721999-01-06 18:42:14 +000013721
Larry Hastings2f936352014-08-05 14:04:04 +100013722 path: path_t(allow_fd='PATH_HAVE_FSTATVFS')
13723
13724Perform a statvfs system call on the given path.
13725
13726path may always be specified as a string.
13727On some platforms, path may also be specified as an open file descriptor.
13728 If this functionality is unavailable, using it raises an exception.
13729[clinic start generated code]*/
13730
13731PyDoc_STRVAR(os_statvfs__doc__,
13732"statvfs($module, /, path)\n"
13733"--\n"
13734"\n"
13735"Perform a statvfs system call on the given path.\n"
13736"\n"
13737"path may always be specified as a string.\n"
13738"On some platforms, path may also be specified as an open file descriptor.\n"
13739" If this functionality is unavailable, using it raises an exception.");
13740
13741#define OS_STATVFS_METHODDEF \
13742 {"statvfs", (PyCFunction)os_statvfs, METH_VARARGS|METH_KEYWORDS, os_statvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013743
13744static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013745os_statvfs_impl(PyModuleDef *module, path_t *path);
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013746
Larry Hastings2f936352014-08-05 14:04:04 +100013747static PyObject *
13748os_statvfs(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13749{
13750 PyObject *return_value = NULL;
13751 static char *_keywords[] = {"path", NULL};
13752 path_t path = PATH_T_INITIALIZE("statvfs", "path", 0, PATH_HAVE_FSTATVFS);
13753
13754 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13755 "O&:statvfs", _keywords,
13756 path_converter, &path))
13757 goto exit;
13758 return_value = os_statvfs_impl(module, &path);
13759
13760exit:
13761 /* Cleanup for path */
13762 path_cleanup(&path);
13763
13764 return return_value;
13765}
13766
13767static PyObject *
13768os_statvfs_impl(PyModuleDef *module, path_t *path)
13769/*[clinic end generated code: output=00ff54983360b446 input=3f5c35791c669bd9]*/
13770{
13771 int result;
13772 struct statvfs st;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013773
13774 Py_BEGIN_ALLOW_THREADS
13775#ifdef HAVE_FSTATVFS
Larry Hastings2f936352014-08-05 14:04:04 +100013776 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070013777#ifdef __APPLE__
13778 /* handle weak-linking on Mac OS X 10.3 */
13779 if (fstatvfs == NULL) {
Larry Hastings2f936352014-08-05 14:04:04 +100013780 fd_specified("statvfs", path->fd);
13781 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013782 }
13783#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013784 result = fstatvfs(path->fd, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013785 }
13786 else
13787#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013788 result = statvfs(path->narrow, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013789 Py_END_ALLOW_THREADS
13790
13791 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100013792 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013793 }
13794
Larry Hastings2f936352014-08-05 14:04:04 +100013795 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013796}
Larry Hastings2f936352014-08-05 14:04:04 +100013797#endif /* defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H) */
13798
Guido van Rossum94f6f721999-01-06 18:42:14 +000013799
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013800#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100013801/*[clinic input]
13802os._getdiskusage
13803
13804 path: Py_UNICODE
13805
13806Return disk usage statistics about the given path as a (total, free) tuple.
13807[clinic start generated code]*/
13808
13809PyDoc_STRVAR(os__getdiskusage__doc__,
13810"_getdiskusage($module, /, path)\n"
13811"--\n"
13812"\n"
13813"Return disk usage statistics about the given path as a (total, free) tuple.");
13814
13815#define OS__GETDISKUSAGE_METHODDEF \
13816 {"_getdiskusage", (PyCFunction)os__getdiskusage, METH_VARARGS|METH_KEYWORDS, os__getdiskusage__doc__},
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013817
13818static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013819os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path);
13820
13821static PyObject *
13822os__getdiskusage(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13823{
13824 PyObject *return_value = NULL;
13825 static char *_keywords[] = {"path", NULL};
13826 Py_UNICODE *path;
13827
13828 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13829 "u:_getdiskusage", _keywords,
13830 &path))
13831 goto exit;
13832 return_value = os__getdiskusage_impl(module, path);
13833
13834exit:
13835 return return_value;
13836}
13837
13838static PyObject *
13839os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path)
13840/*[clinic end generated code: output=054c972179b13708 input=6458133aed893c78]*/
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013841{
13842 BOOL retval;
13843 ULARGE_INTEGER _, total, free;
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013844
13845 Py_BEGIN_ALLOW_THREADS
Victor Stinner6139c1b2011-11-09 22:14:14 +010013846 retval = GetDiskFreeSpaceExW(path, &_, &total, &free);
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013847 Py_END_ALLOW_THREADS
13848 if (retval == 0)
13849 return PyErr_SetFromWindowsErr(0);
13850
13851 return Py_BuildValue("(LL)", total.QuadPart, free.QuadPart);
13852}
Larry Hastings2f936352014-08-05 14:04:04 +100013853#endif /* MS_WINDOWS */
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013854
13855
Fred Drakec9680921999-12-13 16:37:25 +000013856/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
13857 * It maps strings representing configuration variable names to
13858 * integer values, allowing those functions to be called with the
Thomas Wouters7e474022000-07-16 12:04:32 +000013859 * magic names instead of polluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +000013860 * rarely-used constants. There are three separate tables that use
13861 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +000013862 *
13863 * This code is always included, even if none of the interfaces that
13864 * need it are included. The #if hackery needed to avoid it would be
13865 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +000013866 */
13867struct constdef {
13868 char *name;
13869 long value;
13870};
13871
Fred Drake12c6e2d1999-12-14 21:25:03 +000013872static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000013873conv_confname(PyObject *arg, int *valuep, struct constdef *table,
Guido van Rossum7d5baac2007-08-27 23:24:46 +000013874 size_t tablesize)
Fred Drake12c6e2d1999-12-14 21:25:03 +000013875{
Christian Heimes217cfd12007-12-02 14:31:20 +000013876 if (PyLong_Check(arg)) {
Stefan Krah0e803b32010-11-26 16:16:47 +000013877 *valuep = PyLong_AS_LONG(arg);
13878 return 1;
Fred Drake12c6e2d1999-12-14 21:25:03 +000013879 }
Guido van Rossumbce56a62007-05-10 18:04:33 +000013880 else {
Stefan Krah0e803b32010-11-26 16:16:47 +000013881 /* look up the value in the table using a binary search */
13882 size_t lo = 0;
13883 size_t mid;
13884 size_t hi = tablesize;
13885 int cmp;
13886 const char *confname;
13887 if (!PyUnicode_Check(arg)) {
13888 PyErr_SetString(PyExc_TypeError,
13889 "configuration names must be strings or integers");
13890 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013891 }
Stefan Krah0e803b32010-11-26 16:16:47 +000013892 confname = _PyUnicode_AsString(arg);
13893 if (confname == NULL)
13894 return 0;
13895 while (lo < hi) {
13896 mid = (lo + hi) / 2;
13897 cmp = strcmp(confname, table[mid].name);
13898 if (cmp < 0)
13899 hi = mid;
13900 else if (cmp > 0)
13901 lo = mid + 1;
13902 else {
13903 *valuep = table[mid].value;
13904 return 1;
13905 }
13906 }
13907 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
13908 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013909 }
Fred Drake12c6e2d1999-12-14 21:25:03 +000013910}
13911
13912
13913#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
13914static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +000013915#ifdef _PC_ABI_AIO_XFER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013916 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000013917#endif
13918#ifdef _PC_ABI_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013919 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
Fred Draked86ed291999-12-15 15:34:33 +000013920#endif
Fred Drakec9680921999-12-13 16:37:25 +000013921#ifdef _PC_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013922 {"PC_ASYNC_IO", _PC_ASYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013923#endif
13924#ifdef _PC_CHOWN_RESTRICTED
Victor Stinner8c62be82010-05-06 00:08:46 +000013925 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
Fred Drakec9680921999-12-13 16:37:25 +000013926#endif
13927#ifdef _PC_FILESIZEBITS
Victor Stinner8c62be82010-05-06 00:08:46 +000013928 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
Fred Drakec9680921999-12-13 16:37:25 +000013929#endif
13930#ifdef _PC_LAST
Victor Stinner8c62be82010-05-06 00:08:46 +000013931 {"PC_LAST", _PC_LAST},
Fred Drakec9680921999-12-13 16:37:25 +000013932#endif
13933#ifdef _PC_LINK_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013934 {"PC_LINK_MAX", _PC_LINK_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013935#endif
13936#ifdef _PC_MAX_CANON
Victor Stinner8c62be82010-05-06 00:08:46 +000013937 {"PC_MAX_CANON", _PC_MAX_CANON},
Fred Drakec9680921999-12-13 16:37:25 +000013938#endif
13939#ifdef _PC_MAX_INPUT
Victor Stinner8c62be82010-05-06 00:08:46 +000013940 {"PC_MAX_INPUT", _PC_MAX_INPUT},
Fred Drakec9680921999-12-13 16:37:25 +000013941#endif
13942#ifdef _PC_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013943 {"PC_NAME_MAX", _PC_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013944#endif
13945#ifdef _PC_NO_TRUNC
Victor Stinner8c62be82010-05-06 00:08:46 +000013946 {"PC_NO_TRUNC", _PC_NO_TRUNC},
Fred Drakec9680921999-12-13 16:37:25 +000013947#endif
13948#ifdef _PC_PATH_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013949 {"PC_PATH_MAX", _PC_PATH_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013950#endif
13951#ifdef _PC_PIPE_BUF
Victor Stinner8c62be82010-05-06 00:08:46 +000013952 {"PC_PIPE_BUF", _PC_PIPE_BUF},
Fred Drakec9680921999-12-13 16:37:25 +000013953#endif
13954#ifdef _PC_PRIO_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013955 {"PC_PRIO_IO", _PC_PRIO_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013956#endif
13957#ifdef _PC_SOCK_MAXBUF
Victor Stinner8c62be82010-05-06 00:08:46 +000013958 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
Fred Drakec9680921999-12-13 16:37:25 +000013959#endif
13960#ifdef _PC_SYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013961 {"PC_SYNC_IO", _PC_SYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013962#endif
13963#ifdef _PC_VDISABLE
Victor Stinner8c62be82010-05-06 00:08:46 +000013964 {"PC_VDISABLE", _PC_VDISABLE},
Fred Drakec9680921999-12-13 16:37:25 +000013965#endif
Jesus Cea7e9065c2010-10-25 13:02:04 +000013966#ifdef _PC_ACL_ENABLED
13967 {"PC_ACL_ENABLED", _PC_ACL_ENABLED},
13968#endif
13969#ifdef _PC_MIN_HOLE_SIZE
13970 {"PC_MIN_HOLE_SIZE", _PC_MIN_HOLE_SIZE},
13971#endif
13972#ifdef _PC_ALLOC_SIZE_MIN
13973 {"PC_ALLOC_SIZE_MIN", _PC_ALLOC_SIZE_MIN},
13974#endif
13975#ifdef _PC_REC_INCR_XFER_SIZE
13976 {"PC_REC_INCR_XFER_SIZE", _PC_REC_INCR_XFER_SIZE},
13977#endif
13978#ifdef _PC_REC_MAX_XFER_SIZE
13979 {"PC_REC_MAX_XFER_SIZE", _PC_REC_MAX_XFER_SIZE},
13980#endif
13981#ifdef _PC_REC_MIN_XFER_SIZE
13982 {"PC_REC_MIN_XFER_SIZE", _PC_REC_MIN_XFER_SIZE},
13983#endif
13984#ifdef _PC_REC_XFER_ALIGN
13985 {"PC_REC_XFER_ALIGN", _PC_REC_XFER_ALIGN},
13986#endif
13987#ifdef _PC_SYMLINK_MAX
13988 {"PC_SYMLINK_MAX", _PC_SYMLINK_MAX},
13989#endif
13990#ifdef _PC_XATTR_ENABLED
13991 {"PC_XATTR_ENABLED", _PC_XATTR_ENABLED},
13992#endif
13993#ifdef _PC_XATTR_EXISTS
13994 {"PC_XATTR_EXISTS", _PC_XATTR_EXISTS},
13995#endif
13996#ifdef _PC_TIMESTAMP_RESOLUTION
13997 {"PC_TIMESTAMP_RESOLUTION", _PC_TIMESTAMP_RESOLUTION},
13998#endif
Fred Drakec9680921999-12-13 16:37:25 +000013999};
14000
Fred Drakec9680921999-12-13 16:37:25 +000014001static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014002conv_path_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014003{
14004 return conv_confname(arg, valuep, posix_constants_pathconf,
14005 sizeof(posix_constants_pathconf)
14006 / sizeof(struct constdef));
14007}
14008#endif
14009
Larry Hastings2f936352014-08-05 14:04:04 +100014010
Fred Drakec9680921999-12-13 16:37:25 +000014011#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014012/*[clinic input]
14013os.fpathconf -> long
14014
14015 fd: int
14016 name: path_confname
14017 /
14018
14019Return the configuration limit name for the file descriptor fd.
14020
14021If there is no limit, return -1.
14022[clinic start generated code]*/
14023
14024PyDoc_STRVAR(os_fpathconf__doc__,
14025"fpathconf($module, fd, name, /)\n"
14026"--\n"
14027"\n"
14028"Return the configuration limit name for the file descriptor fd.\n"
14029"\n"
14030"If there is no limit, return -1.");
14031
14032#define OS_FPATHCONF_METHODDEF \
14033 {"fpathconf", (PyCFunction)os_fpathconf, METH_VARARGS, os_fpathconf__doc__},
14034
14035static long
14036os_fpathconf_impl(PyModuleDef *module, int fd, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014037
14038static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014039os_fpathconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014040{
Larry Hastings2f936352014-08-05 14:04:04 +100014041 PyObject *return_value = NULL;
14042 int fd;
14043 int name;
14044 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014045
Larry Hastings2f936352014-08-05 14:04:04 +100014046 if (!PyArg_ParseTuple(args,
14047 "iO&:fpathconf",
14048 &fd, conv_path_confname, &name))
14049 goto exit;
14050 _return_value = os_fpathconf_impl(module, fd, name);
14051 if ((_return_value == -1) && PyErr_Occurred())
14052 goto exit;
14053 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014054
Larry Hastings2f936352014-08-05 14:04:04 +100014055exit:
14056 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014057}
Larry Hastings2f936352014-08-05 14:04:04 +100014058
14059static long
14060os_fpathconf_impl(PyModuleDef *module, int fd, int name)
14061/*[clinic end generated code: output=3bf04b40e0523a8c input=5942a024d3777810]*/
14062{
14063 long limit;
14064
14065 errno = 0;
14066 limit = fpathconf(fd, name);
14067 if (limit == -1 && errno != 0)
14068 posix_error();
14069
14070 return limit;
14071}
14072#endif /* HAVE_FPATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014073
14074
14075#ifdef HAVE_PATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014076/*[clinic input]
14077os.pathconf -> long
14078 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
14079 name: path_confname
14080
14081Return the configuration limit name for the file or directory path.
14082
14083If there is no limit, return -1.
14084On some platforms, path may also be specified as an open file descriptor.
14085 If this functionality is unavailable, using it raises an exception.
14086[clinic start generated code]*/
14087
14088PyDoc_STRVAR(os_pathconf__doc__,
14089"pathconf($module, /, path, name)\n"
14090"--\n"
14091"\n"
14092"Return the configuration limit name for the file or directory path.\n"
14093"\n"
14094"If there is no limit, return -1.\n"
14095"On some platforms, path may also be specified as an open file descriptor.\n"
14096" If this functionality is unavailable, using it raises an exception.");
14097
14098#define OS_PATHCONF_METHODDEF \
14099 {"pathconf", (PyCFunction)os_pathconf, METH_VARARGS|METH_KEYWORDS, os_pathconf__doc__},
14100
14101static long
14102os_pathconf_impl(PyModuleDef *module, path_t *path, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014103
14104static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014105os_pathconf(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drakec9680921999-12-13 16:37:25 +000014106{
Larry Hastings2f936352014-08-05 14:04:04 +100014107 PyObject *return_value = NULL;
14108 static char *_keywords[] = {"path", "name", NULL};
14109 path_t path = PATH_T_INITIALIZE("pathconf", "path", 0, PATH_HAVE_FPATHCONF);
Fred Drakec9680921999-12-13 16:37:25 +000014110 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014111 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014112
Larry Hastings2f936352014-08-05 14:04:04 +100014113 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
14114 "O&O&:pathconf", _keywords,
14115 path_converter, &path, conv_path_confname, &name))
14116 goto exit;
14117 _return_value = os_pathconf_impl(module, &path, name);
14118 if ((_return_value == -1) && PyErr_Occurred())
14119 goto exit;
14120 return_value = PyLong_FromLong(_return_value);
14121
14122exit:
14123 /* Cleanup for path */
14124 path_cleanup(&path);
14125
14126 return return_value;
14127}
14128
14129static long
14130os_pathconf_impl(PyModuleDef *module, path_t *path, int name)
14131/*[clinic end generated code: output=1a53e125b6cf63e4 input=bc3e2a985af27e5e]*/
14132{
Victor Stinner8c62be82010-05-06 00:08:46 +000014133 long limit;
Fred Drakec9680921999-12-13 16:37:25 +000014134
Victor Stinner8c62be82010-05-06 00:08:46 +000014135 errno = 0;
Georg Brandl306336b2012-06-24 12:55:33 +020014136#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014137 if (path->fd != -1)
14138 limit = fpathconf(path->fd, name);
Georg Brandl306336b2012-06-24 12:55:33 +020014139 else
14140#endif
Larry Hastings2f936352014-08-05 14:04:04 +100014141 limit = pathconf(path->narrow, name);
Victor Stinner8c62be82010-05-06 00:08:46 +000014142 if (limit == -1 && errno != 0) {
14143 if (errno == EINVAL)
Stefan Krah99439262010-11-26 12:58:05 +000014144 /* could be a path or name problem */
14145 posix_error();
Fred Drakec9680921999-12-13 16:37:25 +000014146 else
Larry Hastings2f936352014-08-05 14:04:04 +100014147 path_error(path);
Victor Stinner8c62be82010-05-06 00:08:46 +000014148 }
Larry Hastings2f936352014-08-05 14:04:04 +100014149
14150 return limit;
Fred Drakec9680921999-12-13 16:37:25 +000014151}
Larry Hastings2f936352014-08-05 14:04:04 +100014152#endif /* HAVE_PATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014153
14154#ifdef HAVE_CONFSTR
14155static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +000014156#ifdef _CS_ARCHITECTURE
Victor Stinner8c62be82010-05-06 00:08:46 +000014157 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
Fred Draked86ed291999-12-15 15:34:33 +000014158#endif
Mark Dickinson876d7c82010-04-16 12:47:52 +000014159#ifdef _CS_GNU_LIBC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014160 {"CS_GNU_LIBC_VERSION", _CS_GNU_LIBC_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014161#endif
14162#ifdef _CS_GNU_LIBPTHREAD_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014163 {"CS_GNU_LIBPTHREAD_VERSION", _CS_GNU_LIBPTHREAD_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014164#endif
Fred Draked86ed291999-12-15 15:34:33 +000014165#ifdef _CS_HOSTNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014166 {"CS_HOSTNAME", _CS_HOSTNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014167#endif
14168#ifdef _CS_HW_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014169 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014170#endif
14171#ifdef _CS_HW_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014172 {"CS_HW_SERIAL", _CS_HW_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014173#endif
14174#ifdef _CS_INITTAB_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014175 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014176#endif
Fred Drakec9680921999-12-13 16:37:25 +000014177#ifdef _CS_LFS64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014178 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014179#endif
14180#ifdef _CS_LFS64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014181 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014182#endif
14183#ifdef _CS_LFS64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014184 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014185#endif
14186#ifdef _CS_LFS64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014187 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014188#endif
14189#ifdef _CS_LFS_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014190 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014191#endif
14192#ifdef _CS_LFS_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014193 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014194#endif
14195#ifdef _CS_LFS_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014196 {"CS_LFS_LIBS", _CS_LFS_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014197#endif
14198#ifdef _CS_LFS_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014199 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014200#endif
Fred Draked86ed291999-12-15 15:34:33 +000014201#ifdef _CS_MACHINE
Victor Stinner8c62be82010-05-06 00:08:46 +000014202 {"CS_MACHINE", _CS_MACHINE},
Fred Draked86ed291999-12-15 15:34:33 +000014203#endif
Fred Drakec9680921999-12-13 16:37:25 +000014204#ifdef _CS_PATH
Victor Stinner8c62be82010-05-06 00:08:46 +000014205 {"CS_PATH", _CS_PATH},
Fred Drakec9680921999-12-13 16:37:25 +000014206#endif
Fred Draked86ed291999-12-15 15:34:33 +000014207#ifdef _CS_RELEASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014208 {"CS_RELEASE", _CS_RELEASE},
Fred Draked86ed291999-12-15 15:34:33 +000014209#endif
14210#ifdef _CS_SRPC_DOMAIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014211 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
Fred Draked86ed291999-12-15 15:34:33 +000014212#endif
14213#ifdef _CS_SYSNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014214 {"CS_SYSNAME", _CS_SYSNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014215#endif
14216#ifdef _CS_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014217 {"CS_VERSION", _CS_VERSION},
Fred Draked86ed291999-12-15 15:34:33 +000014218#endif
Fred Drakec9680921999-12-13 16:37:25 +000014219#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014220 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014221#endif
14222#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014223 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014224#endif
14225#ifdef _CS_XBS5_ILP32_OFF32_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014226 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014227#endif
14228#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014229 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014230#endif
14231#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014232 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014233#endif
14234#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014235 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014236#endif
14237#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014238 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014239#endif
14240#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014241 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014242#endif
14243#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014244 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014245#endif
14246#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014247 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014248#endif
14249#ifdef _CS_XBS5_LP64_OFF64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014250 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014251#endif
14252#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014253 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014254#endif
14255#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014256 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014257#endif
14258#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014259 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014260#endif
14261#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014262 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014263#endif
14264#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014265 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014266#endif
Fred Draked86ed291999-12-15 15:34:33 +000014267#ifdef _MIPS_CS_AVAIL_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014268 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014269#endif
14270#ifdef _MIPS_CS_BASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014271 {"MIPS_CS_BASE", _MIPS_CS_BASE},
Fred Draked86ed291999-12-15 15:34:33 +000014272#endif
14273#ifdef _MIPS_CS_HOSTID
Victor Stinner8c62be82010-05-06 00:08:46 +000014274 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
Fred Draked86ed291999-12-15 15:34:33 +000014275#endif
14276#ifdef _MIPS_CS_HW_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014277 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014278#endif
14279#ifdef _MIPS_CS_NUM_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014280 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014281#endif
14282#ifdef _MIPS_CS_OSREL_MAJ
Victor Stinner8c62be82010-05-06 00:08:46 +000014283 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
Fred Draked86ed291999-12-15 15:34:33 +000014284#endif
14285#ifdef _MIPS_CS_OSREL_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014286 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
Fred Draked86ed291999-12-15 15:34:33 +000014287#endif
14288#ifdef _MIPS_CS_OSREL_PATCH
Victor Stinner8c62be82010-05-06 00:08:46 +000014289 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
Fred Draked86ed291999-12-15 15:34:33 +000014290#endif
14291#ifdef _MIPS_CS_OS_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014292 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014293#endif
14294#ifdef _MIPS_CS_OS_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014295 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014296#endif
14297#ifdef _MIPS_CS_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014298 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014299#endif
14300#ifdef _MIPS_CS_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014301 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014302#endif
14303#ifdef _MIPS_CS_VENDOR
Victor Stinner8c62be82010-05-06 00:08:46 +000014304 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
Fred Draked86ed291999-12-15 15:34:33 +000014305#endif
Fred Drakec9680921999-12-13 16:37:25 +000014306};
14307
14308static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014309conv_confstr_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014310{
14311 return conv_confname(arg, valuep, posix_constants_confstr,
14312 sizeof(posix_constants_confstr)
14313 / sizeof(struct constdef));
14314}
14315
Larry Hastings2f936352014-08-05 14:04:04 +100014316
14317/*[clinic input]
14318os.confstr
14319
14320 name: confstr_confname
14321 /
14322
14323Return a string-valued system configuration variable.
14324[clinic start generated code]*/
14325
14326PyDoc_STRVAR(os_confstr__doc__,
14327"confstr($module, name, /)\n"
14328"--\n"
14329"\n"
14330"Return a string-valued system configuration variable.");
14331
14332#define OS_CONFSTR_METHODDEF \
14333 {"confstr", (PyCFunction)os_confstr, METH_VARARGS, os_confstr__doc__},
Fred Drakec9680921999-12-13 16:37:25 +000014334
14335static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014336os_confstr_impl(PyModuleDef *module, int name);
14337
14338static PyObject *
14339os_confstr(PyModuleDef *module, PyObject *args)
14340{
14341 PyObject *return_value = NULL;
14342 int name;
14343
14344 if (!PyArg_ParseTuple(args,
14345 "O&:confstr",
14346 conv_confstr_confname, &name))
14347 goto exit;
14348 return_value = os_confstr_impl(module, name);
14349
14350exit:
14351 return return_value;
14352}
14353
14354static PyObject *
14355os_confstr_impl(PyModuleDef *module, int name)
14356/*[clinic end generated code: output=3f5e8aba9f8e3174 input=18fb4d0567242e65]*/
Fred Drakec9680921999-12-13 16:37:25 +000014357{
14358 PyObject *result = NULL;
Victor Stinnercb043522010-09-10 23:49:04 +000014359 char buffer[255];
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014360 size_t len;
Fred Drakec9680921999-12-13 16:37:25 +000014361
Victor Stinnercb043522010-09-10 23:49:04 +000014362 errno = 0;
14363 len = confstr(name, buffer, sizeof(buffer));
14364 if (len == 0) {
14365 if (errno) {
14366 posix_error();
14367 return NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014368 }
14369 else {
Victor Stinnercb043522010-09-10 23:49:04 +000014370 Py_RETURN_NONE;
Fred Drakec9680921999-12-13 16:37:25 +000014371 }
14372 }
Victor Stinnercb043522010-09-10 23:49:04 +000014373
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014374 if (len >= sizeof(buffer)) {
Victor Stinnercb043522010-09-10 23:49:04 +000014375 char *buf = PyMem_Malloc(len);
14376 if (buf == NULL)
14377 return PyErr_NoMemory();
14378 confstr(name, buf, len);
14379 result = PyUnicode_DecodeFSDefaultAndSize(buf, len-1);
14380 PyMem_Free(buf);
14381 }
14382 else
14383 result = PyUnicode_DecodeFSDefaultAndSize(buffer, len-1);
Fred Drakec9680921999-12-13 16:37:25 +000014384 return result;
14385}
Larry Hastings2f936352014-08-05 14:04:04 +100014386#endif /* HAVE_CONFSTR */
Fred Drakec9680921999-12-13 16:37:25 +000014387
14388
14389#ifdef HAVE_SYSCONF
14390static struct constdef posix_constants_sysconf[] = {
14391#ifdef _SC_2_CHAR_TERM
Victor Stinner8c62be82010-05-06 00:08:46 +000014392 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
Fred Drakec9680921999-12-13 16:37:25 +000014393#endif
14394#ifdef _SC_2_C_BIND
Victor Stinner8c62be82010-05-06 00:08:46 +000014395 {"SC_2_C_BIND", _SC_2_C_BIND},
Fred Drakec9680921999-12-13 16:37:25 +000014396#endif
14397#ifdef _SC_2_C_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014398 {"SC_2_C_DEV", _SC_2_C_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014399#endif
14400#ifdef _SC_2_C_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014401 {"SC_2_C_VERSION", _SC_2_C_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014402#endif
14403#ifdef _SC_2_FORT_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014404 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014405#endif
14406#ifdef _SC_2_FORT_RUN
Victor Stinner8c62be82010-05-06 00:08:46 +000014407 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
Fred Drakec9680921999-12-13 16:37:25 +000014408#endif
14409#ifdef _SC_2_LOCALEDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000014410 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
Fred Drakec9680921999-12-13 16:37:25 +000014411#endif
14412#ifdef _SC_2_SW_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014413 {"SC_2_SW_DEV", _SC_2_SW_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014414#endif
14415#ifdef _SC_2_UPE
Victor Stinner8c62be82010-05-06 00:08:46 +000014416 {"SC_2_UPE", _SC_2_UPE},
Fred Drakec9680921999-12-13 16:37:25 +000014417#endif
14418#ifdef _SC_2_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014419 {"SC_2_VERSION", _SC_2_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014420#endif
Fred Draked86ed291999-12-15 15:34:33 +000014421#ifdef _SC_ABI_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014422 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
Fred Draked86ed291999-12-15 15:34:33 +000014423#endif
14424#ifdef _SC_ACL
Victor Stinner8c62be82010-05-06 00:08:46 +000014425 {"SC_ACL", _SC_ACL},
Fred Draked86ed291999-12-15 15:34:33 +000014426#endif
Fred Drakec9680921999-12-13 16:37:25 +000014427#ifdef _SC_AIO_LISTIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014428 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014429#endif
Fred Drakec9680921999-12-13 16:37:25 +000014430#ifdef _SC_AIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014431 {"SC_AIO_MAX", _SC_AIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014432#endif
14433#ifdef _SC_AIO_PRIO_DELTA_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014434 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014435#endif
14436#ifdef _SC_ARG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014437 {"SC_ARG_MAX", _SC_ARG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014438#endif
14439#ifdef _SC_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014440 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014441#endif
14442#ifdef _SC_ATEXIT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014443 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014444#endif
Fred Draked86ed291999-12-15 15:34:33 +000014445#ifdef _SC_AUDIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014446 {"SC_AUDIT", _SC_AUDIT},
Fred Draked86ed291999-12-15 15:34:33 +000014447#endif
Fred Drakec9680921999-12-13 16:37:25 +000014448#ifdef _SC_AVPHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014449 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014450#endif
14451#ifdef _SC_BC_BASE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014452 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014453#endif
14454#ifdef _SC_BC_DIM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014455 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014456#endif
14457#ifdef _SC_BC_SCALE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014458 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014459#endif
14460#ifdef _SC_BC_STRING_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014461 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014462#endif
Fred Draked86ed291999-12-15 15:34:33 +000014463#ifdef _SC_CAP
Victor Stinner8c62be82010-05-06 00:08:46 +000014464 {"SC_CAP", _SC_CAP},
Fred Draked86ed291999-12-15 15:34:33 +000014465#endif
Fred Drakec9680921999-12-13 16:37:25 +000014466#ifdef _SC_CHARCLASS_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014467 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014468#endif
14469#ifdef _SC_CHAR_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014470 {"SC_CHAR_BIT", _SC_CHAR_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014471#endif
14472#ifdef _SC_CHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014473 {"SC_CHAR_MAX", _SC_CHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014474#endif
14475#ifdef _SC_CHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014476 {"SC_CHAR_MIN", _SC_CHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014477#endif
14478#ifdef _SC_CHILD_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014479 {"SC_CHILD_MAX", _SC_CHILD_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014480#endif
14481#ifdef _SC_CLK_TCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014482 {"SC_CLK_TCK", _SC_CLK_TCK},
Fred Drakec9680921999-12-13 16:37:25 +000014483#endif
14484#ifdef _SC_COHER_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014485 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014486#endif
14487#ifdef _SC_COLL_WEIGHTS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014488 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014489#endif
14490#ifdef _SC_DCACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014491 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014492#endif
14493#ifdef _SC_DCACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014494 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014495#endif
14496#ifdef _SC_DCACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014497 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014498#endif
14499#ifdef _SC_DCACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014500 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014501#endif
14502#ifdef _SC_DCACHE_TBLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014503 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014504#endif
14505#ifdef _SC_DELAYTIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014506 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014507#endif
14508#ifdef _SC_EQUIV_CLASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014509 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014510#endif
14511#ifdef _SC_EXPR_NEST_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014512 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014513#endif
14514#ifdef _SC_FSYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000014515 {"SC_FSYNC", _SC_FSYNC},
Fred Drakec9680921999-12-13 16:37:25 +000014516#endif
14517#ifdef _SC_GETGR_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014518 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014519#endif
14520#ifdef _SC_GETPW_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014521 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014522#endif
14523#ifdef _SC_ICACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014524 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014525#endif
14526#ifdef _SC_ICACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014527 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014528#endif
14529#ifdef _SC_ICACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014530 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014531#endif
14532#ifdef _SC_ICACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014533 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014534#endif
Fred Draked86ed291999-12-15 15:34:33 +000014535#ifdef _SC_INF
Victor Stinner8c62be82010-05-06 00:08:46 +000014536 {"SC_INF", _SC_INF},
Fred Draked86ed291999-12-15 15:34:33 +000014537#endif
Fred Drakec9680921999-12-13 16:37:25 +000014538#ifdef _SC_INT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014539 {"SC_INT_MAX", _SC_INT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014540#endif
14541#ifdef _SC_INT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014542 {"SC_INT_MIN", _SC_INT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014543#endif
14544#ifdef _SC_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014545 {"SC_IOV_MAX", _SC_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014546#endif
Fred Draked86ed291999-12-15 15:34:33 +000014547#ifdef _SC_IP_SECOPTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014548 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
Fred Draked86ed291999-12-15 15:34:33 +000014549#endif
Fred Drakec9680921999-12-13 16:37:25 +000014550#ifdef _SC_JOB_CONTROL
Victor Stinner8c62be82010-05-06 00:08:46 +000014551 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
Fred Drakec9680921999-12-13 16:37:25 +000014552#endif
Fred Draked86ed291999-12-15 15:34:33 +000014553#ifdef _SC_KERN_POINTERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014554 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
Fred Draked86ed291999-12-15 15:34:33 +000014555#endif
14556#ifdef _SC_KERN_SIM
Victor Stinner8c62be82010-05-06 00:08:46 +000014557 {"SC_KERN_SIM", _SC_KERN_SIM},
Fred Draked86ed291999-12-15 15:34:33 +000014558#endif
Fred Drakec9680921999-12-13 16:37:25 +000014559#ifdef _SC_LINE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014560 {"SC_LINE_MAX", _SC_LINE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014561#endif
14562#ifdef _SC_LOGIN_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014563 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014564#endif
14565#ifdef _SC_LOGNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014566 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014567#endif
14568#ifdef _SC_LONG_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014569 {"SC_LONG_BIT", _SC_LONG_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014570#endif
Fred Draked86ed291999-12-15 15:34:33 +000014571#ifdef _SC_MAC
Victor Stinner8c62be82010-05-06 00:08:46 +000014572 {"SC_MAC", _SC_MAC},
Fred Draked86ed291999-12-15 15:34:33 +000014573#endif
Fred Drakec9680921999-12-13 16:37:25 +000014574#ifdef _SC_MAPPED_FILES
Victor Stinner8c62be82010-05-06 00:08:46 +000014575 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
Fred Drakec9680921999-12-13 16:37:25 +000014576#endif
14577#ifdef _SC_MAXPID
Victor Stinner8c62be82010-05-06 00:08:46 +000014578 {"SC_MAXPID", _SC_MAXPID},
Fred Drakec9680921999-12-13 16:37:25 +000014579#endif
14580#ifdef _SC_MB_LEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014581 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014582#endif
14583#ifdef _SC_MEMLOCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014584 {"SC_MEMLOCK", _SC_MEMLOCK},
Fred Drakec9680921999-12-13 16:37:25 +000014585#endif
14586#ifdef _SC_MEMLOCK_RANGE
Victor Stinner8c62be82010-05-06 00:08:46 +000014587 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
Fred Drakec9680921999-12-13 16:37:25 +000014588#endif
14589#ifdef _SC_MEMORY_PROTECTION
Victor Stinner8c62be82010-05-06 00:08:46 +000014590 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
Fred Drakec9680921999-12-13 16:37:25 +000014591#endif
14592#ifdef _SC_MESSAGE_PASSING
Victor Stinner8c62be82010-05-06 00:08:46 +000014593 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
Fred Drakec9680921999-12-13 16:37:25 +000014594#endif
Fred Draked86ed291999-12-15 15:34:33 +000014595#ifdef _SC_MMAP_FIXED_ALIGNMENT
Victor Stinner8c62be82010-05-06 00:08:46 +000014596 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
Fred Draked86ed291999-12-15 15:34:33 +000014597#endif
Fred Drakec9680921999-12-13 16:37:25 +000014598#ifdef _SC_MQ_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014599 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014600#endif
14601#ifdef _SC_MQ_PRIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014602 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014603#endif
Fred Draked86ed291999-12-15 15:34:33 +000014604#ifdef _SC_NACLS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014605 {"SC_NACLS_MAX", _SC_NACLS_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000014606#endif
Fred Drakec9680921999-12-13 16:37:25 +000014607#ifdef _SC_NGROUPS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014608 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014609#endif
14610#ifdef _SC_NL_ARGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014611 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014612#endif
14613#ifdef _SC_NL_LANGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014614 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014615#endif
14616#ifdef _SC_NL_MSGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014617 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014618#endif
14619#ifdef _SC_NL_NMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014620 {"SC_NL_NMAX", _SC_NL_NMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014621#endif
14622#ifdef _SC_NL_SETMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014623 {"SC_NL_SETMAX", _SC_NL_SETMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014624#endif
14625#ifdef _SC_NL_TEXTMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014626 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014627#endif
14628#ifdef _SC_NPROCESSORS_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014629 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
Fred Drakec9680921999-12-13 16:37:25 +000014630#endif
14631#ifdef _SC_NPROCESSORS_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014632 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
Fred Drakec9680921999-12-13 16:37:25 +000014633#endif
Fred Draked86ed291999-12-15 15:34:33 +000014634#ifdef _SC_NPROC_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014635 {"SC_NPROC_CONF", _SC_NPROC_CONF},
Fred Draked86ed291999-12-15 15:34:33 +000014636#endif
14637#ifdef _SC_NPROC_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014638 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
Fred Draked86ed291999-12-15 15:34:33 +000014639#endif
Fred Drakec9680921999-12-13 16:37:25 +000014640#ifdef _SC_NZERO
Victor Stinner8c62be82010-05-06 00:08:46 +000014641 {"SC_NZERO", _SC_NZERO},
Fred Drakec9680921999-12-13 16:37:25 +000014642#endif
14643#ifdef _SC_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014644 {"SC_OPEN_MAX", _SC_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014645#endif
14646#ifdef _SC_PAGESIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014647 {"SC_PAGESIZE", _SC_PAGESIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014648#endif
14649#ifdef _SC_PAGE_SIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014650 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014651#endif
14652#ifdef _SC_PASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014653 {"SC_PASS_MAX", _SC_PASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014654#endif
14655#ifdef _SC_PHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014656 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014657#endif
14658#ifdef _SC_PII
Victor Stinner8c62be82010-05-06 00:08:46 +000014659 {"SC_PII", _SC_PII},
Fred Drakec9680921999-12-13 16:37:25 +000014660#endif
14661#ifdef _SC_PII_INTERNET
Victor Stinner8c62be82010-05-06 00:08:46 +000014662 {"SC_PII_INTERNET", _SC_PII_INTERNET},
Fred Drakec9680921999-12-13 16:37:25 +000014663#endif
14664#ifdef _SC_PII_INTERNET_DGRAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014665 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
Fred Drakec9680921999-12-13 16:37:25 +000014666#endif
14667#ifdef _SC_PII_INTERNET_STREAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014668 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
Fred Drakec9680921999-12-13 16:37:25 +000014669#endif
14670#ifdef _SC_PII_OSI
Victor Stinner8c62be82010-05-06 00:08:46 +000014671 {"SC_PII_OSI", _SC_PII_OSI},
Fred Drakec9680921999-12-13 16:37:25 +000014672#endif
14673#ifdef _SC_PII_OSI_CLTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014674 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
Fred Drakec9680921999-12-13 16:37:25 +000014675#endif
14676#ifdef _SC_PII_OSI_COTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014677 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
Fred Drakec9680921999-12-13 16:37:25 +000014678#endif
14679#ifdef _SC_PII_OSI_M
Victor Stinner8c62be82010-05-06 00:08:46 +000014680 {"SC_PII_OSI_M", _SC_PII_OSI_M},
Fred Drakec9680921999-12-13 16:37:25 +000014681#endif
14682#ifdef _SC_PII_SOCKET
Victor Stinner8c62be82010-05-06 00:08:46 +000014683 {"SC_PII_SOCKET", _SC_PII_SOCKET},
Fred Drakec9680921999-12-13 16:37:25 +000014684#endif
14685#ifdef _SC_PII_XTI
Victor Stinner8c62be82010-05-06 00:08:46 +000014686 {"SC_PII_XTI", _SC_PII_XTI},
Fred Drakec9680921999-12-13 16:37:25 +000014687#endif
14688#ifdef _SC_POLL
Victor Stinner8c62be82010-05-06 00:08:46 +000014689 {"SC_POLL", _SC_POLL},
Fred Drakec9680921999-12-13 16:37:25 +000014690#endif
14691#ifdef _SC_PRIORITIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014692 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014693#endif
14694#ifdef _SC_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014695 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014696#endif
14697#ifdef _SC_REALTIME_SIGNALS
Victor Stinner8c62be82010-05-06 00:08:46 +000014698 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
Fred Drakec9680921999-12-13 16:37:25 +000014699#endif
14700#ifdef _SC_RE_DUP_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014701 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014702#endif
14703#ifdef _SC_RTSIG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014704 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014705#endif
14706#ifdef _SC_SAVED_IDS
Victor Stinner8c62be82010-05-06 00:08:46 +000014707 {"SC_SAVED_IDS", _SC_SAVED_IDS},
Fred Drakec9680921999-12-13 16:37:25 +000014708#endif
14709#ifdef _SC_SCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014710 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014711#endif
14712#ifdef _SC_SCHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014713 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014714#endif
14715#ifdef _SC_SELECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014716 {"SC_SELECT", _SC_SELECT},
Fred Drakec9680921999-12-13 16:37:25 +000014717#endif
14718#ifdef _SC_SEMAPHORES
Victor Stinner8c62be82010-05-06 00:08:46 +000014719 {"SC_SEMAPHORES", _SC_SEMAPHORES},
Fred Drakec9680921999-12-13 16:37:25 +000014720#endif
14721#ifdef _SC_SEM_NSEMS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014722 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014723#endif
14724#ifdef _SC_SEM_VALUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014725 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014726#endif
14727#ifdef _SC_SHARED_MEMORY_OBJECTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014728 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
Fred Drakec9680921999-12-13 16:37:25 +000014729#endif
14730#ifdef _SC_SHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014731 {"SC_SHRT_MAX", _SC_SHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014732#endif
14733#ifdef _SC_SHRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014734 {"SC_SHRT_MIN", _SC_SHRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014735#endif
14736#ifdef _SC_SIGQUEUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014737 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014738#endif
14739#ifdef _SC_SIGRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014740 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014741#endif
14742#ifdef _SC_SIGRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014743 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014744#endif
Fred Draked86ed291999-12-15 15:34:33 +000014745#ifdef _SC_SOFTPOWER
Victor Stinner8c62be82010-05-06 00:08:46 +000014746 {"SC_SOFTPOWER", _SC_SOFTPOWER},
Fred Draked86ed291999-12-15 15:34:33 +000014747#endif
Fred Drakec9680921999-12-13 16:37:25 +000014748#ifdef _SC_SPLIT_CACHE
Victor Stinner8c62be82010-05-06 00:08:46 +000014749 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
Fred Drakec9680921999-12-13 16:37:25 +000014750#endif
14751#ifdef _SC_SSIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014752 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014753#endif
14754#ifdef _SC_STACK_PROT
Victor Stinner8c62be82010-05-06 00:08:46 +000014755 {"SC_STACK_PROT", _SC_STACK_PROT},
Fred Drakec9680921999-12-13 16:37:25 +000014756#endif
14757#ifdef _SC_STREAM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014758 {"SC_STREAM_MAX", _SC_STREAM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014759#endif
14760#ifdef _SC_SYNCHRONIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014761 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014762#endif
14763#ifdef _SC_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014764 {"SC_THREADS", _SC_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014765#endif
14766#ifdef _SC_THREAD_ATTR_STACKADDR
Victor Stinner8c62be82010-05-06 00:08:46 +000014767 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
Fred Drakec9680921999-12-13 16:37:25 +000014768#endif
14769#ifdef _SC_THREAD_ATTR_STACKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014770 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014771#endif
14772#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014773 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014774#endif
14775#ifdef _SC_THREAD_KEYS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014776 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014777#endif
14778#ifdef _SC_THREAD_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014779 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014780#endif
14781#ifdef _SC_THREAD_PRIO_INHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014782 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
Fred Drakec9680921999-12-13 16:37:25 +000014783#endif
14784#ifdef _SC_THREAD_PRIO_PROTECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014785 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
Fred Drakec9680921999-12-13 16:37:25 +000014786#endif
14787#ifdef _SC_THREAD_PROCESS_SHARED
Victor Stinner8c62be82010-05-06 00:08:46 +000014788 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
Fred Drakec9680921999-12-13 16:37:25 +000014789#endif
14790#ifdef _SC_THREAD_SAFE_FUNCTIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014791 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014792#endif
14793#ifdef _SC_THREAD_STACK_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014794 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014795#endif
14796#ifdef _SC_THREAD_THREADS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014797 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014798#endif
14799#ifdef _SC_TIMERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014800 {"SC_TIMERS", _SC_TIMERS},
Fred Drakec9680921999-12-13 16:37:25 +000014801#endif
14802#ifdef _SC_TIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014803 {"SC_TIMER_MAX", _SC_TIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014804#endif
14805#ifdef _SC_TTY_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014806 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014807#endif
14808#ifdef _SC_TZNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014809 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014810#endif
14811#ifdef _SC_T_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014812 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014813#endif
14814#ifdef _SC_UCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014815 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014816#endif
14817#ifdef _SC_UINT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014818 {"SC_UINT_MAX", _SC_UINT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014819#endif
14820#ifdef _SC_UIO_MAXIOV
Victor Stinner8c62be82010-05-06 00:08:46 +000014821 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
Fred Drakec9680921999-12-13 16:37:25 +000014822#endif
14823#ifdef _SC_ULONG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014824 {"SC_ULONG_MAX", _SC_ULONG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014825#endif
14826#ifdef _SC_USHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014827 {"SC_USHRT_MAX", _SC_USHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014828#endif
14829#ifdef _SC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014830 {"SC_VERSION", _SC_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014831#endif
14832#ifdef _SC_WORD_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014833 {"SC_WORD_BIT", _SC_WORD_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014834#endif
14835#ifdef _SC_XBS5_ILP32_OFF32
Victor Stinner8c62be82010-05-06 00:08:46 +000014836 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
Fred Drakec9680921999-12-13 16:37:25 +000014837#endif
14838#ifdef _SC_XBS5_ILP32_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014839 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014840#endif
14841#ifdef _SC_XBS5_LP64_OFF64
Victor Stinner8c62be82010-05-06 00:08:46 +000014842 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
Fred Drakec9680921999-12-13 16:37:25 +000014843#endif
14844#ifdef _SC_XBS5_LPBIG_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014845 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014846#endif
14847#ifdef _SC_XOPEN_CRYPT
Victor Stinner8c62be82010-05-06 00:08:46 +000014848 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
Fred Drakec9680921999-12-13 16:37:25 +000014849#endif
14850#ifdef _SC_XOPEN_ENH_I18N
Victor Stinner8c62be82010-05-06 00:08:46 +000014851 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
Fred Drakec9680921999-12-13 16:37:25 +000014852#endif
14853#ifdef _SC_XOPEN_LEGACY
Victor Stinner8c62be82010-05-06 00:08:46 +000014854 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
Fred Drakec9680921999-12-13 16:37:25 +000014855#endif
14856#ifdef _SC_XOPEN_REALTIME
Victor Stinner8c62be82010-05-06 00:08:46 +000014857 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
Fred Drakec9680921999-12-13 16:37:25 +000014858#endif
14859#ifdef _SC_XOPEN_REALTIME_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014860 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014861#endif
14862#ifdef _SC_XOPEN_SHM
Victor Stinner8c62be82010-05-06 00:08:46 +000014863 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
Fred Drakec9680921999-12-13 16:37:25 +000014864#endif
14865#ifdef _SC_XOPEN_UNIX
Victor Stinner8c62be82010-05-06 00:08:46 +000014866 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
Fred Drakec9680921999-12-13 16:37:25 +000014867#endif
14868#ifdef _SC_XOPEN_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014869 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014870#endif
14871#ifdef _SC_XOPEN_XCU_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014872 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014873#endif
14874#ifdef _SC_XOPEN_XPG2
Victor Stinner8c62be82010-05-06 00:08:46 +000014875 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
Fred Drakec9680921999-12-13 16:37:25 +000014876#endif
14877#ifdef _SC_XOPEN_XPG3
Victor Stinner8c62be82010-05-06 00:08:46 +000014878 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
Fred Drakec9680921999-12-13 16:37:25 +000014879#endif
14880#ifdef _SC_XOPEN_XPG4
Victor Stinner8c62be82010-05-06 00:08:46 +000014881 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
Fred Drakec9680921999-12-13 16:37:25 +000014882#endif
14883};
14884
14885static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014886conv_sysconf_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014887{
14888 return conv_confname(arg, valuep, posix_constants_sysconf,
14889 sizeof(posix_constants_sysconf)
14890 / sizeof(struct constdef));
14891}
14892
Larry Hastings2f936352014-08-05 14:04:04 +100014893
14894/*[clinic input]
14895os.sysconf -> long
14896 name: sysconf_confname
14897 /
14898
14899Return an integer-valued system configuration variable.
14900[clinic start generated code]*/
14901
14902PyDoc_STRVAR(os_sysconf__doc__,
14903"sysconf($module, name, /)\n"
14904"--\n"
14905"\n"
14906"Return an integer-valued system configuration variable.");
14907
14908#define OS_SYSCONF_METHODDEF \
14909 {"sysconf", (PyCFunction)os_sysconf, METH_VARARGS, os_sysconf__doc__},
14910
14911static long
14912os_sysconf_impl(PyModuleDef *module, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014913
14914static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014915os_sysconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014916{
Larry Hastings2f936352014-08-05 14:04:04 +100014917 PyObject *return_value = NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014918 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014919 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014920
Larry Hastings2f936352014-08-05 14:04:04 +100014921 if (!PyArg_ParseTuple(args,
14922 "O&:sysconf",
14923 conv_sysconf_confname, &name))
14924 goto exit;
14925 _return_value = os_sysconf_impl(module, name);
14926 if ((_return_value == -1) && PyErr_Occurred())
14927 goto exit;
14928 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014929
Larry Hastings2f936352014-08-05 14:04:04 +100014930exit:
14931 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014932}
Larry Hastings2f936352014-08-05 14:04:04 +100014933
14934static long
14935os_sysconf_impl(PyModuleDef *module, int name)
14936/*[clinic end generated code: output=7b06dfdc472431e4 input=279e3430a33f29e4]*/
14937{
14938 long value;
14939
14940 errno = 0;
14941 value = sysconf(name);
14942 if (value == -1 && errno != 0)
14943 posix_error();
14944 return value;
14945}
14946#endif /* HAVE_SYSCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014947
14948
Fred Drakebec628d1999-12-15 18:31:10 +000014949/* This code is used to ensure that the tables of configuration value names
14950 * are in sorted order as required by conv_confname(), and also to build the
14951 * the exported dictionaries that are used to publish information about the
14952 * names available on the host platform.
14953 *
14954 * Sorting the table at runtime ensures that the table is properly ordered
14955 * when used, even for platforms we're not able to test on. It also makes
14956 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +000014957 */
Fred Drakebec628d1999-12-15 18:31:10 +000014958
14959static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014960cmp_constdefs(const void *v1, const void *v2)
Fred Drakebec628d1999-12-15 18:31:10 +000014961{
14962 const struct constdef *c1 =
Victor Stinner8c62be82010-05-06 00:08:46 +000014963 (const struct constdef *) v1;
Fred Drakebec628d1999-12-15 18:31:10 +000014964 const struct constdef *c2 =
Victor Stinner8c62be82010-05-06 00:08:46 +000014965 (const struct constdef *) v2;
Fred Drakebec628d1999-12-15 18:31:10 +000014966
14967 return strcmp(c1->name, c2->name);
14968}
14969
14970static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014971setup_confname_table(struct constdef *table, size_t tablesize,
Victor Stinner8c62be82010-05-06 00:08:46 +000014972 char *tablename, PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000014973{
Fred Drakebec628d1999-12-15 18:31:10 +000014974 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +000014975 size_t i;
Fred Drakebec628d1999-12-15 18:31:10 +000014976
14977 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
14978 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +000014979 if (d == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +000014980 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000014981
Barry Warsaw3155db32000-04-13 15:20:40 +000014982 for (i=0; i < tablesize; ++i) {
Victor Stinner8c62be82010-05-06 00:08:46 +000014983 PyObject *o = PyLong_FromLong(table[i].value);
14984 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
14985 Py_XDECREF(o);
14986 Py_DECREF(d);
14987 return -1;
14988 }
14989 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +000014990 }
Fred Drake4d1e64b2002-04-15 19:40:07 +000014991 return PyModule_AddObject(module, tablename, d);
Fred Draked86ed291999-12-15 15:34:33 +000014992}
14993
Fred Drakebec628d1999-12-15 18:31:10 +000014994/* Return -1 on failure, 0 on success. */
14995static int
Fred Drake4d1e64b2002-04-15 19:40:07 +000014996setup_confname_tables(PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000014997{
14998#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +000014999 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +000015000 sizeof(posix_constants_pathconf)
15001 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015002 "pathconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015003 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015004#endif
15005#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +000015006 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +000015007 sizeof(posix_constants_confstr)
15008 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015009 "confstr_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015010 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015011#endif
15012#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +000015013 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +000015014 sizeof(posix_constants_sysconf)
15015 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015016 "sysconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015017 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015018#endif
Fred Drakebec628d1999-12-15 18:31:10 +000015019 return 0;
Fred Draked86ed291999-12-15 15:34:33 +000015020}
Fred Draked86ed291999-12-15 15:34:33 +000015021
15022
Larry Hastings2f936352014-08-05 14:04:04 +100015023/*[clinic input]
15024os.abort
15025
15026Abort the interpreter immediately.
15027
15028This function 'dumps core' or otherwise fails in the hardest way possible
15029on the hosting operating system. This function never returns.
15030[clinic start generated code]*/
15031
15032PyDoc_STRVAR(os_abort__doc__,
15033"abort($module, /)\n"
15034"--\n"
15035"\n"
15036"Abort the interpreter immediately.\n"
15037"\n"
15038"This function \'dumps core\' or otherwise fails in the hardest way possible\n"
15039"on the hosting operating system. This function never returns.");
15040
15041#define OS_ABORT_METHODDEF \
15042 {"abort", (PyCFunction)os_abort, METH_NOARGS, os_abort__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015043
15044static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015045os_abort_impl(PyModuleDef *module);
15046
15047static PyObject *
15048os_abort(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15049{
15050 return os_abort_impl(module);
15051}
15052
15053static PyObject *
15054os_abort_impl(PyModuleDef *module)
15055/*[clinic end generated code: output=cded2cc8c5453d3a input=cf2c7d98bc504047]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015056{
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015057 abort();
15058 /*NOTREACHED*/
15059 Py_FatalError("abort() called from Python code didn't abort!");
15060 return NULL;
15061}
Fred Drakebec628d1999-12-15 18:31:10 +000015062
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000015063#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100015064/* AC 3.5: change to path_t? but that might change exceptions */
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015065PyDoc_STRVAR(win32_startfile__doc__,
Larry Hastings2f936352014-08-05 14:04:04 +100015066"startfile(filepath [, operation])\n\
15067\n\
15068Start a file with its associated application.\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015069\n\
Georg Brandlf4f44152006-02-18 22:29:33 +000015070When \"operation\" is not specified or \"open\", this acts like\n\
15071double-clicking the file in Explorer, or giving the file name as an\n\
15072argument to the DOS \"start\" command: the file is opened with whatever\n\
15073application (if any) its extension is associated.\n\
15074When another \"operation\" is given, it specifies what should be done with\n\
15075the file. A typical operation is \"print\".\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015076\n\
15077startfile returns as soon as the associated application is launched.\n\
15078There is no option to wait for the application to close, and no way\n\
15079to retrieve the application's exit status.\n\
15080\n\
15081The filepath is relative to the current directory. If you want to use\n\
15082an absolute path, make sure the first character is not a slash (\"/\");\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015083the underlying Win32 ShellExecute function doesn't work if it is.");
Tim Petersf58a7aa2000-09-22 10:05:54 +000015084
15085static PyObject *
15086win32_startfile(PyObject *self, PyObject *args)
15087{
Victor Stinner8c62be82010-05-06 00:08:46 +000015088 PyObject *ofilepath;
15089 char *filepath;
15090 char *operation = NULL;
Victor Stinnereb5657a2011-09-30 01:44:27 +020015091 wchar_t *wpath, *woperation;
Victor Stinner8c62be82010-05-06 00:08:46 +000015092 HINSTANCE rc;
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +000015093
Victor Stinnereb5657a2011-09-30 01:44:27 +020015094 PyObject *unipath, *uoperation = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015095 if (!PyArg_ParseTuple(args, "U|s:startfile",
15096 &unipath, &operation)) {
15097 PyErr_Clear();
15098 goto normal;
15099 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015100
Victor Stinner8c62be82010-05-06 00:08:46 +000015101 if (operation) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015102 uoperation = PyUnicode_DecodeASCII(operation,
Victor Stinner8c62be82010-05-06 00:08:46 +000015103 strlen(operation), NULL);
Victor Stinnereb5657a2011-09-30 01:44:27 +020015104 if (!uoperation) {
Victor Stinner8c62be82010-05-06 00:08:46 +000015105 PyErr_Clear();
15106 operation = NULL;
15107 goto normal;
15108 }
15109 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015110
Victor Stinnereb5657a2011-09-30 01:44:27 +020015111 wpath = PyUnicode_AsUnicode(unipath);
15112 if (wpath == NULL)
15113 goto normal;
15114 if (uoperation) {
15115 woperation = PyUnicode_AsUnicode(uoperation);
15116 if (woperation == NULL)
15117 goto normal;
15118 }
15119 else
15120 woperation = NULL;
15121
Victor Stinner8c62be82010-05-06 00:08:46 +000015122 Py_BEGIN_ALLOW_THREADS
Victor Stinnereb5657a2011-09-30 01:44:27 +020015123 rc = ShellExecuteW((HWND)0, woperation, wpath,
15124 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000015125 Py_END_ALLOW_THREADS
15126
Victor Stinnereb5657a2011-09-30 01:44:27 +020015127 Py_XDECREF(uoperation);
Victor Stinner8c62be82010-05-06 00:08:46 +000015128 if (rc <= (HINSTANCE)32) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015129 win32_error_object("startfile", unipath);
15130 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015131 }
15132 Py_INCREF(Py_None);
15133 return Py_None;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000015134
15135normal:
Victor Stinner8c62be82010-05-06 00:08:46 +000015136 if (!PyArg_ParseTuple(args, "O&|s:startfile",
15137 PyUnicode_FSConverter, &ofilepath,
15138 &operation))
15139 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +010015140 if (win32_warn_bytes_api()) {
15141 Py_DECREF(ofilepath);
15142 return NULL;
15143 }
Victor Stinner8c62be82010-05-06 00:08:46 +000015144 filepath = PyBytes_AsString(ofilepath);
15145 Py_BEGIN_ALLOW_THREADS
15146 rc = ShellExecute((HWND)0, operation, filepath,
15147 NULL, NULL, SW_SHOWNORMAL);
15148 Py_END_ALLOW_THREADS
15149 if (rc <= (HINSTANCE)32) {
15150 PyObject *errval = win32_error("startfile", filepath);
15151 Py_DECREF(ofilepath);
15152 return errval;
15153 }
15154 Py_DECREF(ofilepath);
15155 Py_INCREF(Py_None);
15156 return Py_None;
Tim Petersf58a7aa2000-09-22 10:05:54 +000015157}
Larry Hastings2f936352014-08-05 14:04:04 +100015158#endif /* MS_WINDOWS */
15159
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015160
Martin v. Löwis438b5342002-12-27 10:16:42 +000015161#ifdef HAVE_GETLOADAVG
Larry Hastings2f936352014-08-05 14:04:04 +100015162/*[clinic input]
15163os.getloadavg
15164
15165Return average recent system load information.
15166
15167Return the number of processes in the system run queue averaged over
15168the last 1, 5, and 15 minutes as a tuple of three floats.
15169Raises OSError if the load average was unobtainable.
15170[clinic start generated code]*/
15171
15172PyDoc_STRVAR(os_getloadavg__doc__,
15173"getloadavg($module, /)\n"
15174"--\n"
15175"\n"
15176"Return average recent system load information.\n"
15177"\n"
15178"Return the number of processes in the system run queue averaged over\n"
15179"the last 1, 5, and 15 minutes as a tuple of three floats.\n"
15180"Raises OSError if the load average was unobtainable.");
15181
15182#define OS_GETLOADAVG_METHODDEF \
15183 {"getloadavg", (PyCFunction)os_getloadavg, METH_NOARGS, os_getloadavg__doc__},
Martin v. Löwis438b5342002-12-27 10:16:42 +000015184
15185static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015186os_getloadavg_impl(PyModuleDef *module);
15187
15188static PyObject *
15189os_getloadavg(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15190{
15191 return os_getloadavg_impl(module);
15192}
15193
15194static PyObject *
15195os_getloadavg_impl(PyModuleDef *module)
15196/*[clinic end generated code: output=67593a92457d55af input=3d6d826b76d8a34e]*/
Martin v. Löwis438b5342002-12-27 10:16:42 +000015197{
15198 double loadavg[3];
Martin v. Löwis438b5342002-12-27 10:16:42 +000015199 if (getloadavg(loadavg, 3)!=3) {
Stefan Krah0e803b32010-11-26 16:16:47 +000015200 PyErr_SetString(PyExc_OSError, "Load averages are unobtainable");
15201 return NULL;
Martin v. Löwis438b5342002-12-27 10:16:42 +000015202 } else
Stefan Krah0e803b32010-11-26 16:16:47 +000015203 return Py_BuildValue("ddd", loadavg[0], loadavg[1], loadavg[2]);
Martin v. Löwis438b5342002-12-27 10:16:42 +000015204}
Larry Hastings2f936352014-08-05 14:04:04 +100015205#endif /* HAVE_GETLOADAVG */
Martin v. Löwis438b5342002-12-27 10:16:42 +000015206
Larry Hastings2f936352014-08-05 14:04:04 +100015207
15208/*[clinic input]
15209os.device_encoding
15210 fd: int
15211
15212Return a string describing the encoding of a terminal's file descriptor.
15213
15214The file descriptor must be attached to a terminal.
15215If the device is not a terminal, return None.
15216[clinic start generated code]*/
15217
15218PyDoc_STRVAR(os_device_encoding__doc__,
15219"device_encoding($module, /, fd)\n"
15220"--\n"
15221"\n"
15222"Return a string describing the encoding of a terminal\'s file descriptor.\n"
15223"\n"
15224"The file descriptor must be attached to a terminal.\n"
15225"If the device is not a terminal, return None.");
15226
15227#define OS_DEVICE_ENCODING_METHODDEF \
15228 {"device_encoding", (PyCFunction)os_device_encoding, METH_VARARGS|METH_KEYWORDS, os_device_encoding__doc__},
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015229
15230static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015231os_device_encoding_impl(PyModuleDef *module, int fd);
15232
15233static PyObject *
15234os_device_encoding(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015235{
Larry Hastings2f936352014-08-05 14:04:04 +100015236 PyObject *return_value = NULL;
15237 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000015238 int fd;
Brett Cannonefb00c02012-02-29 18:31:31 -050015239
Larry Hastings2f936352014-08-05 14:04:04 +100015240 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15241 "i:device_encoding", _keywords,
15242 &fd))
15243 goto exit;
15244 return_value = os_device_encoding_impl(module, fd);
Brett Cannonefb00c02012-02-29 18:31:31 -050015245
Larry Hastings2f936352014-08-05 14:04:04 +100015246exit:
15247 return return_value;
15248}
15249
15250static PyObject *
15251os_device_encoding_impl(PyModuleDef *module, int fd)
15252/*[clinic end generated code: output=e9f8274d42f5cce3 input=9e1d4a42b66df312]*/
15253{
Brett Cannonefb00c02012-02-29 18:31:31 -050015254 return _Py_device_encoding(fd);
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015255}
15256
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015257
Larry Hastings2f936352014-08-05 14:04:04 +100015258#ifdef HAVE_SETRESUID
15259/*[clinic input]
15260os.setresuid
15261
15262 ruid: uid_t
15263 euid: uid_t
15264 suid: uid_t
15265 /
15266
15267Set the current process's real, effective, and saved user ids.
15268[clinic start generated code]*/
15269
15270PyDoc_STRVAR(os_setresuid__doc__,
15271"setresuid($module, ruid, euid, suid, /)\n"
15272"--\n"
15273"\n"
15274"Set the current process\'s real, effective, and saved user ids.");
15275
15276#define OS_SETRESUID_METHODDEF \
15277 {"setresuid", (PyCFunction)os_setresuid, METH_VARARGS, os_setresuid__doc__},
15278
15279static PyObject *
15280os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid);
15281
15282static PyObject *
15283os_setresuid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015284{
Larry Hastings2f936352014-08-05 14:04:04 +100015285 PyObject *return_value = NULL;
15286 uid_t ruid;
15287 uid_t euid;
15288 uid_t suid;
15289
15290 if (!PyArg_ParseTuple(args,
15291 "O&O&O&:setresuid",
15292 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid, _Py_Uid_Converter, &suid))
15293 goto exit;
15294 return_value = os_setresuid_impl(module, ruid, euid, suid);
15295
15296exit:
15297 return return_value;
15298}
15299
15300static PyObject *
15301os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid)
15302/*[clinic end generated code: output=2e3457cfe7cd1f94 input=9e33cb79a82792f3]*/
15303{
Victor Stinner8c62be82010-05-06 00:08:46 +000015304 if (setresuid(ruid, euid, suid) < 0)
15305 return posix_error();
15306 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015307}
Larry Hastings2f936352014-08-05 14:04:04 +100015308#endif /* HAVE_SETRESUID */
15309
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015310
15311#ifdef HAVE_SETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015312/*[clinic input]
15313os.setresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015314
Larry Hastings2f936352014-08-05 14:04:04 +100015315 rgid: gid_t
15316 egid: gid_t
15317 sgid: gid_t
15318 /
15319
15320Set the current process's real, effective, and saved group ids.
15321[clinic start generated code]*/
15322
15323PyDoc_STRVAR(os_setresgid__doc__,
15324"setresgid($module, rgid, egid, sgid, /)\n"
15325"--\n"
15326"\n"
15327"Set the current process\'s real, effective, and saved group ids.");
15328
15329#define OS_SETRESGID_METHODDEF \
15330 {"setresgid", (PyCFunction)os_setresgid, METH_VARARGS, os_setresgid__doc__},
15331
15332static PyObject *
15333os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid);
15334
15335static PyObject *
15336os_setresgid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015337{
Larry Hastings2f936352014-08-05 14:04:04 +100015338 PyObject *return_value = NULL;
15339 gid_t rgid;
15340 gid_t egid;
15341 gid_t sgid;
15342
15343 if (!PyArg_ParseTuple(args,
15344 "O&O&O&:setresgid",
15345 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid, _Py_Gid_Converter, &sgid))
15346 goto exit;
15347 return_value = os_setresgid_impl(module, rgid, egid, sgid);
15348
15349exit:
15350 return return_value;
15351}
15352
15353static PyObject *
15354os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid)
15355/*[clinic end generated code: output=8a7ee6c1f2482362 input=33e9e0785ef426b1]*/
15356{
Victor Stinner8c62be82010-05-06 00:08:46 +000015357 if (setresgid(rgid, egid, sgid) < 0)
15358 return posix_error();
15359 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015360}
Larry Hastings2f936352014-08-05 14:04:04 +100015361#endif /* HAVE_SETRESGID */
15362
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015363
15364#ifdef HAVE_GETRESUID
Larry Hastings2f936352014-08-05 14:04:04 +100015365/*[clinic input]
15366os.getresuid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015367
Larry Hastings2f936352014-08-05 14:04:04 +100015368Return a tuple of the current process's real, effective, and saved user ids.
15369[clinic start generated code]*/
15370
15371PyDoc_STRVAR(os_getresuid__doc__,
15372"getresuid($module, /)\n"
15373"--\n"
15374"\n"
15375"Return a tuple of the current process\'s real, effective, and saved user ids.");
15376
15377#define OS_GETRESUID_METHODDEF \
15378 {"getresuid", (PyCFunction)os_getresuid, METH_NOARGS, os_getresuid__doc__},
15379
15380static PyObject *
15381os_getresuid_impl(PyModuleDef *module);
15382
15383static PyObject *
15384os_getresuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15385{
15386 return os_getresuid_impl(module);
15387}
15388
15389static PyObject *
15390os_getresuid_impl(PyModuleDef *module)
15391/*[clinic end generated code: output=d0786686a6ef1320 input=41ccfa8e1f6517ad]*/
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015392{
Victor Stinner8c62be82010-05-06 00:08:46 +000015393 uid_t ruid, euid, suid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015394 if (getresuid(&ruid, &euid, &suid) < 0)
15395 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015396 return Py_BuildValue("(NNN)", _PyLong_FromUid(ruid),
15397 _PyLong_FromUid(euid),
15398 _PyLong_FromUid(suid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015399}
Larry Hastings2f936352014-08-05 14:04:04 +100015400#endif /* HAVE_GETRESUID */
15401
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015402
15403#ifdef HAVE_GETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015404/*[clinic input]
15405os.getresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015406
Larry Hastings2f936352014-08-05 14:04:04 +100015407Return a tuple of the current process's real, effective, and saved group ids.
15408[clinic start generated code]*/
15409
15410PyDoc_STRVAR(os_getresgid__doc__,
15411"getresgid($module, /)\n"
15412"--\n"
15413"\n"
15414"Return a tuple of the current process\'s real, effective, and saved group ids.");
15415
15416#define OS_GETRESGID_METHODDEF \
15417 {"getresgid", (PyCFunction)os_getresgid, METH_NOARGS, os_getresgid__doc__},
15418
15419static PyObject *
15420os_getresgid_impl(PyModuleDef *module);
15421
15422static PyObject *
15423os_getresgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015424{
Larry Hastings2f936352014-08-05 14:04:04 +100015425 return os_getresgid_impl(module);
15426}
15427
15428static PyObject *
15429os_getresgid_impl(PyModuleDef *module)
15430/*[clinic end generated code: output=05249ac795fa759f input=517e68db9ca32df6]*/
15431{
15432 gid_t rgid, egid, sgid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015433 if (getresgid(&rgid, &egid, &sgid) < 0)
15434 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015435 return Py_BuildValue("(NNN)", _PyLong_FromGid(rgid),
15436 _PyLong_FromGid(egid),
15437 _PyLong_FromGid(sgid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015438}
Larry Hastings2f936352014-08-05 14:04:04 +100015439#endif /* HAVE_GETRESGID */
15440
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015441
Benjamin Peterson9428d532011-09-14 11:45:52 -040015442#ifdef USE_XATTRS
Larry Hastings2f936352014-08-05 14:04:04 +100015443/*[clinic input]
15444os.getxattr
Benjamin Peterson799bd802011-08-31 22:15:17 -040015445
Larry Hastings2f936352014-08-05 14:04:04 +100015446 path: path_t(allow_fd=True)
15447 attribute: path_t
15448 *
15449 follow_symlinks: bool = True
15450
15451Return the value of extended attribute attribute on path.
15452
15453path may be either a string or an open file descriptor.
15454If follow_symlinks is False, and the last element of the path is a symbolic
15455 link, getxattr will examine the symbolic link itself instead of the file
15456 the link points to.
15457
15458[clinic start generated code]*/
15459
15460PyDoc_STRVAR(os_getxattr__doc__,
15461"getxattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15462"--\n"
15463"\n"
15464"Return the value of extended attribute attribute on path.\n"
15465"\n"
15466"path may be either a string or an open file descriptor.\n"
15467"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15468" link, getxattr will examine the symbolic link itself instead of the file\n"
15469" the link points to.");
15470
15471#define OS_GETXATTR_METHODDEF \
15472 {"getxattr", (PyCFunction)os_getxattr, METH_VARARGS|METH_KEYWORDS, os_getxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015473
15474static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015475os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15476
15477static PyObject *
15478os_getxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015479{
Larry Hastings2f936352014-08-05 14:04:04 +100015480 PyObject *return_value = NULL;
15481 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15482 path_t path = PATH_T_INITIALIZE("getxattr", "path", 0, 1);
15483 path_t attribute = PATH_T_INITIALIZE("getxattr", "attribute", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015484 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015485
Larry Hastings2f936352014-08-05 14:04:04 +100015486 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15487 "O&O&|$p:getxattr", _keywords,
15488 path_converter, &path, path_converter, &attribute, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015489 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015490 return_value = os_getxattr_impl(module, &path, &attribute, follow_symlinks);
15491
15492exit:
15493 /* Cleanup for path */
15494 path_cleanup(&path);
15495 /* Cleanup for attribute */
15496 path_cleanup(&attribute);
15497
15498 return return_value;
15499}
15500
15501static PyObject *
15502os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15503/*[clinic end generated code: output=bbc9454fe2b9ea86 input=8c8ea3bab78d89c2]*/
15504{
15505 Py_ssize_t i;
15506 PyObject *buffer = NULL;
15507
15508 if (fd_and_follow_symlinks_invalid("getxattr", path->fd, follow_symlinks))
15509 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015510
Larry Hastings9cf065c2012-06-22 16:30:09 -070015511 for (i = 0; ; i++) {
15512 void *ptr;
15513 ssize_t result;
15514 static Py_ssize_t buffer_sizes[] = {128, XATTR_SIZE_MAX, 0};
15515 Py_ssize_t buffer_size = buffer_sizes[i];
15516 if (!buffer_size) {
Larry Hastings2f936352014-08-05 14:04:04 +100015517 path_error(path);
15518 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015519 }
15520 buffer = PyBytes_FromStringAndSize(NULL, buffer_size);
15521 if (!buffer)
Larry Hastings2f936352014-08-05 14:04:04 +100015522 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015523 ptr = PyBytes_AS_STRING(buffer);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015524
Larry Hastings9cf065c2012-06-22 16:30:09 -070015525 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015526 if (path->fd >= 0)
15527 result = fgetxattr(path->fd, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015528 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015529 result = getxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015530 else
Larry Hastings2f936352014-08-05 14:04:04 +100015531 result = lgetxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015532 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015533
Larry Hastings9cf065c2012-06-22 16:30:09 -070015534 if (result < 0) {
15535 Py_DECREF(buffer);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015536 if (errno == ERANGE)
15537 continue;
Larry Hastings2f936352014-08-05 14:04:04 +100015538 path_error(path);
15539 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015540 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015541
Larry Hastings9cf065c2012-06-22 16:30:09 -070015542 if (result != buffer_size) {
15543 /* Can only shrink. */
15544 _PyBytes_Resize(&buffer, result);
15545 }
15546 break;
15547 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015548
Larry Hastings9cf065c2012-06-22 16:30:09 -070015549 return buffer;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015550}
15551
Larry Hastings2f936352014-08-05 14:04:04 +100015552
15553/*[clinic input]
15554os.setxattr
15555
15556 path: path_t(allow_fd=True)
15557 attribute: path_t
15558 value: Py_buffer
15559 flags: int = 0
15560 *
15561 follow_symlinks: bool = True
15562
15563Set extended attribute attribute on path to value.
15564
15565path may be either a string or an open file descriptor.
15566If follow_symlinks is False, and the last element of the path is a symbolic
15567 link, setxattr will modify the symbolic link itself instead of the file
15568 the link points to.
15569
15570[clinic start generated code]*/
15571
15572PyDoc_STRVAR(os_setxattr__doc__,
15573"setxattr($module, /, path, attribute, value, flags=0, *,\n"
15574" follow_symlinks=True)\n"
15575"--\n"
15576"\n"
15577"Set extended attribute attribute on path to value.\n"
15578"\n"
15579"path may be either a string or an open file descriptor.\n"
15580"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15581" link, setxattr will modify the symbolic link itself instead of the file\n"
15582" the link points to.");
15583
15584#define OS_SETXATTR_METHODDEF \
15585 {"setxattr", (PyCFunction)os_setxattr, METH_VARARGS|METH_KEYWORDS, os_setxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015586
15587static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015588os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks);
15589
15590static PyObject *
15591os_setxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015592{
Larry Hastings2f936352014-08-05 14:04:04 +100015593 PyObject *return_value = NULL;
15594 static char *_keywords[] = {"path", "attribute", "value", "flags", "follow_symlinks", NULL};
15595 path_t path = PATH_T_INITIALIZE("setxattr", "path", 0, 1);
15596 path_t attribute = PATH_T_INITIALIZE("setxattr", "attribute", 0, 0);
15597 Py_buffer value = {NULL, NULL};
Larry Hastings9cf065c2012-06-22 16:30:09 -070015598 int flags = 0;
15599 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015600
Larry Hastings2f936352014-08-05 14:04:04 +100015601 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15602 "O&O&y*|i$p:setxattr", _keywords,
15603 path_converter, &path, path_converter, &attribute, &value, &flags, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015604 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015605 return_value = os_setxattr_impl(module, &path, &attribute, &value, flags, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015606
Larry Hastings9cf065c2012-06-22 16:30:09 -070015607exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015608 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015609 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015610 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015611 path_cleanup(&attribute);
Larry Hastings2f936352014-08-05 14:04:04 +100015612 /* Cleanup for value */
15613 if (value.obj)
15614 PyBuffer_Release(&value);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015615
Larry Hastings9cf065c2012-06-22 16:30:09 -070015616 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015617}
15618
Benjamin Peterson799bd802011-08-31 22:15:17 -040015619static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015620os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks)
15621/*[clinic end generated code: output=2ff845d8e024b218 input=f0d26833992015c2]*/
Benjamin Peterson799bd802011-08-31 22:15:17 -040015622{
Larry Hastings2f936352014-08-05 14:04:04 +100015623 ssize_t result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015624
Larry Hastings2f936352014-08-05 14:04:04 +100015625 if (fd_and_follow_symlinks_invalid("setxattr", path->fd, follow_symlinks))
Benjamin Peterson799bd802011-08-31 22:15:17 -040015626 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015627
Benjamin Peterson799bd802011-08-31 22:15:17 -040015628 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015629 if (path->fd > -1)
15630 result = fsetxattr(path->fd, attribute->narrow,
15631 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015632 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015633 result = setxattr(path->narrow, attribute->narrow,
15634 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015635 else
Larry Hastings2f936352014-08-05 14:04:04 +100015636 result = lsetxattr(path->narrow, attribute->narrow,
15637 value->buf, value->len, flags);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015638 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015639
Larry Hastings9cf065c2012-06-22 16:30:09 -070015640 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100015641 path_error(path);
15642 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015643 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015644
Larry Hastings2f936352014-08-05 14:04:04 +100015645 Py_RETURN_NONE;
15646}
15647
15648
15649/*[clinic input]
15650os.removexattr
15651
15652 path: path_t(allow_fd=True)
15653 attribute: path_t
15654 *
15655 follow_symlinks: bool = True
15656
15657Remove extended attribute attribute on path.
15658
15659path may be either a string or an open file descriptor.
15660If follow_symlinks is False, and the last element of the path is a symbolic
15661 link, removexattr will modify the symbolic link itself instead of the file
15662 the link points to.
15663
15664[clinic start generated code]*/
15665
15666PyDoc_STRVAR(os_removexattr__doc__,
15667"removexattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15668"--\n"
15669"\n"
15670"Remove extended attribute attribute on path.\n"
15671"\n"
15672"path may be either a string or an open file descriptor.\n"
15673"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15674" link, removexattr will modify the symbolic link itself instead of the file\n"
15675" the link points to.");
15676
15677#define OS_REMOVEXATTR_METHODDEF \
15678 {"removexattr", (PyCFunction)os_removexattr, METH_VARARGS|METH_KEYWORDS, os_removexattr__doc__},
15679
15680static PyObject *
15681os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15682
15683static PyObject *
15684os_removexattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
15685{
15686 PyObject *return_value = NULL;
15687 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15688 path_t path = PATH_T_INITIALIZE("removexattr", "path", 0, 1);
15689 path_t attribute = PATH_T_INITIALIZE("removexattr", "attribute", 0, 0);
15690 int follow_symlinks = 1;
15691
15692 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15693 "O&O&|$p:removexattr", _keywords,
15694 path_converter, &path, path_converter, &attribute, &follow_symlinks))
15695 goto exit;
15696 return_value = os_removexattr_impl(module, &path, &attribute, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015697
Larry Hastings9cf065c2012-06-22 16:30:09 -070015698exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015699 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015700 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015701 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015702 path_cleanup(&attribute);
15703
15704 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015705}
15706
Larry Hastings2f936352014-08-05 14:04:04 +100015707static PyObject *
15708os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15709/*[clinic end generated code: output=8dfc715bf607c4cf input=cdb54834161e3329]*/
15710{
15711 ssize_t result;
15712
15713 if (fd_and_follow_symlinks_invalid("removexattr", path->fd, follow_symlinks))
15714 return NULL;
15715
15716 Py_BEGIN_ALLOW_THREADS;
15717 if (path->fd > -1)
15718 result = fremovexattr(path->fd, attribute->narrow);
15719 else if (follow_symlinks)
15720 result = removexattr(path->narrow, attribute->narrow);
15721 else
15722 result = lremovexattr(path->narrow, attribute->narrow);
15723 Py_END_ALLOW_THREADS;
15724
15725 if (result) {
15726 return path_error(path);
15727 }
15728
15729 Py_RETURN_NONE;
15730}
15731
15732
15733/*[clinic input]
15734os.listxattr
15735
15736 path: path_t(allow_fd=True, nullable=True) = None
15737 *
15738 follow_symlinks: bool = True
15739
15740Return a list of extended attributes on path.
15741
15742path may be either None, a string, or an open file descriptor.
15743if path is None, listxattr will examine the current directory.
15744If follow_symlinks is False, and the last element of the path is a symbolic
15745 link, listxattr will examine the symbolic link itself instead of the file
15746 the link points to.
15747[clinic start generated code]*/
15748
15749PyDoc_STRVAR(os_listxattr__doc__,
15750"listxattr($module, /, path=None, *, follow_symlinks=True)\n"
15751"--\n"
15752"\n"
15753"Return a list of extended attributes on path.\n"
15754"\n"
15755"path may be either None, a string, or an open file descriptor.\n"
15756"if path is None, listxattr will examine the current directory.\n"
15757"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15758" link, listxattr will examine the symbolic link itself instead of the file\n"
15759" the link points to.");
15760
15761#define OS_LISTXATTR_METHODDEF \
15762 {"listxattr", (PyCFunction)os_listxattr, METH_VARARGS|METH_KEYWORDS, os_listxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015763
15764static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015765os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks);
15766
15767static PyObject *
15768os_listxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015769{
Larry Hastings2f936352014-08-05 14:04:04 +100015770 PyObject *return_value = NULL;
15771 static char *_keywords[] = {"path", "follow_symlinks", NULL};
15772 path_t path = PATH_T_INITIALIZE("listxattr", "path", 1, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015773 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100015774
15775 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15776 "|O&$p:listxattr", _keywords,
15777 path_converter, &path, &follow_symlinks))
15778 goto exit;
15779 return_value = os_listxattr_impl(module, &path, follow_symlinks);
15780
15781exit:
15782 /* Cleanup for path */
15783 path_cleanup(&path);
15784
15785 return return_value;
15786}
15787
15788static PyObject *
15789os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks)
15790/*[clinic end generated code: output=3104cafda1a3d887 input=08cca53ac0b07c13]*/
15791{
Larry Hastings9cf065c2012-06-22 16:30:09 -070015792 Py_ssize_t i;
15793 PyObject *result = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100015794 const char *name;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015795 char *buffer = NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015796
Larry Hastings2f936352014-08-05 14:04:04 +100015797 if (fd_and_follow_symlinks_invalid("listxattr", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015798 goto exit;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015799
Larry Hastings2f936352014-08-05 14:04:04 +100015800 name = path->narrow ? path->narrow : ".";
15801
Larry Hastings9cf065c2012-06-22 16:30:09 -070015802 for (i = 0; ; i++) {
15803 char *start, *trace, *end;
15804 ssize_t length;
15805 static Py_ssize_t buffer_sizes[] = { 256, XATTR_LIST_MAX, 0 };
15806 Py_ssize_t buffer_size = buffer_sizes[i];
15807 if (!buffer_size) {
Christian Heimes3b9493b2012-09-23 16:11:15 +020015808 /* ERANGE */
Larry Hastings2f936352014-08-05 14:04:04 +100015809 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015810 break;
15811 }
15812 buffer = PyMem_MALLOC(buffer_size);
15813 if (!buffer) {
15814 PyErr_NoMemory();
15815 break;
15816 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015817
Larry Hastings9cf065c2012-06-22 16:30:09 -070015818 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015819 if (path->fd > -1)
15820 length = flistxattr(path->fd, buffer, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015821 else if (follow_symlinks)
15822 length = listxattr(name, buffer, buffer_size);
15823 else
15824 length = llistxattr(name, buffer, buffer_size);
15825 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015826
Larry Hastings9cf065c2012-06-22 16:30:09 -070015827 if (length < 0) {
Antoine Pitrou7f987392013-05-13 19:46:29 +020015828 if (errno == ERANGE) {
15829 PyMem_FREE(buffer);
Benjamin Petersondedac522013-05-13 19:55:40 -050015830 buffer = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015831 continue;
Antoine Pitrou7f987392013-05-13 19:46:29 +020015832 }
Larry Hastings2f936352014-08-05 14:04:04 +100015833 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015834 break;
15835 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015836
Larry Hastings9cf065c2012-06-22 16:30:09 -070015837 result = PyList_New(0);
15838 if (!result) {
15839 goto exit;
15840 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015841
Larry Hastings9cf065c2012-06-22 16:30:09 -070015842 end = buffer + length;
15843 for (trace = start = buffer; trace != end; trace++) {
15844 if (!*trace) {
15845 int error;
15846 PyObject *attribute = PyUnicode_DecodeFSDefaultAndSize(start,
15847 trace - start);
15848 if (!attribute) {
15849 Py_DECREF(result);
15850 result = NULL;
15851 goto exit;
15852 }
15853 error = PyList_Append(result, attribute);
15854 Py_DECREF(attribute);
15855 if (error) {
15856 Py_DECREF(result);
15857 result = NULL;
15858 goto exit;
15859 }
15860 start = trace + 1;
15861 }
15862 }
15863 break;
15864 }
15865exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070015866 if (buffer)
15867 PyMem_FREE(buffer);
15868 return result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015869}
Benjamin Peterson9428d532011-09-14 11:45:52 -040015870#endif /* USE_XATTRS */
Benjamin Peterson799bd802011-08-31 22:15:17 -040015871
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015872
Larry Hastings2f936352014-08-05 14:04:04 +100015873/*[clinic input]
15874os.urandom
15875
15876 size: Py_ssize_t
15877 /
15878
15879Return a bytes object containing random bytes suitable for cryptographic use.
15880[clinic start generated code]*/
15881
15882PyDoc_STRVAR(os_urandom__doc__,
15883"urandom($module, size, /)\n"
15884"--\n"
15885"\n"
15886"Return a bytes object containing random bytes suitable for cryptographic use.");
15887
15888#define OS_URANDOM_METHODDEF \
15889 {"urandom", (PyCFunction)os_urandom, METH_VARARGS, os_urandom__doc__},
Georg Brandl2fb477c2012-02-21 00:33:36 +010015890
15891static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015892os_urandom_impl(PyModuleDef *module, Py_ssize_t size);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015893
Larry Hastings2f936352014-08-05 14:04:04 +100015894static PyObject *
15895os_urandom(PyModuleDef *module, PyObject *args)
15896{
15897 PyObject *return_value = NULL;
15898 Py_ssize_t size;
15899
15900 if (!PyArg_ParseTuple(args,
15901 "n:urandom",
15902 &size))
15903 goto exit;
15904 return_value = os_urandom_impl(module, size);
15905
15906exit:
15907 return return_value;
15908}
15909
15910static PyObject *
15911os_urandom_impl(PyModuleDef *module, Py_ssize_t size)
15912/*[clinic end generated code: output=5dbff582cab94cb9 input=4067cdb1b6776c29]*/
15913{
15914 PyObject *bytes;
15915 int result;
15916
Georg Brandl2fb477c2012-02-21 00:33:36 +010015917 if (size < 0)
15918 return PyErr_Format(PyExc_ValueError,
15919 "negative argument not allowed");
Larry Hastings2f936352014-08-05 14:04:04 +100015920 bytes = PyBytes_FromStringAndSize(NULL, size);
15921 if (bytes == NULL)
Georg Brandl2fb477c2012-02-21 00:33:36 +010015922 return NULL;
15923
Larry Hastings2f936352014-08-05 14:04:04 +100015924 result = _PyOS_URandom(PyBytes_AS_STRING(bytes),
15925 PyBytes_GET_SIZE(bytes));
15926 if (result == -1) {
15927 Py_DECREF(bytes);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015928 return NULL;
15929 }
Larry Hastings2f936352014-08-05 14:04:04 +100015930 return bytes;
Georg Brandl2fb477c2012-02-21 00:33:36 +010015931}
15932
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015933/* Terminal size querying */
15934
15935static PyTypeObject TerminalSizeType;
15936
15937PyDoc_STRVAR(TerminalSize_docstring,
15938 "A tuple of (columns, lines) for holding terminal window size");
15939
15940static PyStructSequence_Field TerminalSize_fields[] = {
15941 {"columns", "width of the terminal window in characters"},
15942 {"lines", "height of the terminal window in characters"},
15943 {NULL, NULL}
15944};
15945
15946static PyStructSequence_Desc TerminalSize_desc = {
15947 "os.terminal_size",
15948 TerminalSize_docstring,
15949 TerminalSize_fields,
15950 2,
15951};
15952
15953#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
Larry Hastings2f936352014-08-05 14:04:04 +100015954/* AC 3.5: fd should accept None */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015955PyDoc_STRVAR(termsize__doc__,
15956 "Return the size of the terminal window as (columns, lines).\n" \
15957 "\n" \
15958 "The optional argument fd (default standard output) specifies\n" \
15959 "which file descriptor should be queried.\n" \
15960 "\n" \
15961 "If the file descriptor is not connected to a terminal, an OSError\n" \
15962 "is thrown.\n" \
15963 "\n" \
15964 "This function will only be defined if an implementation is\n" \
15965 "available for this system.\n" \
15966 "\n" \
15967 "shutil.get_terminal_size is the high-level function which should \n" \
15968 "normally be used, os.get_terminal_size is the low-level implementation.");
15969
15970static PyObject*
15971get_terminal_size(PyObject *self, PyObject *args)
15972{
15973 int columns, lines;
15974 PyObject *termsize;
15975
15976 int fd = fileno(stdout);
15977 /* Under some conditions stdout may not be connected and
15978 * fileno(stdout) may point to an invalid file descriptor. For example
15979 * GUI apps don't have valid standard streams by default.
15980 *
15981 * If this happens, and the optional fd argument is not present,
15982 * the ioctl below will fail returning EBADF. This is what we want.
15983 */
15984
15985 if (!PyArg_ParseTuple(args, "|i", &fd))
15986 return NULL;
15987
15988#ifdef TERMSIZE_USE_IOCTL
15989 {
15990 struct winsize w;
15991 if (ioctl(fd, TIOCGWINSZ, &w))
15992 return PyErr_SetFromErrno(PyExc_OSError);
15993 columns = w.ws_col;
15994 lines = w.ws_row;
15995 }
15996#endif /* TERMSIZE_USE_IOCTL */
15997
15998#ifdef TERMSIZE_USE_CONIO
15999 {
16000 DWORD nhandle;
16001 HANDLE handle;
16002 CONSOLE_SCREEN_BUFFER_INFO csbi;
16003 switch (fd) {
16004 case 0: nhandle = STD_INPUT_HANDLE;
16005 break;
16006 case 1: nhandle = STD_OUTPUT_HANDLE;
16007 break;
16008 case 2: nhandle = STD_ERROR_HANDLE;
16009 break;
16010 default:
16011 return PyErr_Format(PyExc_ValueError, "bad file descriptor");
16012 }
16013 handle = GetStdHandle(nhandle);
16014 if (handle == NULL)
16015 return PyErr_Format(PyExc_OSError, "handle cannot be retrieved");
16016 if (handle == INVALID_HANDLE_VALUE)
16017 return PyErr_SetFromWindowsErr(0);
16018
16019 if (!GetConsoleScreenBufferInfo(handle, &csbi))
16020 return PyErr_SetFromWindowsErr(0);
16021
16022 columns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
16023 lines = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
16024 }
16025#endif /* TERMSIZE_USE_CONIO */
16026
16027 termsize = PyStructSequence_New(&TerminalSizeType);
16028 if (termsize == NULL)
16029 return NULL;
16030 PyStructSequence_SET_ITEM(termsize, 0, PyLong_FromLong(columns));
16031 PyStructSequence_SET_ITEM(termsize, 1, PyLong_FromLong(lines));
16032 if (PyErr_Occurred()) {
16033 Py_DECREF(termsize);
16034 return NULL;
16035 }
16036 return termsize;
16037}
16038#endif /* defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL) */
16039
Larry Hastings2f936352014-08-05 14:04:04 +100016040
16041/*[clinic input]
16042os.cpu_count
16043
16044Return the number of CPUs in the system; return None if indeterminable.
16045[clinic start generated code]*/
16046
16047PyDoc_STRVAR(os_cpu_count__doc__,
16048"cpu_count($module, /)\n"
16049"--\n"
16050"\n"
16051"Return the number of CPUs in the system; return None if indeterminable.");
16052
16053#define OS_CPU_COUNT_METHODDEF \
16054 {"cpu_count", (PyCFunction)os_cpu_count, METH_NOARGS, os_cpu_count__doc__},
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016055
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016056static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100016057os_cpu_count_impl(PyModuleDef *module);
16058
16059static PyObject *
16060os_cpu_count(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
16061{
16062 return os_cpu_count_impl(module);
16063}
16064
16065static PyObject *
16066os_cpu_count_impl(PyModuleDef *module)
16067/*[clinic end generated code: output=92e2a4a729eb7740 input=d55e2f8f3823a628]*/
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016068{
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016069 int ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016070#ifdef MS_WINDOWS
16071 SYSTEM_INFO sysinfo;
16072 GetSystemInfo(&sysinfo);
16073 ncpu = sysinfo.dwNumberOfProcessors;
16074#elif defined(__hpux)
16075 ncpu = mpctl(MPC_GETNUMSPUS, NULL, NULL);
16076#elif defined(HAVE_SYSCONF) && defined(_SC_NPROCESSORS_ONLN)
16077 ncpu = sysconf(_SC_NPROCESSORS_ONLN);
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016078#elif defined(__DragonFly__) || \
16079 defined(__OpenBSD__) || \
16080 defined(__FreeBSD__) || \
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016081 defined(__NetBSD__) || \
16082 defined(__APPLE__)
Charles-Francois Natali7c4f8da2013-05-20 17:40:32 +020016083 int mib[2];
16084 size_t len = sizeof(ncpu);
16085 mib[0] = CTL_HW;
16086 mib[1] = HW_NCPU;
16087 if (sysctl(mib, 2, &ncpu, &len, NULL, 0) != 0)
16088 ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016089#endif
16090 if (ncpu >= 1)
16091 return PyLong_FromLong(ncpu);
16092 else
16093 Py_RETURN_NONE;
16094}
16095
Victor Stinnerdaf45552013-08-28 00:53:59 +020016096
Larry Hastings2f936352014-08-05 14:04:04 +100016097/*[clinic input]
16098os.get_inheritable -> bool
16099
16100 fd: int
16101 /
16102
16103Get the close-on-exe flag of the specified file descriptor.
16104[clinic start generated code]*/
16105
16106PyDoc_STRVAR(os_get_inheritable__doc__,
16107"get_inheritable($module, fd, /)\n"
16108"--\n"
16109"\n"
16110"Get the close-on-exe flag of the specified file descriptor.");
16111
16112#define OS_GET_INHERITABLE_METHODDEF \
16113 {"get_inheritable", (PyCFunction)os_get_inheritable, METH_VARARGS, os_get_inheritable__doc__},
16114
16115static int
16116os_get_inheritable_impl(PyModuleDef *module, int fd);
16117
16118static PyObject *
16119os_get_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016120{
Larry Hastings2f936352014-08-05 14:04:04 +100016121 PyObject *return_value = NULL;
16122 int fd;
16123 int _return_value;
16124
16125 if (!PyArg_ParseTuple(args,
16126 "i:get_inheritable",
16127 &fd))
16128 goto exit;
16129 _return_value = os_get_inheritable_impl(module, fd);
16130 if ((_return_value == -1) && PyErr_Occurred())
16131 goto exit;
16132 return_value = PyBool_FromLong((long)_return_value);
16133
16134exit:
16135 return return_value;
16136}
16137
16138static int
16139os_get_inheritable_impl(PyModuleDef *module, int fd)
16140/*[clinic end generated code: output=261d1dd2b0dbdc35 input=89ac008dc9ab6b95]*/
16141{
16142 if (!_PyVerify_fd(fd)){
16143 posix_error();
16144 return -1;
16145 }
16146
16147 return _Py_get_inheritable(fd);
16148}
16149
16150
16151/*[clinic input]
16152os.set_inheritable
16153 fd: int
16154 inheritable: int
16155 /
16156
16157Set the inheritable flag of the specified file descriptor.
16158[clinic start generated code]*/
16159
16160PyDoc_STRVAR(os_set_inheritable__doc__,
16161"set_inheritable($module, fd, inheritable, /)\n"
16162"--\n"
16163"\n"
16164"Set the inheritable flag of the specified file descriptor.");
16165
16166#define OS_SET_INHERITABLE_METHODDEF \
16167 {"set_inheritable", (PyCFunction)os_set_inheritable, METH_VARARGS, os_set_inheritable__doc__},
16168
16169static PyObject *
16170os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable);
16171
16172static PyObject *
16173os_set_inheritable(PyModuleDef *module, PyObject *args)
16174{
16175 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016176 int fd;
16177 int inheritable;
16178
Larry Hastings2f936352014-08-05 14:04:04 +100016179 if (!PyArg_ParseTuple(args,
16180 "ii:set_inheritable",
16181 &fd, &inheritable))
16182 goto exit;
16183 return_value = os_set_inheritable_impl(module, fd, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016184
Larry Hastings2f936352014-08-05 14:04:04 +100016185exit:
16186 return return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016187}
16188
Larry Hastings2f936352014-08-05 14:04:04 +100016189static PyObject *
16190os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable)
16191/*[clinic end generated code: output=64dfe5e15c906539 input=9ceaead87a1e2402]*/
Victor Stinnerdaf45552013-08-28 00:53:59 +020016192{
Victor Stinnerdaf45552013-08-28 00:53:59 +020016193 if (!_PyVerify_fd(fd))
16194 return posix_error();
16195
16196 if (_Py_set_inheritable(fd, inheritable, NULL) < 0)
16197 return NULL;
16198 Py_RETURN_NONE;
16199}
16200
16201
16202#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100016203/*[clinic input]
16204os.get_handle_inheritable -> bool
16205 handle: Py_intptr_t
16206 /
Victor Stinnerdaf45552013-08-28 00:53:59 +020016207
Larry Hastings2f936352014-08-05 14:04:04 +100016208Get the close-on-exe flag of the specified file descriptor.
16209[clinic start generated code]*/
16210
16211PyDoc_STRVAR(os_get_handle_inheritable__doc__,
16212"get_handle_inheritable($module, handle, /)\n"
16213"--\n"
16214"\n"
16215"Get the close-on-exe flag of the specified file descriptor.");
16216
16217#define OS_GET_HANDLE_INHERITABLE_METHODDEF \
16218 {"get_handle_inheritable", (PyCFunction)os_get_handle_inheritable, METH_VARARGS, os_get_handle_inheritable__doc__},
16219
16220static int
16221os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle);
16222
16223static PyObject *
16224os_get_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016225{
Larry Hastings2f936352014-08-05 14:04:04 +100016226 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016227 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016228 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016229
Larry Hastings2f936352014-08-05 14:04:04 +100016230 if (!PyArg_ParseTuple(args,
16231 "" _Py_PARSE_INTPTR ":get_handle_inheritable",
16232 &handle))
16233 goto exit;
16234 _return_value = os_get_handle_inheritable_impl(module, handle);
16235 if ((_return_value == -1) && PyErr_Occurred())
16236 goto exit;
16237 return_value = PyBool_FromLong((long)_return_value);
16238
16239exit:
16240 return return_value;
16241}
16242
16243static int
16244os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle)
16245/*[clinic end generated code: output=d5bf9d86900bf457 input=5f7759443aae3dc5]*/
16246{
16247 DWORD flags;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016248
16249 if (!GetHandleInformation((HANDLE)handle, &flags)) {
16250 PyErr_SetFromWindowsErr(0);
Larry Hastings2f936352014-08-05 14:04:04 +100016251 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016252 }
16253
Larry Hastings2f936352014-08-05 14:04:04 +100016254 return flags & HANDLE_FLAG_INHERIT;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016255}
16256
Victor Stinnerdaf45552013-08-28 00:53:59 +020016257
Larry Hastings2f936352014-08-05 14:04:04 +100016258/*[clinic input]
16259os.set_handle_inheritable
16260 handle: Py_intptr_t
16261 inheritable: bool
16262 /
16263
16264Set the inheritable flag of the specified handle.
16265[clinic start generated code]*/
16266
16267PyDoc_STRVAR(os_set_handle_inheritable__doc__,
16268"set_handle_inheritable($module, handle, inheritable, /)\n"
16269"--\n"
16270"\n"
16271"Set the inheritable flag of the specified handle.");
16272
16273#define OS_SET_HANDLE_INHERITABLE_METHODDEF \
16274 {"set_handle_inheritable", (PyCFunction)os_set_handle_inheritable, METH_VARARGS, os_set_handle_inheritable__doc__},
16275
16276static PyObject *
16277os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable);
16278
16279static PyObject *
16280os_set_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016281{
Larry Hastings2f936352014-08-05 14:04:04 +100016282 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016283 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016284 int inheritable;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016285
Larry Hastings2f936352014-08-05 14:04:04 +100016286 if (!PyArg_ParseTuple(args,
16287 "" _Py_PARSE_INTPTR "p:set_handle_inheritable",
16288 &handle, &inheritable))
16289 goto exit;
16290 return_value = os_set_handle_inheritable_impl(module, handle, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016291
Larry Hastings2f936352014-08-05 14:04:04 +100016292exit:
16293 return return_value;
16294}
16295
16296static PyObject *
16297os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable)
16298/*[clinic end generated code: output=ee5fcc6d9f0d4f8b input=e64b2b2730469def]*/
16299{
16300 DWORD flags = inheritable ? HANDLE_FLAG_INHERIT : 0;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016301 if (!SetHandleInformation((HANDLE)handle, HANDLE_FLAG_INHERIT, flags)) {
16302 PyErr_SetFromWindowsErr(0);
16303 return NULL;
16304 }
16305 Py_RETURN_NONE;
16306}
Larry Hastings2f936352014-08-05 14:04:04 +100016307#endif /* MS_WINDOWS */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010016308
Victor Stinner1db9e7b2014-07-29 22:32:47 +020016309#ifndef MS_WINDOWS
16310PyDoc_STRVAR(get_blocking__doc__,
16311 "get_blocking(fd) -> bool\n" \
16312 "\n" \
16313 "Get the blocking mode of the file descriptor:\n" \
16314 "False if the O_NONBLOCK flag is set, True if the flag is cleared.");
16315
16316static PyObject*
16317posix_get_blocking(PyObject *self, PyObject *args)
16318{
16319 int fd;
16320 int blocking;
16321
16322 if (!PyArg_ParseTuple(args, "i:get_blocking", &fd))
16323 return NULL;
16324
16325 if (!_PyVerify_fd(fd))
16326 return posix_error();
16327
16328 blocking = _Py_get_blocking(fd);
16329 if (blocking < 0)
16330 return NULL;
16331 return PyBool_FromLong(blocking);
16332}
16333
16334PyDoc_STRVAR(set_blocking__doc__,
16335 "set_blocking(fd, blocking)\n" \
16336 "\n" \
16337 "Set the blocking mode of the specified file descriptor.\n" \
16338 "Set the O_NONBLOCK flag if blocking is False,\n" \
16339 "clear the O_NONBLOCK flag otherwise.");
16340
16341static PyObject*
16342posix_set_blocking(PyObject *self, PyObject *args)
16343{
16344 int fd, blocking;
16345
16346 if (!PyArg_ParseTuple(args, "ii:set_blocking", &fd, &blocking))
16347 return NULL;
16348
16349 if (!_PyVerify_fd(fd))
16350 return posix_error();
16351
16352 if (_Py_set_blocking(fd, blocking) < 0)
16353 return NULL;
16354 Py_RETURN_NONE;
16355}
16356#endif /* !MS_WINDOWS */
16357
16358
Larry Hastings7726ac92014-01-31 22:03:12 -080016359/*[clinic input]
16360dump buffer
16361[clinic start generated code]*/
16362
16363#ifndef OS_TTYNAME_METHODDEF
16364 #define OS_TTYNAME_METHODDEF
16365#endif /* !defined(OS_TTYNAME_METHODDEF) */
Larry Hastings2f936352014-08-05 14:04:04 +100016366
16367#ifndef OS_CTERMID_METHODDEF
16368 #define OS_CTERMID_METHODDEF
16369#endif /* !defined(OS_CTERMID_METHODDEF) */
16370
16371#ifndef OS_FCHDIR_METHODDEF
16372 #define OS_FCHDIR_METHODDEF
16373#endif /* !defined(OS_FCHDIR_METHODDEF) */
16374
16375#ifndef OS_FCHMOD_METHODDEF
16376 #define OS_FCHMOD_METHODDEF
16377#endif /* !defined(OS_FCHMOD_METHODDEF) */
16378
16379#ifndef OS_LCHMOD_METHODDEF
16380 #define OS_LCHMOD_METHODDEF
16381#endif /* !defined(OS_LCHMOD_METHODDEF) */
16382
16383#ifndef OS_CHFLAGS_METHODDEF
16384 #define OS_CHFLAGS_METHODDEF
16385#endif /* !defined(OS_CHFLAGS_METHODDEF) */
16386
16387#ifndef OS_LCHFLAGS_METHODDEF
16388 #define OS_LCHFLAGS_METHODDEF
16389#endif /* !defined(OS_LCHFLAGS_METHODDEF) */
16390
16391#ifndef OS_CHROOT_METHODDEF
16392 #define OS_CHROOT_METHODDEF
16393#endif /* !defined(OS_CHROOT_METHODDEF) */
16394
16395#ifndef OS_FSYNC_METHODDEF
16396 #define OS_FSYNC_METHODDEF
16397#endif /* !defined(OS_FSYNC_METHODDEF) */
16398
16399#ifndef OS_SYNC_METHODDEF
16400 #define OS_SYNC_METHODDEF
16401#endif /* !defined(OS_SYNC_METHODDEF) */
16402
16403#ifndef OS_FDATASYNC_METHODDEF
16404 #define OS_FDATASYNC_METHODDEF
16405#endif /* !defined(OS_FDATASYNC_METHODDEF) */
16406
16407#ifndef OS_CHOWN_METHODDEF
16408 #define OS_CHOWN_METHODDEF
16409#endif /* !defined(OS_CHOWN_METHODDEF) */
16410
16411#ifndef OS_FCHOWN_METHODDEF
16412 #define OS_FCHOWN_METHODDEF
16413#endif /* !defined(OS_FCHOWN_METHODDEF) */
16414
16415#ifndef OS_LCHOWN_METHODDEF
16416 #define OS_LCHOWN_METHODDEF
16417#endif /* !defined(OS_LCHOWN_METHODDEF) */
16418
16419#ifndef OS_LINK_METHODDEF
16420 #define OS_LINK_METHODDEF
16421#endif /* !defined(OS_LINK_METHODDEF) */
16422
16423#ifndef OS__GETFINALPATHNAME_METHODDEF
16424 #define OS__GETFINALPATHNAME_METHODDEF
16425#endif /* !defined(OS__GETFINALPATHNAME_METHODDEF) */
16426
16427#ifndef OS__GETVOLUMEPATHNAME_METHODDEF
16428 #define OS__GETVOLUMEPATHNAME_METHODDEF
16429#endif /* !defined(OS__GETVOLUMEPATHNAME_METHODDEF) */
16430
16431#ifndef OS_NICE_METHODDEF
16432 #define OS_NICE_METHODDEF
16433#endif /* !defined(OS_NICE_METHODDEF) */
16434
16435#ifndef OS_GETPRIORITY_METHODDEF
16436 #define OS_GETPRIORITY_METHODDEF
16437#endif /* !defined(OS_GETPRIORITY_METHODDEF) */
16438
16439#ifndef OS_SETPRIORITY_METHODDEF
16440 #define OS_SETPRIORITY_METHODDEF
16441#endif /* !defined(OS_SETPRIORITY_METHODDEF) */
16442
16443#ifndef OS_SYSTEM_METHODDEF
16444 #define OS_SYSTEM_METHODDEF
16445#endif /* !defined(OS_SYSTEM_METHODDEF) */
16446
16447#ifndef OS_SYSTEM_METHODDEF
16448 #define OS_SYSTEM_METHODDEF
16449#endif /* !defined(OS_SYSTEM_METHODDEF) */
16450
16451#ifndef OS_UNAME_METHODDEF
16452 #define OS_UNAME_METHODDEF
16453#endif /* !defined(OS_UNAME_METHODDEF) */
16454
16455#ifndef OS_EXECV_METHODDEF
16456 #define OS_EXECV_METHODDEF
16457#endif /* !defined(OS_EXECV_METHODDEF) */
16458
16459#ifndef OS_EXECVE_METHODDEF
16460 #define OS_EXECVE_METHODDEF
16461#endif /* !defined(OS_EXECVE_METHODDEF) */
16462
16463#ifndef OS_SPAWNV_METHODDEF
16464 #define OS_SPAWNV_METHODDEF
16465#endif /* !defined(OS_SPAWNV_METHODDEF) */
16466
16467#ifndef OS_SPAWNVE_METHODDEF
16468 #define OS_SPAWNVE_METHODDEF
16469#endif /* !defined(OS_SPAWNVE_METHODDEF) */
16470
16471#ifndef OS_FORK1_METHODDEF
16472 #define OS_FORK1_METHODDEF
16473#endif /* !defined(OS_FORK1_METHODDEF) */
16474
16475#ifndef OS_FORK_METHODDEF
16476 #define OS_FORK_METHODDEF
16477#endif /* !defined(OS_FORK_METHODDEF) */
16478
16479#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16480 #define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16481#endif /* !defined(OS_SCHED_GET_PRIORITY_MAX_METHODDEF) */
16482
16483#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16484 #define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16485#endif /* !defined(OS_SCHED_GET_PRIORITY_MIN_METHODDEF) */
16486
16487#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
16488 #define OS_SCHED_GETSCHEDULER_METHODDEF
16489#endif /* !defined(OS_SCHED_GETSCHEDULER_METHODDEF) */
16490
16491#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
16492 #define OS_SCHED_SETSCHEDULER_METHODDEF
16493#endif /* !defined(OS_SCHED_SETSCHEDULER_METHODDEF) */
16494
16495#ifndef OS_SCHED_GETPARAM_METHODDEF
16496 #define OS_SCHED_GETPARAM_METHODDEF
16497#endif /* !defined(OS_SCHED_GETPARAM_METHODDEF) */
16498
16499#ifndef OS_SCHED_SETPARAM_METHODDEF
16500 #define OS_SCHED_SETPARAM_METHODDEF
16501#endif /* !defined(OS_SCHED_SETPARAM_METHODDEF) */
16502
16503#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
16504 #define OS_SCHED_RR_GET_INTERVAL_METHODDEF
16505#endif /* !defined(OS_SCHED_RR_GET_INTERVAL_METHODDEF) */
16506
16507#ifndef OS_SCHED_YIELD_METHODDEF
16508 #define OS_SCHED_YIELD_METHODDEF
16509#endif /* !defined(OS_SCHED_YIELD_METHODDEF) */
16510
16511#ifndef OS_SCHED_SETAFFINITY_METHODDEF
16512 #define OS_SCHED_SETAFFINITY_METHODDEF
16513#endif /* !defined(OS_SCHED_SETAFFINITY_METHODDEF) */
16514
16515#ifndef OS_SCHED_GETAFFINITY_METHODDEF
16516 #define OS_SCHED_GETAFFINITY_METHODDEF
16517#endif /* !defined(OS_SCHED_GETAFFINITY_METHODDEF) */
16518
16519#ifndef OS_OPENPTY_METHODDEF
16520 #define OS_OPENPTY_METHODDEF
16521#endif /* !defined(OS_OPENPTY_METHODDEF) */
16522
16523#ifndef OS_FORKPTY_METHODDEF
16524 #define OS_FORKPTY_METHODDEF
16525#endif /* !defined(OS_FORKPTY_METHODDEF) */
16526
16527#ifndef OS_GETEGID_METHODDEF
16528 #define OS_GETEGID_METHODDEF
16529#endif /* !defined(OS_GETEGID_METHODDEF) */
16530
16531#ifndef OS_GETEUID_METHODDEF
16532 #define OS_GETEUID_METHODDEF
16533#endif /* !defined(OS_GETEUID_METHODDEF) */
16534
16535#ifndef OS_GETGID_METHODDEF
16536 #define OS_GETGID_METHODDEF
16537#endif /* !defined(OS_GETGID_METHODDEF) */
16538
16539#ifndef OS_GETGROUPS_METHODDEF
16540 #define OS_GETGROUPS_METHODDEF
16541#endif /* !defined(OS_GETGROUPS_METHODDEF) */
16542
16543#ifndef OS_GETPGID_METHODDEF
16544 #define OS_GETPGID_METHODDEF
16545#endif /* !defined(OS_GETPGID_METHODDEF) */
16546
16547#ifndef OS_GETPGRP_METHODDEF
16548 #define OS_GETPGRP_METHODDEF
16549#endif /* !defined(OS_GETPGRP_METHODDEF) */
16550
16551#ifndef OS_SETPGRP_METHODDEF
16552 #define OS_SETPGRP_METHODDEF
16553#endif /* !defined(OS_SETPGRP_METHODDEF) */
16554
16555#ifndef OS_GETPPID_METHODDEF
16556 #define OS_GETPPID_METHODDEF
16557#endif /* !defined(OS_GETPPID_METHODDEF) */
16558
16559#ifndef OS_GETLOGIN_METHODDEF
16560 #define OS_GETLOGIN_METHODDEF
16561#endif /* !defined(OS_GETLOGIN_METHODDEF) */
16562
16563#ifndef OS_GETUID_METHODDEF
16564 #define OS_GETUID_METHODDEF
16565#endif /* !defined(OS_GETUID_METHODDEF) */
16566
16567#ifndef OS_KILL_METHODDEF
16568 #define OS_KILL_METHODDEF
16569#endif /* !defined(OS_KILL_METHODDEF) */
16570
16571#ifndef OS_KILLPG_METHODDEF
16572 #define OS_KILLPG_METHODDEF
16573#endif /* !defined(OS_KILLPG_METHODDEF) */
16574
16575#ifndef OS_PLOCK_METHODDEF
16576 #define OS_PLOCK_METHODDEF
16577#endif /* !defined(OS_PLOCK_METHODDEF) */
16578
16579#ifndef OS_SETUID_METHODDEF
16580 #define OS_SETUID_METHODDEF
16581#endif /* !defined(OS_SETUID_METHODDEF) */
16582
16583#ifndef OS_SETEUID_METHODDEF
16584 #define OS_SETEUID_METHODDEF
16585#endif /* !defined(OS_SETEUID_METHODDEF) */
16586
16587#ifndef OS_SETEGID_METHODDEF
16588 #define OS_SETEGID_METHODDEF
16589#endif /* !defined(OS_SETEGID_METHODDEF) */
16590
16591#ifndef OS_SETREUID_METHODDEF
16592 #define OS_SETREUID_METHODDEF
16593#endif /* !defined(OS_SETREUID_METHODDEF) */
16594
16595#ifndef OS_SETREGID_METHODDEF
16596 #define OS_SETREGID_METHODDEF
16597#endif /* !defined(OS_SETREGID_METHODDEF) */
16598
16599#ifndef OS_SETGID_METHODDEF
16600 #define OS_SETGID_METHODDEF
16601#endif /* !defined(OS_SETGID_METHODDEF) */
16602
16603#ifndef OS_SETGROUPS_METHODDEF
16604 #define OS_SETGROUPS_METHODDEF
16605#endif /* !defined(OS_SETGROUPS_METHODDEF) */
16606
16607#ifndef OS_WAIT3_METHODDEF
16608 #define OS_WAIT3_METHODDEF
16609#endif /* !defined(OS_WAIT3_METHODDEF) */
16610
16611#ifndef OS_WAIT4_METHODDEF
16612 #define OS_WAIT4_METHODDEF
16613#endif /* !defined(OS_WAIT4_METHODDEF) */
16614
16615#ifndef OS_WAITID_METHODDEF
16616 #define OS_WAITID_METHODDEF
16617#endif /* !defined(OS_WAITID_METHODDEF) */
16618
16619#ifndef OS_WAITPID_METHODDEF
16620 #define OS_WAITPID_METHODDEF
16621#endif /* !defined(OS_WAITPID_METHODDEF) */
16622
16623#ifndef OS_WAITPID_METHODDEF
16624 #define OS_WAITPID_METHODDEF
16625#endif /* !defined(OS_WAITPID_METHODDEF) */
16626
16627#ifndef OS_WAIT_METHODDEF
16628 #define OS_WAIT_METHODDEF
16629#endif /* !defined(OS_WAIT_METHODDEF) */
16630
16631#ifndef OS_SYMLINK_METHODDEF
16632 #define OS_SYMLINK_METHODDEF
16633#endif /* !defined(OS_SYMLINK_METHODDEF) */
16634
16635#ifndef OS_TIMES_METHODDEF
16636 #define OS_TIMES_METHODDEF
16637#endif /* !defined(OS_TIMES_METHODDEF) */
16638
16639#ifndef OS_GETSID_METHODDEF
16640 #define OS_GETSID_METHODDEF
16641#endif /* !defined(OS_GETSID_METHODDEF) */
16642
16643#ifndef OS_SETSID_METHODDEF
16644 #define OS_SETSID_METHODDEF
16645#endif /* !defined(OS_SETSID_METHODDEF) */
16646
16647#ifndef OS_SETPGID_METHODDEF
16648 #define OS_SETPGID_METHODDEF
16649#endif /* !defined(OS_SETPGID_METHODDEF) */
16650
16651#ifndef OS_TCGETPGRP_METHODDEF
16652 #define OS_TCGETPGRP_METHODDEF
16653#endif /* !defined(OS_TCGETPGRP_METHODDEF) */
16654
16655#ifndef OS_TCSETPGRP_METHODDEF
16656 #define OS_TCSETPGRP_METHODDEF
16657#endif /* !defined(OS_TCSETPGRP_METHODDEF) */
16658
16659#ifndef OS_LOCKF_METHODDEF
16660 #define OS_LOCKF_METHODDEF
16661#endif /* !defined(OS_LOCKF_METHODDEF) */
16662
16663#ifndef OS_READV_METHODDEF
16664 #define OS_READV_METHODDEF
16665#endif /* !defined(OS_READV_METHODDEF) */
16666
16667#ifndef OS_PREAD_METHODDEF
16668 #define OS_PREAD_METHODDEF
16669#endif /* !defined(OS_PREAD_METHODDEF) */
16670
16671#ifndef OS_PIPE_METHODDEF
16672 #define OS_PIPE_METHODDEF
16673#endif /* !defined(OS_PIPE_METHODDEF) */
16674
16675#ifndef OS_PIPE2_METHODDEF
16676 #define OS_PIPE2_METHODDEF
16677#endif /* !defined(OS_PIPE2_METHODDEF) */
16678
16679#ifndef OS_WRITEV_METHODDEF
16680 #define OS_WRITEV_METHODDEF
16681#endif /* !defined(OS_WRITEV_METHODDEF) */
16682
16683#ifndef OS_PWRITE_METHODDEF
16684 #define OS_PWRITE_METHODDEF
16685#endif /* !defined(OS_PWRITE_METHODDEF) */
16686
16687#ifndef OS_MKFIFO_METHODDEF
16688 #define OS_MKFIFO_METHODDEF
16689#endif /* !defined(OS_MKFIFO_METHODDEF) */
16690
16691#ifndef OS_MKNOD_METHODDEF
16692 #define OS_MKNOD_METHODDEF
16693#endif /* !defined(OS_MKNOD_METHODDEF) */
16694
16695#ifndef OS_MAJOR_METHODDEF
16696 #define OS_MAJOR_METHODDEF
16697#endif /* !defined(OS_MAJOR_METHODDEF) */
16698
16699#ifndef OS_MINOR_METHODDEF
16700 #define OS_MINOR_METHODDEF
16701#endif /* !defined(OS_MINOR_METHODDEF) */
16702
16703#ifndef OS_MAKEDEV_METHODDEF
16704 #define OS_MAKEDEV_METHODDEF
16705#endif /* !defined(OS_MAKEDEV_METHODDEF) */
16706
16707#ifndef OS_FTRUNCATE_METHODDEF
16708 #define OS_FTRUNCATE_METHODDEF
16709#endif /* !defined(OS_FTRUNCATE_METHODDEF) */
16710
16711#ifndef OS_TRUNCATE_METHODDEF
16712 #define OS_TRUNCATE_METHODDEF
16713#endif /* !defined(OS_TRUNCATE_METHODDEF) */
16714
16715#ifndef OS_POSIX_FALLOCATE_METHODDEF
16716 #define OS_POSIX_FALLOCATE_METHODDEF
16717#endif /* !defined(OS_POSIX_FALLOCATE_METHODDEF) */
16718
16719#ifndef OS_POSIX_FADVISE_METHODDEF
16720 #define OS_POSIX_FADVISE_METHODDEF
16721#endif /* !defined(OS_POSIX_FADVISE_METHODDEF) */
16722
16723#ifndef OS_PUTENV_METHODDEF
16724 #define OS_PUTENV_METHODDEF
16725#endif /* !defined(OS_PUTENV_METHODDEF) */
16726
16727#ifndef OS_PUTENV_METHODDEF
16728 #define OS_PUTENV_METHODDEF
16729#endif /* !defined(OS_PUTENV_METHODDEF) */
16730
16731#ifndef OS_UNSETENV_METHODDEF
16732 #define OS_UNSETENV_METHODDEF
16733#endif /* !defined(OS_UNSETENV_METHODDEF) */
16734
16735#ifndef OS_WCOREDUMP_METHODDEF
16736 #define OS_WCOREDUMP_METHODDEF
16737#endif /* !defined(OS_WCOREDUMP_METHODDEF) */
16738
16739#ifndef OS_WIFCONTINUED_METHODDEF
16740 #define OS_WIFCONTINUED_METHODDEF
16741#endif /* !defined(OS_WIFCONTINUED_METHODDEF) */
16742
16743#ifndef OS_WIFSTOPPED_METHODDEF
16744 #define OS_WIFSTOPPED_METHODDEF
16745#endif /* !defined(OS_WIFSTOPPED_METHODDEF) */
16746
16747#ifndef OS_WIFSIGNALED_METHODDEF
16748 #define OS_WIFSIGNALED_METHODDEF
16749#endif /* !defined(OS_WIFSIGNALED_METHODDEF) */
16750
16751#ifndef OS_WIFEXITED_METHODDEF
16752 #define OS_WIFEXITED_METHODDEF
16753#endif /* !defined(OS_WIFEXITED_METHODDEF) */
16754
16755#ifndef OS_WEXITSTATUS_METHODDEF
16756 #define OS_WEXITSTATUS_METHODDEF
16757#endif /* !defined(OS_WEXITSTATUS_METHODDEF) */
16758
16759#ifndef OS_WTERMSIG_METHODDEF
16760 #define OS_WTERMSIG_METHODDEF
16761#endif /* !defined(OS_WTERMSIG_METHODDEF) */
16762
16763#ifndef OS_WSTOPSIG_METHODDEF
16764 #define OS_WSTOPSIG_METHODDEF
16765#endif /* !defined(OS_WSTOPSIG_METHODDEF) */
16766
16767#ifndef OS_FSTATVFS_METHODDEF
16768 #define OS_FSTATVFS_METHODDEF
16769#endif /* !defined(OS_FSTATVFS_METHODDEF) */
16770
16771#ifndef OS_STATVFS_METHODDEF
16772 #define OS_STATVFS_METHODDEF
16773#endif /* !defined(OS_STATVFS_METHODDEF) */
16774
16775#ifndef OS__GETDISKUSAGE_METHODDEF
16776 #define OS__GETDISKUSAGE_METHODDEF
16777#endif /* !defined(OS__GETDISKUSAGE_METHODDEF) */
16778
16779#ifndef OS_FPATHCONF_METHODDEF
16780 #define OS_FPATHCONF_METHODDEF
16781#endif /* !defined(OS_FPATHCONF_METHODDEF) */
16782
16783#ifndef OS_PATHCONF_METHODDEF
16784 #define OS_PATHCONF_METHODDEF
16785#endif /* !defined(OS_PATHCONF_METHODDEF) */
16786
16787#ifndef OS_CONFSTR_METHODDEF
16788 #define OS_CONFSTR_METHODDEF
16789#endif /* !defined(OS_CONFSTR_METHODDEF) */
16790
16791#ifndef OS_SYSCONF_METHODDEF
16792 #define OS_SYSCONF_METHODDEF
16793#endif /* !defined(OS_SYSCONF_METHODDEF) */
16794
16795#ifndef OS_GETLOADAVG_METHODDEF
16796 #define OS_GETLOADAVG_METHODDEF
16797#endif /* !defined(OS_GETLOADAVG_METHODDEF) */
16798
16799#ifndef OS_SETRESUID_METHODDEF
16800 #define OS_SETRESUID_METHODDEF
16801#endif /* !defined(OS_SETRESUID_METHODDEF) */
16802
16803#ifndef OS_SETRESGID_METHODDEF
16804 #define OS_SETRESGID_METHODDEF
16805#endif /* !defined(OS_SETRESGID_METHODDEF) */
16806
16807#ifndef OS_GETRESUID_METHODDEF
16808 #define OS_GETRESUID_METHODDEF
16809#endif /* !defined(OS_GETRESUID_METHODDEF) */
16810
16811#ifndef OS_GETRESGID_METHODDEF
16812 #define OS_GETRESGID_METHODDEF
16813#endif /* !defined(OS_GETRESGID_METHODDEF) */
16814
16815#ifndef OS_GETXATTR_METHODDEF
16816 #define OS_GETXATTR_METHODDEF
16817#endif /* !defined(OS_GETXATTR_METHODDEF) */
16818
16819#ifndef OS_SETXATTR_METHODDEF
16820 #define OS_SETXATTR_METHODDEF
16821#endif /* !defined(OS_SETXATTR_METHODDEF) */
16822
16823#ifndef OS_REMOVEXATTR_METHODDEF
16824 #define OS_REMOVEXATTR_METHODDEF
16825#endif /* !defined(OS_REMOVEXATTR_METHODDEF) */
16826
16827#ifndef OS_LISTXATTR_METHODDEF
16828 #define OS_LISTXATTR_METHODDEF
16829#endif /* !defined(OS_LISTXATTR_METHODDEF) */
16830
16831#ifndef OS_GET_HANDLE_INHERITABLE_METHODDEF
16832 #define OS_GET_HANDLE_INHERITABLE_METHODDEF
16833#endif /* !defined(OS_GET_HANDLE_INHERITABLE_METHODDEF) */
16834
16835#ifndef OS_SET_HANDLE_INHERITABLE_METHODDEF
16836 #define OS_SET_HANDLE_INHERITABLE_METHODDEF
16837#endif /* !defined(OS_SET_HANDLE_INHERITABLE_METHODDEF) */
16838/*[clinic end generated code: output=52a6140b0b052ce6 input=524ce2e021e4eba6]*/
Larry Hastings7726ac92014-01-31 22:03:12 -080016839
Larry Hastings31826802013-10-19 00:09:25 -070016840
Fred Drake5ab8eaf1999-12-09 21:13:07 +000016841static PyMethodDef posix_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -070016842
16843 OS_STAT_METHODDEF
16844 OS_ACCESS_METHODDEF
16845 OS_TTYNAME_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100016846 OS_CHDIR_METHODDEF
16847 OS_CHFLAGS_METHODDEF
16848 OS_CHMOD_METHODDEF
16849 OS_FCHMOD_METHODDEF
16850 OS_LCHMOD_METHODDEF
16851 OS_CHOWN_METHODDEF
16852 OS_FCHOWN_METHODDEF
16853 OS_LCHOWN_METHODDEF
16854 OS_LCHFLAGS_METHODDEF
16855 OS_CHROOT_METHODDEF
16856 OS_CTERMID_METHODDEF
16857 OS_GETCWD_METHODDEF
16858 OS_GETCWDB_METHODDEF
16859 OS_LINK_METHODDEF
16860 OS_LISTDIR_METHODDEF
16861 OS_LSTAT_METHODDEF
16862 OS_MKDIR_METHODDEF
16863 OS_NICE_METHODDEF
16864 OS_GETPRIORITY_METHODDEF
16865 OS_SETPRIORITY_METHODDEF
Guido van Rossumb6775db1994-08-01 11:34:53 +000016866#ifdef HAVE_READLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070016867 {"readlink", (PyCFunction)posix_readlink,
16868 METH_VARARGS | METH_KEYWORDS,
16869 readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000016870#endif /* HAVE_READLINK */
Brian Curtind40e6f72010-07-08 21:39:08 +000016871#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
Larry Hastings9cf065c2012-06-22 16:30:09 -070016872 {"readlink", (PyCFunction)win_readlink,
16873 METH_VARARGS | METH_KEYWORDS,
16874 readlink__doc__},
Brian Curtind40e6f72010-07-08 21:39:08 +000016875#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
Larry Hastings2f936352014-08-05 14:04:04 +100016876 OS_RENAME_METHODDEF
16877 OS_REPLACE_METHODDEF
16878 OS_RMDIR_METHODDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000016879 {"stat_float_times", stat_float_times, METH_VARARGS, stat_float_times__doc__},
Larry Hastings2f936352014-08-05 14:04:04 +100016880 OS_SYMLINK_METHODDEF
16881 OS_SYSTEM_METHODDEF
16882 OS_UMASK_METHODDEF
16883 OS_UNAME_METHODDEF
16884 OS_UNLINK_METHODDEF
16885 OS_REMOVE_METHODDEF
16886 OS_UTIME_METHODDEF
16887 OS_TIMES_METHODDEF
16888 OS__EXIT_METHODDEF
16889 OS_EXECV_METHODDEF
16890 OS_EXECVE_METHODDEF
16891 OS_SPAWNV_METHODDEF
16892 OS_SPAWNVE_METHODDEF
16893 OS_FORK1_METHODDEF
16894 OS_FORK_METHODDEF
16895 OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16896 OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16897 OS_SCHED_GETPARAM_METHODDEF
16898 OS_SCHED_GETSCHEDULER_METHODDEF
16899 OS_SCHED_RR_GET_INTERVAL_METHODDEF
16900 OS_SCHED_SETPARAM_METHODDEF
16901 OS_SCHED_SETSCHEDULER_METHODDEF
16902 OS_SCHED_YIELD_METHODDEF
16903 OS_SCHED_SETAFFINITY_METHODDEF
16904 OS_SCHED_GETAFFINITY_METHODDEF
16905 OS_OPENPTY_METHODDEF
16906 OS_FORKPTY_METHODDEF
16907 OS_GETEGID_METHODDEF
16908 OS_GETEUID_METHODDEF
16909 OS_GETGID_METHODDEF
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +020016910#ifdef HAVE_GETGROUPLIST
16911 {"getgrouplist", posix_getgrouplist, METH_VARARGS, posix_getgrouplist__doc__},
16912#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016913 OS_GETGROUPS_METHODDEF
16914 OS_GETPID_METHODDEF
16915 OS_GETPGRP_METHODDEF
16916 OS_GETPPID_METHODDEF
16917 OS_GETUID_METHODDEF
16918 OS_GETLOGIN_METHODDEF
16919 OS_KILL_METHODDEF
16920 OS_KILLPG_METHODDEF
16921 OS_PLOCK_METHODDEF
Thomas Heller8b7a9572007-08-31 06:44:36 +000016922#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000016923 {"startfile", win32_startfile, METH_VARARGS, win32_startfile__doc__},
Thomas Heller8b7a9572007-08-31 06:44:36 +000016924#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016925 OS_SETUID_METHODDEF
16926 OS_SETEUID_METHODDEF
16927 OS_SETREUID_METHODDEF
16928 OS_SETGID_METHODDEF
16929 OS_SETEGID_METHODDEF
16930 OS_SETREGID_METHODDEF
16931 OS_SETGROUPS_METHODDEF
Antoine Pitroub7572f02009-12-02 20:46:48 +000016932#ifdef HAVE_INITGROUPS
Victor Stinner8c62be82010-05-06 00:08:46 +000016933 {"initgroups", posix_initgroups, METH_VARARGS, posix_initgroups__doc__},
Antoine Pitroub7572f02009-12-02 20:46:48 +000016934#endif /* HAVE_INITGROUPS */
Larry Hastings2f936352014-08-05 14:04:04 +100016935 OS_GETPGID_METHODDEF
16936 OS_SETPGRP_METHODDEF
16937 OS_WAIT_METHODDEF
16938 OS_WAIT3_METHODDEF
16939 OS_WAIT4_METHODDEF
16940 OS_WAITID_METHODDEF
16941 OS_WAITPID_METHODDEF
16942 OS_GETSID_METHODDEF
16943 OS_SETSID_METHODDEF
16944 OS_SETPGID_METHODDEF
16945 OS_TCGETPGRP_METHODDEF
16946 OS_TCSETPGRP_METHODDEF
16947 OS_OPEN_METHODDEF
16948 OS_CLOSE_METHODDEF
16949 OS_CLOSERANGE_METHODDEF
16950 OS_DEVICE_ENCODING_METHODDEF
16951 OS_DUP_METHODDEF
16952 OS_DUP2_METHODDEF
16953 OS_LOCKF_METHODDEF
16954 OS_LSEEK_METHODDEF
16955 OS_READ_METHODDEF
16956 OS_READV_METHODDEF
16957 OS_PREAD_METHODDEF
16958 OS_WRITE_METHODDEF
16959 OS_WRITEV_METHODDEF
16960 OS_PWRITE_METHODDEF
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000016961#ifdef HAVE_SENDFILE
16962 {"sendfile", (PyCFunction)posix_sendfile, METH_VARARGS | METH_KEYWORDS,
16963 posix_sendfile__doc__},
16964#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016965 OS_FSTAT_METHODDEF
16966 OS_ISATTY_METHODDEF
16967 OS_PIPE_METHODDEF
16968 OS_PIPE2_METHODDEF
16969 OS_MKFIFO_METHODDEF
16970 OS_MKNOD_METHODDEF
16971 OS_MAJOR_METHODDEF
16972 OS_MINOR_METHODDEF
16973 OS_MAKEDEV_METHODDEF
16974 OS_FTRUNCATE_METHODDEF
16975 OS_TRUNCATE_METHODDEF
16976 OS_POSIX_FALLOCATE_METHODDEF
16977 OS_POSIX_FADVISE_METHODDEF
16978 OS_PUTENV_METHODDEF
16979 OS_UNSETENV_METHODDEF
16980 OS_STRERROR_METHODDEF
16981 OS_FCHDIR_METHODDEF
16982 OS_FSYNC_METHODDEF
16983 OS_SYNC_METHODDEF
16984 OS_FDATASYNC_METHODDEF
16985 OS_WCOREDUMP_METHODDEF
16986 OS_WIFCONTINUED_METHODDEF
16987 OS_WIFSTOPPED_METHODDEF
16988 OS_WIFSIGNALED_METHODDEF
16989 OS_WIFEXITED_METHODDEF
16990 OS_WEXITSTATUS_METHODDEF
16991 OS_WTERMSIG_METHODDEF
16992 OS_WSTOPSIG_METHODDEF
16993 OS_FSTATVFS_METHODDEF
16994 OS_STATVFS_METHODDEF
16995 OS_CONFSTR_METHODDEF
16996 OS_SYSCONF_METHODDEF
16997 OS_FPATHCONF_METHODDEF
16998 OS_PATHCONF_METHODDEF
16999 OS_ABORT_METHODDEF
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000017000#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000017001 {"_getfullpathname", posix__getfullpathname, METH_VARARGS, NULL},
Brian Curtin95d028f2011-06-09 09:10:38 -050017002 {"_isdir", posix__isdir, METH_VARARGS, posix__isdir__doc__},
Mark Hammondef8b6542001-05-13 08:04:26 +000017003#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017004 OS__GETDISKUSAGE_METHODDEF
17005 OS__GETFINALPATHNAME_METHODDEF
17006 OS__GETVOLUMEPATHNAME_METHODDEF
17007 OS_GETLOADAVG_METHODDEF
17008 OS_URANDOM_METHODDEF
17009 OS_SETRESUID_METHODDEF
17010 OS_SETRESGID_METHODDEF
17011 OS_GETRESUID_METHODDEF
17012 OS_GETRESGID_METHODDEF
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000017013
Larry Hastings2f936352014-08-05 14:04:04 +100017014 OS_GETXATTR_METHODDEF
17015 OS_SETXATTR_METHODDEF
17016 OS_REMOVEXATTR_METHODDEF
17017 OS_LISTXATTR_METHODDEF
17018
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017019#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
17020 {"get_terminal_size", get_terminal_size, METH_VARARGS, termsize__doc__},
17021#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017022 OS_CPU_COUNT_METHODDEF
17023 OS_GET_INHERITABLE_METHODDEF
17024 OS_SET_INHERITABLE_METHODDEF
17025 OS_GET_HANDLE_INHERITABLE_METHODDEF
17026 OS_SET_HANDLE_INHERITABLE_METHODDEF
Victor Stinner1db9e7b2014-07-29 22:32:47 +020017027#ifndef MS_WINDOWS
17028 {"get_blocking", posix_get_blocking, METH_VARARGS, get_blocking__doc__},
17029 {"set_blocking", posix_set_blocking, METH_VARARGS, set_blocking__doc__},
17030#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017031 {NULL, NULL} /* Sentinel */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000017032};
17033
17034
Brian Curtin52173d42010-12-02 18:29:18 +000017035#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017036static int
Brian Curtin52173d42010-12-02 18:29:18 +000017037enable_symlink()
17038{
17039 HANDLE tok;
17040 TOKEN_PRIVILEGES tok_priv;
17041 LUID luid;
17042 int meth_idx = 0;
17043
17044 if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &tok))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017045 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017046
17047 if (!LookupPrivilegeValue(NULL, SE_CREATE_SYMBOLIC_LINK_NAME, &luid))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017048 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017049
17050 tok_priv.PrivilegeCount = 1;
17051 tok_priv.Privileges[0].Luid = luid;
17052 tok_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
17053
17054 if (!AdjustTokenPrivileges(tok, FALSE, &tok_priv,
17055 sizeof(TOKEN_PRIVILEGES),
17056 (PTOKEN_PRIVILEGES) NULL, (PDWORD) NULL))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017057 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017058
Brian Curtin3b4499c2010-12-28 14:31:47 +000017059 /* ERROR_NOT_ALL_ASSIGNED returned when the privilege can't be assigned. */
17060 return GetLastError() == ERROR_NOT_ALL_ASSIGNED ? 0 : 1;
Brian Curtin52173d42010-12-02 18:29:18 +000017061}
17062#endif /* defined(HAVE_SYMLINK) && defined(MS_WINDOWS) */
17063
Barry Warsaw4a342091996-12-19 23:50:02 +000017064static int
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017065all_ins(PyObject *m)
Barry Warsaw4a342091996-12-19 23:50:02 +000017066{
Guido van Rossum94f6f721999-01-06 18:42:14 +000017067#ifdef F_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017068 if (PyModule_AddIntMacro(m, F_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017069#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017070#ifdef R_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017071 if (PyModule_AddIntMacro(m, R_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017072#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017073#ifdef W_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017074 if (PyModule_AddIntMacro(m, W_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017075#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017076#ifdef X_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017077 if (PyModule_AddIntMacro(m, X_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017078#endif
Fred Drakec9680921999-12-13 16:37:25 +000017079#ifdef NGROUPS_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017080 if (PyModule_AddIntMacro(m, NGROUPS_MAX)) return -1;
Fred Drakec9680921999-12-13 16:37:25 +000017081#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017082#ifdef TMP_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017083 if (PyModule_AddIntMacro(m, TMP_MAX)) return -1;
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017084#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017085#ifdef WCONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017086 if (PyModule_AddIntMacro(m, WCONTINUED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017087#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017088#ifdef WNOHANG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017089 if (PyModule_AddIntMacro(m, WNOHANG)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017090#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017091#ifdef WUNTRACED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017092 if (PyModule_AddIntMacro(m, WUNTRACED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017093#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017094#ifdef O_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017095 if (PyModule_AddIntMacro(m, O_RDONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017096#endif
17097#ifdef O_WRONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017098 if (PyModule_AddIntMacro(m, O_WRONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017099#endif
17100#ifdef O_RDWR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017101 if (PyModule_AddIntMacro(m, O_RDWR)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017102#endif
17103#ifdef O_NDELAY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017104 if (PyModule_AddIntMacro(m, O_NDELAY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017105#endif
17106#ifdef O_NONBLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017107 if (PyModule_AddIntMacro(m, O_NONBLOCK)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017108#endif
17109#ifdef O_APPEND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017110 if (PyModule_AddIntMacro(m, O_APPEND)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017111#endif
17112#ifdef O_DSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017113 if (PyModule_AddIntMacro(m, O_DSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017114#endif
17115#ifdef O_RSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017116 if (PyModule_AddIntMacro(m, O_RSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017117#endif
17118#ifdef O_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017119 if (PyModule_AddIntMacro(m, O_SYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017120#endif
17121#ifdef O_NOCTTY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017122 if (PyModule_AddIntMacro(m, O_NOCTTY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017123#endif
17124#ifdef O_CREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017125 if (PyModule_AddIntMacro(m, O_CREAT)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017126#endif
17127#ifdef O_EXCL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017128 if (PyModule_AddIntMacro(m, O_EXCL)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017129#endif
17130#ifdef O_TRUNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017131 if (PyModule_AddIntMacro(m, O_TRUNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017132#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +000017133#ifdef O_BINARY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017134 if (PyModule_AddIntMacro(m, O_BINARY)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017135#endif
17136#ifdef O_TEXT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017137 if (PyModule_AddIntMacro(m, O_TEXT)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017138#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017139#ifdef O_XATTR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017140 if (PyModule_AddIntMacro(m, O_XATTR)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017141#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017142#ifdef O_LARGEFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017143 if (PyModule_AddIntMacro(m, O_LARGEFILE)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017144#endif
Skip Montanaro5ff14922005-05-16 02:42:22 +000017145#ifdef O_SHLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017146 if (PyModule_AddIntMacro(m, O_SHLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017147#endif
17148#ifdef O_EXLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017149 if (PyModule_AddIntMacro(m, O_EXLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017150#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017151#ifdef O_EXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017152 if (PyModule_AddIntMacro(m, O_EXEC)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017153#endif
17154#ifdef O_SEARCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017155 if (PyModule_AddIntMacro(m, O_SEARCH)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017156#endif
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017157#ifdef O_PATH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017158 if (PyModule_AddIntMacro(m, O_PATH)) return -1;
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017159#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017160#ifdef O_TTY_INIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017161 if (PyModule_AddIntMacro(m, O_TTY_INIT)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017162#endif
Christian Heimes177b3f92013-08-16 14:35:09 +020017163#ifdef O_TMPFILE
17164 if (PyModule_AddIntMacro(m, O_TMPFILE)) return -1;
17165#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017166#ifdef PRIO_PROCESS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017167 if (PyModule_AddIntMacro(m, PRIO_PROCESS)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017168#endif
17169#ifdef PRIO_PGRP
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017170 if (PyModule_AddIntMacro(m, PRIO_PGRP)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017171#endif
17172#ifdef PRIO_USER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017173 if (PyModule_AddIntMacro(m, PRIO_USER)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017174#endif
Charles-François Natali1e045b12011-05-22 20:42:32 +020017175#ifdef O_CLOEXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017176 if (PyModule_AddIntMacro(m, O_CLOEXEC)) return -1;
Charles-François Natali1e045b12011-05-22 20:42:32 +020017177#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017178#ifdef O_ACCMODE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017179 if (PyModule_AddIntMacro(m, O_ACCMODE)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017180#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017181
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017182
Jesus Cea94363612012-06-22 18:32:07 +020017183#ifdef SEEK_HOLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017184 if (PyModule_AddIntMacro(m, SEEK_HOLE)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017185#endif
17186#ifdef SEEK_DATA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017187 if (PyModule_AddIntMacro(m, SEEK_DATA)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017188#endif
17189
Tim Peters5aa91602002-01-30 05:46:57 +000017190/* MS Windows */
17191#ifdef O_NOINHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000017192 /* Don't inherit in child processes. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017193 if (PyModule_AddIntMacro(m, O_NOINHERIT)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017194#endif
17195#ifdef _O_SHORT_LIVED
Victor Stinner8c62be82010-05-06 00:08:46 +000017196 /* Optimize for short life (keep in memory). */
17197 /* MS forgot to define this one with a non-underscore form too. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017198 if (PyModule_AddIntConstant(m, "O_SHORT_LIVED", _O_SHORT_LIVED)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017199#endif
17200#ifdef O_TEMPORARY
Victor Stinner8c62be82010-05-06 00:08:46 +000017201 /* Automatically delete when last handle is closed. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017202 if (PyModule_AddIntMacro(m, O_TEMPORARY)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017203#endif
17204#ifdef O_RANDOM
Victor Stinner8c62be82010-05-06 00:08:46 +000017205 /* Optimize for random access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017206 if (PyModule_AddIntMacro(m, O_RANDOM)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017207#endif
17208#ifdef O_SEQUENTIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000017209 /* Optimize for sequential access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017210 if (PyModule_AddIntMacro(m, O_SEQUENTIAL)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017211#endif
17212
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017213/* GNU extensions. */
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017214#ifdef O_ASYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000017215 /* Send a SIGIO signal whenever input or output
17216 becomes available on file descriptor */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017217 if (PyModule_AddIntMacro(m, O_ASYNC)) return -1;
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017218#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017219#ifdef O_DIRECT
Victor Stinner8c62be82010-05-06 00:08:46 +000017220 /* Direct disk access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017221 if (PyModule_AddIntMacro(m, O_DIRECT)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017222#endif
17223#ifdef O_DIRECTORY
Victor Stinner8c62be82010-05-06 00:08:46 +000017224 /* Must be a directory. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017225 if (PyModule_AddIntMacro(m, O_DIRECTORY)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017226#endif
17227#ifdef O_NOFOLLOW
Victor Stinner8c62be82010-05-06 00:08:46 +000017228 /* Do not follow links. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017229 if (PyModule_AddIntMacro(m, O_NOFOLLOW)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017230#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017231#ifdef O_NOLINKS
17232 /* Fails if link count of the named file is greater than 1 */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017233 if (PyModule_AddIntMacro(m, O_NOLINKS)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017234#endif
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017235#ifdef O_NOATIME
Victor Stinner8c62be82010-05-06 00:08:46 +000017236 /* Do not update the access time. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017237 if (PyModule_AddIntMacro(m, O_NOATIME)) return -1;
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017238#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +000017239
Victor Stinner8c62be82010-05-06 00:08:46 +000017240 /* These come from sysexits.h */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017241#ifdef EX_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017242 if (PyModule_AddIntMacro(m, EX_OK)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017243#endif /* EX_OK */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017244#ifdef EX_USAGE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017245 if (PyModule_AddIntMacro(m, EX_USAGE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017246#endif /* EX_USAGE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017247#ifdef EX_DATAERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017248 if (PyModule_AddIntMacro(m, EX_DATAERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017249#endif /* EX_DATAERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017250#ifdef EX_NOINPUT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017251 if (PyModule_AddIntMacro(m, EX_NOINPUT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017252#endif /* EX_NOINPUT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017253#ifdef EX_NOUSER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017254 if (PyModule_AddIntMacro(m, EX_NOUSER)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017255#endif /* EX_NOUSER */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017256#ifdef EX_NOHOST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017257 if (PyModule_AddIntMacro(m, EX_NOHOST)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017258#endif /* EX_NOHOST */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017259#ifdef EX_UNAVAILABLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017260 if (PyModule_AddIntMacro(m, EX_UNAVAILABLE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017261#endif /* EX_UNAVAILABLE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017262#ifdef EX_SOFTWARE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017263 if (PyModule_AddIntMacro(m, EX_SOFTWARE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017264#endif /* EX_SOFTWARE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017265#ifdef EX_OSERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017266 if (PyModule_AddIntMacro(m, EX_OSERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017267#endif /* EX_OSERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017268#ifdef EX_OSFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017269 if (PyModule_AddIntMacro(m, EX_OSFILE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017270#endif /* EX_OSFILE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017271#ifdef EX_CANTCREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017272 if (PyModule_AddIntMacro(m, EX_CANTCREAT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017273#endif /* EX_CANTCREAT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017274#ifdef EX_IOERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017275 if (PyModule_AddIntMacro(m, EX_IOERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017276#endif /* EX_IOERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017277#ifdef EX_TEMPFAIL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017278 if (PyModule_AddIntMacro(m, EX_TEMPFAIL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017279#endif /* EX_TEMPFAIL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017280#ifdef EX_PROTOCOL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017281 if (PyModule_AddIntMacro(m, EX_PROTOCOL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017282#endif /* EX_PROTOCOL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017283#ifdef EX_NOPERM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017284 if (PyModule_AddIntMacro(m, EX_NOPERM)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017285#endif /* EX_NOPERM */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017286#ifdef EX_CONFIG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017287 if (PyModule_AddIntMacro(m, EX_CONFIG)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017288#endif /* EX_CONFIG */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017289#ifdef EX_NOTFOUND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017290 if (PyModule_AddIntMacro(m, EX_NOTFOUND)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017291#endif /* EX_NOTFOUND */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017292
Amaury Forgeot d'Arc66d00ad2010-09-10 18:11:45 +000017293 /* statvfs */
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017294#ifdef ST_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017295 if (PyModule_AddIntMacro(m, ST_RDONLY)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017296#endif /* ST_RDONLY */
17297#ifdef ST_NOSUID
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017298 if (PyModule_AddIntMacro(m, ST_NOSUID)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017299#endif /* ST_NOSUID */
17300
doko@ubuntu.comca616a22013-12-08 15:23:07 +010017301 /* GNU extensions */
17302#ifdef ST_NODEV
17303 if (PyModule_AddIntMacro(m, ST_NODEV)) return -1;
17304#endif /* ST_NODEV */
17305#ifdef ST_NOEXEC
17306 if (PyModule_AddIntMacro(m, ST_NOEXEC)) return -1;
17307#endif /* ST_NOEXEC */
17308#ifdef ST_SYNCHRONOUS
17309 if (PyModule_AddIntMacro(m, ST_SYNCHRONOUS)) return -1;
17310#endif /* ST_SYNCHRONOUS */
17311#ifdef ST_MANDLOCK
17312 if (PyModule_AddIntMacro(m, ST_MANDLOCK)) return -1;
17313#endif /* ST_MANDLOCK */
17314#ifdef ST_WRITE
17315 if (PyModule_AddIntMacro(m, ST_WRITE)) return -1;
17316#endif /* ST_WRITE */
17317#ifdef ST_APPEND
17318 if (PyModule_AddIntMacro(m, ST_APPEND)) return -1;
17319#endif /* ST_APPEND */
17320#ifdef ST_NOATIME
17321 if (PyModule_AddIntMacro(m, ST_NOATIME)) return -1;
17322#endif /* ST_NOATIME */
17323#ifdef ST_NODIRATIME
17324 if (PyModule_AddIntMacro(m, ST_NODIRATIME)) return -1;
17325#endif /* ST_NODIRATIME */
17326#ifdef ST_RELATIME
17327 if (PyModule_AddIntMacro(m, ST_RELATIME)) return -1;
17328#endif /* ST_RELATIME */
17329
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017330 /* FreeBSD sendfile() constants */
17331#ifdef SF_NODISKIO
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017332 if (PyModule_AddIntMacro(m, SF_NODISKIO)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017333#endif
17334#ifdef SF_MNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017335 if (PyModule_AddIntMacro(m, SF_MNOWAIT)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017336#endif
17337#ifdef SF_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017338 if (PyModule_AddIntMacro(m, SF_SYNC)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017339#endif
17340
Ross Lagerwall7807c352011-03-17 20:20:30 +020017341 /* constants for posix_fadvise */
17342#ifdef POSIX_FADV_NORMAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017343 if (PyModule_AddIntMacro(m, POSIX_FADV_NORMAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017344#endif
17345#ifdef POSIX_FADV_SEQUENTIAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017346 if (PyModule_AddIntMacro(m, POSIX_FADV_SEQUENTIAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017347#endif
17348#ifdef POSIX_FADV_RANDOM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017349 if (PyModule_AddIntMacro(m, POSIX_FADV_RANDOM)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017350#endif
17351#ifdef POSIX_FADV_NOREUSE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017352 if (PyModule_AddIntMacro(m, POSIX_FADV_NOREUSE)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017353#endif
17354#ifdef POSIX_FADV_WILLNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017355 if (PyModule_AddIntMacro(m, POSIX_FADV_WILLNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017356#endif
17357#ifdef POSIX_FADV_DONTNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017358 if (PyModule_AddIntMacro(m, POSIX_FADV_DONTNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017359#endif
17360
17361 /* constants for waitid */
17362#if defined(HAVE_SYS_WAIT_H) && defined(HAVE_WAITID)
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017363 if (PyModule_AddIntMacro(m, P_PID)) return -1;
17364 if (PyModule_AddIntMacro(m, P_PGID)) return -1;
17365 if (PyModule_AddIntMacro(m, P_ALL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017366#endif
17367#ifdef WEXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017368 if (PyModule_AddIntMacro(m, WEXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017369#endif
17370#ifdef WNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017371 if (PyModule_AddIntMacro(m, WNOWAIT)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017372#endif
17373#ifdef WSTOPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017374 if (PyModule_AddIntMacro(m, WSTOPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017375#endif
17376#ifdef CLD_EXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017377 if (PyModule_AddIntMacro(m, CLD_EXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017378#endif
17379#ifdef CLD_DUMPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017380 if (PyModule_AddIntMacro(m, CLD_DUMPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017381#endif
17382#ifdef CLD_TRAPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017383 if (PyModule_AddIntMacro(m, CLD_TRAPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017384#endif
17385#ifdef CLD_CONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017386 if (PyModule_AddIntMacro(m, CLD_CONTINUED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017387#endif
17388
17389 /* constants for lockf */
17390#ifdef F_LOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017391 if (PyModule_AddIntMacro(m, F_LOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017392#endif
17393#ifdef F_TLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017394 if (PyModule_AddIntMacro(m, F_TLOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017395#endif
17396#ifdef F_ULOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017397 if (PyModule_AddIntMacro(m, F_ULOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017398#endif
17399#ifdef F_TEST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017400 if (PyModule_AddIntMacro(m, F_TEST)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017401#endif
17402
Guido van Rossum246bc171999-02-01 23:54:31 +000017403#ifdef HAVE_SPAWNV
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017404 if (PyModule_AddIntConstant(m, "P_WAIT", _P_WAIT)) return -1;
17405 if (PyModule_AddIntConstant(m, "P_NOWAIT", _P_NOWAIT)) return -1;
17406 if (PyModule_AddIntConstant(m, "P_OVERLAY", _OLD_P_OVERLAY)) return -1;
17407 if (PyModule_AddIntConstant(m, "P_NOWAITO", _P_NOWAITO)) return -1;
17408 if (PyModule_AddIntConstant(m, "P_DETACH", _P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +000017409#endif
17410
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017411#ifdef HAVE_SCHED_H
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017412 if (PyModule_AddIntMacro(m, SCHED_OTHER)) return -1;
17413 if (PyModule_AddIntMacro(m, SCHED_FIFO)) return -1;
17414 if (PyModule_AddIntMacro(m, SCHED_RR)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017415#ifdef SCHED_SPORADIC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017416 if (PyModule_AddIntMacro(m, SCHED_SPORADIC) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017417#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017418#ifdef SCHED_BATCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017419 if (PyModule_AddIntMacro(m, SCHED_BATCH)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017420#endif
17421#ifdef SCHED_IDLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017422 if (PyModule_AddIntMacro(m, SCHED_IDLE)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017423#endif
17424#ifdef SCHED_RESET_ON_FORK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017425 if (PyModule_AddIntMacro(m, SCHED_RESET_ON_FORK)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017426#endif
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017427#ifdef SCHED_SYS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017428 if (PyModule_AddIntMacro(m, SCHED_SYS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017429#endif
17430#ifdef SCHED_IA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017431 if (PyModule_AddIntMacro(m, SCHED_IA)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017432#endif
17433#ifdef SCHED_FSS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017434 if (PyModule_AddIntMacro(m, SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017435#endif
17436#ifdef SCHED_FX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017437 if (PyModule_AddIntConstant(m, "SCHED_FX", SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017438#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017439#endif
17440
Benjamin Peterson9428d532011-09-14 11:45:52 -040017441#ifdef USE_XATTRS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017442 if (PyModule_AddIntMacro(m, XATTR_CREATE)) return -1;
17443 if (PyModule_AddIntMacro(m, XATTR_REPLACE)) return -1;
17444 if (PyModule_AddIntMacro(m, XATTR_SIZE_MAX)) return -1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040017445#endif
17446
Victor Stinner8b905bd2011-10-25 13:34:04 +020017447#ifdef RTLD_LAZY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017448 if (PyModule_AddIntMacro(m, RTLD_LAZY)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017449#endif
17450#ifdef RTLD_NOW
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017451 if (PyModule_AddIntMacro(m, RTLD_NOW)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017452#endif
17453#ifdef RTLD_GLOBAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017454 if (PyModule_AddIntMacro(m, RTLD_GLOBAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017455#endif
17456#ifdef RTLD_LOCAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017457 if (PyModule_AddIntMacro(m, RTLD_LOCAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017458#endif
17459#ifdef RTLD_NODELETE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017460 if (PyModule_AddIntMacro(m, RTLD_NODELETE)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017461#endif
17462#ifdef RTLD_NOLOAD
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017463 if (PyModule_AddIntMacro(m, RTLD_NOLOAD)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017464#endif
17465#ifdef RTLD_DEEPBIND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017466 if (PyModule_AddIntMacro(m, RTLD_DEEPBIND)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017467#endif
17468
Victor Stinner8c62be82010-05-06 00:08:46 +000017469 return 0;
Barry Warsaw4a342091996-12-19 23:50:02 +000017470}
17471
17472
Tim Peters5aa91602002-01-30 05:46:57 +000017473#if (defined(_MSC_VER) || defined(__WATCOMC__) || defined(__BORLANDC__)) && !defined(__QNX__)
Martin v. Löwis1a214512008-06-11 05:26:20 +000017474#define INITFUNC PyInit_nt
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017475#define MODNAME "nt"
Tim Peters58e0a8c2001-05-14 22:32:33 +000017476
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000017477#else
Martin v. Löwis1a214512008-06-11 05:26:20 +000017478#define INITFUNC PyInit_posix
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017479#define MODNAME "posix"
17480#endif
17481
Martin v. Löwis1a214512008-06-11 05:26:20 +000017482static struct PyModuleDef posixmodule = {
Victor Stinner8c62be82010-05-06 00:08:46 +000017483 PyModuleDef_HEAD_INIT,
17484 MODNAME,
17485 posix__doc__,
17486 -1,
17487 posix_methods,
17488 NULL,
17489 NULL,
17490 NULL,
17491 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +000017492};
17493
17494
Larry Hastings9cf065c2012-06-22 16:30:09 -070017495static char *have_functions[] = {
17496
17497#ifdef HAVE_FACCESSAT
17498 "HAVE_FACCESSAT",
17499#endif
17500
17501#ifdef HAVE_FCHDIR
17502 "HAVE_FCHDIR",
17503#endif
17504
17505#ifdef HAVE_FCHMOD
17506 "HAVE_FCHMOD",
17507#endif
17508
17509#ifdef HAVE_FCHMODAT
17510 "HAVE_FCHMODAT",
17511#endif
17512
17513#ifdef HAVE_FCHOWN
17514 "HAVE_FCHOWN",
17515#endif
17516
Larry Hastings00964ed2013-08-12 13:49:30 -040017517#ifdef HAVE_FCHOWNAT
17518 "HAVE_FCHOWNAT",
17519#endif
17520
Larry Hastings9cf065c2012-06-22 16:30:09 -070017521#ifdef HAVE_FEXECVE
17522 "HAVE_FEXECVE",
17523#endif
17524
17525#ifdef HAVE_FDOPENDIR
17526 "HAVE_FDOPENDIR",
17527#endif
17528
Georg Brandl306336b2012-06-24 12:55:33 +020017529#ifdef HAVE_FPATHCONF
17530 "HAVE_FPATHCONF",
17531#endif
17532
Larry Hastings9cf065c2012-06-22 16:30:09 -070017533#ifdef HAVE_FSTATAT
17534 "HAVE_FSTATAT",
17535#endif
17536
17537#ifdef HAVE_FSTATVFS
17538 "HAVE_FSTATVFS",
17539#endif
17540
Georg Brandl306336b2012-06-24 12:55:33 +020017541#ifdef HAVE_FTRUNCATE
17542 "HAVE_FTRUNCATE",
17543#endif
17544
Larry Hastings9cf065c2012-06-22 16:30:09 -070017545#ifdef HAVE_FUTIMENS
17546 "HAVE_FUTIMENS",
17547#endif
17548
17549#ifdef HAVE_FUTIMES
17550 "HAVE_FUTIMES",
17551#endif
17552
17553#ifdef HAVE_FUTIMESAT
17554 "HAVE_FUTIMESAT",
17555#endif
17556
17557#ifdef HAVE_LINKAT
17558 "HAVE_LINKAT",
17559#endif
17560
17561#ifdef HAVE_LCHFLAGS
17562 "HAVE_LCHFLAGS",
17563#endif
17564
17565#ifdef HAVE_LCHMOD
17566 "HAVE_LCHMOD",
17567#endif
17568
17569#ifdef HAVE_LCHOWN
17570 "HAVE_LCHOWN",
17571#endif
17572
17573#ifdef HAVE_LSTAT
17574 "HAVE_LSTAT",
17575#endif
17576
17577#ifdef HAVE_LUTIMES
17578 "HAVE_LUTIMES",
17579#endif
17580
17581#ifdef HAVE_MKDIRAT
17582 "HAVE_MKDIRAT",
17583#endif
17584
17585#ifdef HAVE_MKFIFOAT
17586 "HAVE_MKFIFOAT",
17587#endif
17588
17589#ifdef HAVE_MKNODAT
17590 "HAVE_MKNODAT",
17591#endif
17592
17593#ifdef HAVE_OPENAT
17594 "HAVE_OPENAT",
17595#endif
17596
17597#ifdef HAVE_READLINKAT
17598 "HAVE_READLINKAT",
17599#endif
17600
17601#ifdef HAVE_RENAMEAT
17602 "HAVE_RENAMEAT",
17603#endif
17604
17605#ifdef HAVE_SYMLINKAT
17606 "HAVE_SYMLINKAT",
17607#endif
17608
17609#ifdef HAVE_UNLINKAT
17610 "HAVE_UNLINKAT",
17611#endif
17612
17613#ifdef HAVE_UTIMENSAT
17614 "HAVE_UTIMENSAT",
17615#endif
17616
17617#ifdef MS_WINDOWS
17618 "MS_WINDOWS",
17619#endif
17620
17621 NULL
17622};
17623
17624
Mark Hammondfe51c6d2002-08-02 02:27:13 +000017625PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +000017626INITFUNC(void)
Guido van Rossumb6775db1994-08-01 11:34:53 +000017627{
Victor Stinner8c62be82010-05-06 00:08:46 +000017628 PyObject *m, *v;
Larry Hastings9cf065c2012-06-22 16:30:09 -070017629 PyObject *list;
17630 char **trace;
Tim Peters5aa91602002-01-30 05:46:57 +000017631
Brian Curtin52173d42010-12-02 18:29:18 +000017632#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017633 win32_can_symlink = enable_symlink();
Brian Curtin52173d42010-12-02 18:29:18 +000017634#endif
17635
Victor Stinner8c62be82010-05-06 00:08:46 +000017636 m = PyModule_Create(&posixmodule);
17637 if (m == NULL)
17638 return NULL;
Tim Peters5aa91602002-01-30 05:46:57 +000017639
Victor Stinner8c62be82010-05-06 00:08:46 +000017640 /* Initialize environ dictionary */
17641 v = convertenviron();
17642 Py_XINCREF(v);
17643 if (v == NULL || PyModule_AddObject(m, "environ", v) != 0)
17644 return NULL;
17645 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +000017646
Victor Stinner8c62be82010-05-06 00:08:46 +000017647 if (all_ins(m))
17648 return NULL;
Barry Warsaw4a342091996-12-19 23:50:02 +000017649
Victor Stinner8c62be82010-05-06 00:08:46 +000017650 if (setup_confname_tables(m))
17651 return NULL;
Fred Drakebec628d1999-12-15 18:31:10 +000017652
Victor Stinner8c62be82010-05-06 00:08:46 +000017653 Py_INCREF(PyExc_OSError);
17654 PyModule_AddObject(m, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +000017655
Guido van Rossumb3d39562000-01-31 18:41:26 +000017656#ifdef HAVE_PUTENV
Victor Stinner8c62be82010-05-06 00:08:46 +000017657 if (posix_putenv_garbage == NULL)
17658 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +000017659#endif
Guido van Rossum98bf58f2001-10-18 20:34:25 +000017660
Victor Stinner8c62be82010-05-06 00:08:46 +000017661 if (!initialized) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020017662#if defined(HAVE_WAITID) && !defined(__APPLE__)
17663 waitid_result_desc.name = MODNAME ".waitid_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017664 if (PyStructSequence_InitType2(&WaitidResultType, &waitid_result_desc) < 0)
17665 return NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017666#endif
17667
Christian Heimes25827622013-10-12 01:27:08 +020017668 stat_result_desc.name = "os.stat_result"; /* see issue #19209 */
Victor Stinner8c62be82010-05-06 00:08:46 +000017669 stat_result_desc.fields[7].name = PyStructSequence_UnnamedField;
17670 stat_result_desc.fields[8].name = PyStructSequence_UnnamedField;
17671 stat_result_desc.fields[9].name = PyStructSequence_UnnamedField;
Victor Stinner1c8f0592013-07-22 22:24:54 +020017672 if (PyStructSequence_InitType2(&StatResultType, &stat_result_desc) < 0)
17673 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017674 structseq_new = StatResultType.tp_new;
17675 StatResultType.tp_new = statresult_new;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017676
Christian Heimes25827622013-10-12 01:27:08 +020017677 statvfs_result_desc.name = "os.statvfs_result"; /* see issue #19209 */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017678 if (PyStructSequence_InitType2(&StatVFSResultType,
17679 &statvfs_result_desc) < 0)
17680 return NULL;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017681#ifdef NEED_TICKS_PER_SECOND
17682# if defined(HAVE_SYSCONF) && defined(_SC_CLK_TCK)
Victor Stinner8c62be82010-05-06 00:08:46 +000017683 ticks_per_second = sysconf(_SC_CLK_TCK);
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017684# elif defined(HZ)
Victor Stinner8c62be82010-05-06 00:08:46 +000017685 ticks_per_second = HZ;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017686# else
Victor Stinner8c62be82010-05-06 00:08:46 +000017687 ticks_per_second = 60; /* magic fallback value; may be bogus */
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017688# endif
17689#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017690
Benjamin Peterson0163c9a2011-08-02 18:11:38 -050017691#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017692 sched_param_desc.name = MODNAME ".sched_param";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017693 if (PyStructSequence_InitType2(&SchedParamType, &sched_param_desc) < 0)
17694 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100017695 SchedParamType.tp_new = os_sched_param;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017696#endif
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017697
17698 /* initialize TerminalSize_info */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017699 if (PyStructSequence_InitType2(&TerminalSizeType,
17700 &TerminalSize_desc) < 0)
17701 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017702 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020017703#if defined(HAVE_WAITID) && !defined(__APPLE__)
17704 Py_INCREF((PyObject*) &WaitidResultType);
17705 PyModule_AddObject(m, "waitid_result", (PyObject*) &WaitidResultType);
17706#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017707 Py_INCREF((PyObject*) &StatResultType);
17708 PyModule_AddObject(m, "stat_result", (PyObject*) &StatResultType);
17709 Py_INCREF((PyObject*) &StatVFSResultType);
17710 PyModule_AddObject(m, "statvfs_result",
17711 (PyObject*) &StatVFSResultType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017712
17713#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017714 Py_INCREF(&SchedParamType);
17715 PyModule_AddObject(m, "sched_param", (PyObject *)&SchedParamType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017716#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +000017717
Larry Hastings605a62d2012-06-24 04:33:36 -070017718 times_result_desc.name = MODNAME ".times_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017719 if (PyStructSequence_InitType2(&TimesResultType, &times_result_desc) < 0)
17720 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017721 PyModule_AddObject(m, "times_result", (PyObject *)&TimesResultType);
17722
17723 uname_result_desc.name = MODNAME ".uname_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017724 if (PyStructSequence_InitType2(&UnameResultType, &uname_result_desc) < 0)
17725 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017726 PyModule_AddObject(m, "uname_result", (PyObject *)&UnameResultType);
17727
Thomas Wouters477c8d52006-05-27 19:21:47 +000017728#ifdef __APPLE__
Victor Stinner8c62be82010-05-06 00:08:46 +000017729 /*
17730 * Step 2 of weak-linking support on Mac OS X.
17731 *
17732 * The code below removes functions that are not available on the
17733 * currently active platform.
17734 *
17735 * This block allow one to use a python binary that was build on
Larry Hastings9cf065c2012-06-22 16:30:09 -070017736 * OSX 10.4 on OSX 10.3, without losing access to new APIs on
Victor Stinner8c62be82010-05-06 00:08:46 +000017737 * OSX 10.4.
17738 */
Thomas Wouters477c8d52006-05-27 19:21:47 +000017739#ifdef HAVE_FSTATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017740 if (fstatvfs == NULL) {
17741 if (PyObject_DelAttrString(m, "fstatvfs") == -1) {
17742 return NULL;
17743 }
17744 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017745#endif /* HAVE_FSTATVFS */
17746
17747#ifdef HAVE_STATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017748 if (statvfs == NULL) {
17749 if (PyObject_DelAttrString(m, "statvfs") == -1) {
17750 return NULL;
17751 }
17752 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017753#endif /* HAVE_STATVFS */
17754
17755# ifdef HAVE_LCHOWN
Victor Stinner8c62be82010-05-06 00:08:46 +000017756 if (lchown == NULL) {
17757 if (PyObject_DelAttrString(m, "lchown") == -1) {
17758 return NULL;
17759 }
17760 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017761#endif /* HAVE_LCHOWN */
17762
17763
17764#endif /* __APPLE__ */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017765
Antoine Pitrou9d20e0e2012-09-12 18:01:36 +020017766 Py_INCREF(&TerminalSizeType);
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017767 PyModule_AddObject(m, "terminal_size", (PyObject*) &TerminalSizeType);
17768
Larry Hastings6fe20b32012-04-19 15:07:49 -070017769 billion = PyLong_FromLong(1000000000);
17770 if (!billion)
17771 return NULL;
17772
Larry Hastings9cf065c2012-06-22 16:30:09 -070017773 /* suppress "function not used" warnings */
17774 {
17775 int ignored;
17776 fd_specified("", -1);
17777 follow_symlinks_specified("", 1);
17778 dir_fd_and_follow_symlinks_invalid("chmod", DEFAULT_DIR_FD, 1);
17779 dir_fd_converter(Py_None, &ignored);
17780 dir_fd_unavailable(Py_None, &ignored);
17781 }
17782
17783 /*
17784 * provide list of locally available functions
17785 * so os.py can populate support_* lists
17786 */
17787 list = PyList_New(0);
17788 if (!list)
17789 return NULL;
17790 for (trace = have_functions; *trace; trace++) {
17791 PyObject *unicode = PyUnicode_DecodeASCII(*trace, strlen(*trace), NULL);
17792 if (!unicode)
17793 return NULL;
17794 if (PyList_Append(list, unicode))
17795 return NULL;
17796 Py_DECREF(unicode);
17797 }
17798 PyModule_AddObject(m, "_have_functions", list);
17799
17800 initialized = 1;
17801
Victor Stinner8c62be82010-05-06 00:08:46 +000017802 return m;
Guido van Rossumb6775db1994-08-01 11:34:53 +000017803}
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017804
17805#ifdef __cplusplus
17806}
17807#endif