blob: 542e600e7f8b32c38ee286d0157205dcc6a467da [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
Victor Stinnerf427a142014-10-22 12:33:23 +02009 test macro, e.g. '_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 _MSC_VER /* Microsoft compiler */
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +0000147#define HAVE_GETPPID 1
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000148#define HAVE_GETLOGIN 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000149#define HAVE_SPAWNV 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000150#define HAVE_EXECV 1
151#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000152#define HAVE_SYSTEM 1
153#define HAVE_CWAIT 1
154#define HAVE_FSYNC 1
Tim Peters11b23062003-04-23 02:39:17 +0000155#define fsync _commit
Andrew MacIntyre6c73af22002-03-03 03:07:07 +0000156#else
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000157/* Unix functions that the configure script doesn't check for */
158#define HAVE_EXECV 1
159#define HAVE_FORK 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000160#if defined(__USLC__) && defined(__SCO_VERSION__) /* SCO UDK Compiler */
Guido van Rossum2242f2f2001-04-11 20:58:20 +0000161#define HAVE_FORK1 1
162#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000163#define HAVE_GETEGID 1
164#define HAVE_GETEUID 1
165#define HAVE_GETGID 1
166#define HAVE_GETPPID 1
167#define HAVE_GETUID 1
168#define HAVE_KILL 1
169#define HAVE_OPENDIR 1
170#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000171#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000172#define HAVE_WAIT 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000173#define HAVE_TTYNAME 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000174#endif /* _MSC_VER */
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000175#endif /* ! __WATCOMC__ || __QNX__ */
Guido van Rossumad0ee831995-03-01 10:34:45 +0000176
Victor Stinnera2f7c002012-02-08 03:36:25 +0100177
Larry Hastings61272b72014-01-07 12:41:53 -0800178/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +1000179# one of the few times we lie about this name!
Larry Hastings44e2eaa2013-11-23 15:37:55 -0800180module os
Larry Hastings61272b72014-01-07 12:41:53 -0800181[clinic start generated code]*/
Larry Hastings2f936352014-08-05 14:04:04 +1000182/*[clinic end generated code: output=da39a3ee5e6b4b0d input=94a0f0f978acae17]*/
Victor Stinnera2f7c002012-02-08 03:36:25 +0100183
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000184#ifndef _MSC_VER
Guido van Rossum36bc6801995-06-14 22:54:23 +0000185
Martin v. Löwis8eb92a02002-09-19 08:03:21 +0000186#if defined(__sgi)&&_COMPILER_VERSION>=700
187/* declare ctermid_r if compiling with MIPSPro 7.x in ANSI C mode
188 (default) */
189extern char *ctermid_r(char *);
190#endif
191
Thomas Wouters1e0c2f42000-07-24 16:06:23 +0000192#ifndef HAVE_UNISTD_H
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000193#if defined(PYCC_VACPP)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000194extern int mkdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000195#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000196#if ( defined(__WATCOMC__) || defined(_MSC_VER) ) && !defined(__QNX__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000197extern int mkdir(const char *);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000198#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000199extern int mkdir(const char *, mode_t);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000200#endif
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000201#endif
202#if defined(__IBMC__) || defined(__IBMCPP__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000203extern int chdir(char *);
204extern int rmdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000205#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000206extern int chdir(const char *);
207extern int rmdir(const char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000208#endif
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000209extern int chmod(const char *, mode_t);
Christian Heimes4e30a842007-11-30 22:12:06 +0000210/*#ifdef HAVE_FCHMOD
211extern int fchmod(int, mode_t);
212#endif*/
213/*#ifdef HAVE_LCHMOD
214extern int lchmod(const char *, mode_t);
215#endif*/
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000216extern int chown(const char *, uid_t, gid_t);
217extern char *getcwd(char *, int);
218extern char *strerror(int);
219extern int link(const char *, const char *);
220extern int rename(const char *, const char *);
221extern int stat(const char *, struct stat *);
222extern int unlink(const char *);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000223#ifdef HAVE_SYMLINK
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000224extern int symlink(const char *, const char *);
Guido van Rossuma38a5031995-02-17 15:11:36 +0000225#endif /* HAVE_SYMLINK */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000226#ifdef HAVE_LSTAT
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000227extern int lstat(const char *, struct stat *);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000228#endif /* HAVE_LSTAT */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000229#endif /* !HAVE_UNISTD_H */
Guido van Rossum36bc6801995-06-14 22:54:23 +0000230
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000231#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000232
Guido van Rossumb6775db1994-08-01 11:34:53 +0000233#ifdef HAVE_UTIME_H
234#include <utime.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000235#endif /* HAVE_UTIME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000236
Guido van Rossum14ed0b21994-09-29 09:50:09 +0000237#ifdef HAVE_SYS_UTIME_H
238#include <sys/utime.h>
239#define HAVE_UTIME_H /* pretend we do for the rest of this file */
240#endif /* HAVE_SYS_UTIME_H */
241
Guido van Rossumb6775db1994-08-01 11:34:53 +0000242#ifdef HAVE_SYS_TIMES_H
243#include <sys/times.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000244#endif /* HAVE_SYS_TIMES_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000245
246#ifdef HAVE_SYS_PARAM_H
247#include <sys/param.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000248#endif /* HAVE_SYS_PARAM_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000249
250#ifdef HAVE_SYS_UTSNAME_H
251#include <sys/utsname.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000252#endif /* HAVE_SYS_UTSNAME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000253
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000254#ifdef HAVE_DIRENT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000255#include <dirent.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000256#define NAMLEN(dirent) strlen((dirent)->d_name)
257#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000258#if defined(__WATCOMC__) && !defined(__QNX__)
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000259#include <direct.h>
260#define NAMLEN(dirent) strlen((dirent)->d_name)
261#else
Guido van Rossumb6775db1994-08-01 11:34:53 +0000262#define dirent direct
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000263#define NAMLEN(dirent) (dirent)->d_namlen
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000264#endif
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000265#ifdef HAVE_SYS_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000266#include <sys/ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000267#endif
268#ifdef HAVE_SYS_DIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000269#include <sys/dir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000270#endif
271#ifdef HAVE_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000272#include <ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000273#endif
274#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +0000275
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000276#ifdef _MSC_VER
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000277#ifdef HAVE_DIRECT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000278#include <direct.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000279#endif
280#ifdef HAVE_IO_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000281#include <io.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000282#endif
283#ifdef HAVE_PROCESS_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000284#include <process.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000285#endif
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000286#ifndef VOLUME_NAME_DOS
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000287#define VOLUME_NAME_DOS 0x0
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000288#endif
289#ifndef VOLUME_NAME_NT
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000290#define VOLUME_NAME_NT 0x2
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000291#endif
292#ifndef IO_REPARSE_TAG_SYMLINK
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000293#define IO_REPARSE_TAG_SYMLINK (0xA000000CL)
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000294#endif
Tim Golden0321cf22014-05-05 19:46:17 +0100295#ifndef IO_REPARSE_TAG_MOUNT_POINT
296#define IO_REPARSE_TAG_MOUNT_POINT (0xA0000003L)
297#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000298#include "osdefs.h"
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +0000299#include <malloc.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +0000300#include <windows.h>
Victor Stinner8c62be82010-05-06 00:08:46 +0000301#include <shellapi.h> /* for ShellExecute() */
Brian Curtine8e4b3b2010-09-23 20:04:14 +0000302#include <lmcons.h> /* for UNLEN */
Brian Curtin52173d42010-12-02 18:29:18 +0000303#ifdef SE_CREATE_SYMBOLIC_LINK_NAME /* Available starting with Vista */
304#define HAVE_SYMLINK
Brian Curtin3b4499c2010-12-28 14:31:47 +0000305static int win32_can_symlink = 0;
Brian Curtin52173d42010-12-02 18:29:18 +0000306#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000307#endif /* _MSC_VER */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000308
Tim Petersbc2e10e2002-03-03 23:17:02 +0000309#ifndef MAXPATHLEN
Thomas Wouters477c8d52006-05-27 19:21:47 +0000310#if defined(PATH_MAX) && PATH_MAX > 1024
311#define MAXPATHLEN PATH_MAX
312#else
Tim Petersbc2e10e2002-03-03 23:17:02 +0000313#define MAXPATHLEN 1024
Thomas Wouters477c8d52006-05-27 19:21:47 +0000314#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000315#endif /* MAXPATHLEN */
316
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000317#ifdef UNION_WAIT
318/* Emulate some macros on systems that have a union instead of macros */
319
320#ifndef WIFEXITED
321#define WIFEXITED(u_wait) (!(u_wait).w_termsig && !(u_wait).w_coredump)
322#endif
323
324#ifndef WEXITSTATUS
325#define WEXITSTATUS(u_wait) (WIFEXITED(u_wait)?((u_wait).w_retcode):-1)
326#endif
327
328#ifndef WTERMSIG
329#define WTERMSIG(u_wait) ((u_wait).w_termsig)
330#endif
331
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000332#define WAIT_TYPE union wait
333#define WAIT_STATUS_INT(s) (s.w_status)
334
335#else /* !UNION_WAIT */
336#define WAIT_TYPE int
337#define WAIT_STATUS_INT(s) (s)
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000338#endif /* UNION_WAIT */
339
Greg Wardb48bc172000-03-01 21:51:56 +0000340/* Don't use the "_r" form if we don't need it (also, won't have a
341 prototype for it, at least on Solaris -- maybe others as well?). */
342#if defined(HAVE_CTERMID_R) && defined(WITH_THREAD)
343#define USE_CTERMID_R
344#endif
345
Fred Drake699f3522000-06-29 21:12:41 +0000346/* choose the appropriate stat and fstat functions and return structs */
Guido van Rossum64529cd2000-06-30 22:45:12 +0000347#undef STAT
Antoine Pitroue47e0932011-01-19 15:21:35 +0000348#undef FSTAT
349#undef STRUCT_STAT
Victor Stinner14b9b112013-06-25 00:37:25 +0200350#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +0000351# define STAT win32_stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700352# define LSTAT win32_lstat
Victor Stinner8c62be82010-05-06 00:08:46 +0000353# define FSTAT win32_fstat
354# define STRUCT_STAT struct win32_stat
Fred Drake699f3522000-06-29 21:12:41 +0000355#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000356# define STAT stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700357# define LSTAT lstat
Victor Stinner8c62be82010-05-06 00:08:46 +0000358# define FSTAT fstat
359# define STRUCT_STAT struct stat
Fred Drake699f3522000-06-29 21:12:41 +0000360#endif
361
Tim Peters11b23062003-04-23 02:39:17 +0000362#if defined(MAJOR_IN_MKDEV)
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000363#include <sys/mkdev.h>
364#else
365#if defined(MAJOR_IN_SYSMACROS)
366#include <sys/sysmacros.h>
367#endif
Neal Norwitz3d949422002-04-20 13:46:43 +0000368#if defined(HAVE_MKNOD) && defined(HAVE_SYS_MKDEV_H)
369#include <sys/mkdev.h>
370#endif
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000371#endif
Fred Drake699f3522000-06-29 21:12:41 +0000372
Victor Stinner6edddfa2013-11-24 19:22:57 +0100373#define DWORD_MAX 4294967295U
374
Larry Hastings9cf065c2012-06-22 16:30:09 -0700375
376#ifdef MS_WINDOWS
377static int
378win32_warn_bytes_api()
379{
380 return PyErr_WarnEx(PyExc_DeprecationWarning,
381 "The Windows bytes API has been deprecated, "
382 "use Unicode filenames instead",
383 1);
384}
385#endif
386
387
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200388#ifndef MS_WINDOWS
389PyObject *
390_PyLong_FromUid(uid_t uid)
391{
392 if (uid == (uid_t)-1)
393 return PyLong_FromLong(-1);
394 return PyLong_FromUnsignedLong(uid);
395}
396
397PyObject *
398_PyLong_FromGid(gid_t gid)
399{
400 if (gid == (gid_t)-1)
401 return PyLong_FromLong(-1);
402 return PyLong_FromUnsignedLong(gid);
403}
404
405int
406_Py_Uid_Converter(PyObject *obj, void *p)
407{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700408 uid_t uid;
409 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200410 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200411 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700412 unsigned long uresult;
413
414 index = PyNumber_Index(obj);
415 if (index == NULL) {
416 PyErr_Format(PyExc_TypeError,
417 "uid should be integer, not %.200s",
418 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200419 return 0;
420 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700421
422 /*
423 * Handling uid_t is complicated for two reasons:
424 * * Although uid_t is (always?) unsigned, it still
425 * accepts -1.
426 * * We don't know its size in advance--it may be
427 * bigger than an int, or it may be smaller than
428 * a long.
429 *
430 * So a bit of defensive programming is in order.
431 * Start with interpreting the value passed
432 * in as a signed long and see if it works.
433 */
434
435 result = PyLong_AsLongAndOverflow(index, &overflow);
436
437 if (!overflow) {
438 uid = (uid_t)result;
439
440 if (result == -1) {
441 if (PyErr_Occurred())
442 goto fail;
443 /* It's a legitimate -1, we're done. */
444 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200445 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700446
447 /* Any other negative number is disallowed. */
448 if (result < 0)
449 goto underflow;
450
451 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200452 if (sizeof(uid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700453 (long)uid != result)
454 goto underflow;
455 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200456 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700457
458 if (overflow < 0)
459 goto underflow;
460
461 /*
462 * Okay, the value overflowed a signed long. If it
463 * fits in an *unsigned* long, it may still be okay,
464 * as uid_t may be unsigned long on this platform.
465 */
466 uresult = PyLong_AsUnsignedLong(index);
467 if (PyErr_Occurred()) {
468 if (PyErr_ExceptionMatches(PyExc_OverflowError))
469 goto overflow;
470 goto fail;
471 }
472
473 uid = (uid_t)uresult;
474
475 /*
476 * If uid == (uid_t)-1, the user actually passed in ULONG_MAX,
477 * but this value would get interpreted as (uid_t)-1 by chown
478 * and its siblings. That's not what the user meant! So we
479 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100480 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700481 */
482 if (uid == (uid_t)-1)
483 goto overflow;
484
485 /* Ensure the value wasn't truncated. */
486 if (sizeof(uid_t) < sizeof(long) &&
487 (unsigned long)uid != uresult)
488 goto overflow;
489 /* fallthrough */
490
491success:
492 Py_DECREF(index);
493 *(uid_t *)p = uid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200494 return 1;
495
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700496underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200497 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700498 "uid is less than minimum");
499 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200500
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700501overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200502 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700503 "uid is greater than maximum");
504 /* fallthrough */
505
506fail:
507 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200508 return 0;
509}
510
511int
512_Py_Gid_Converter(PyObject *obj, void *p)
513{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700514 gid_t gid;
515 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200516 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200517 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700518 unsigned long uresult;
519
520 index = PyNumber_Index(obj);
521 if (index == NULL) {
522 PyErr_Format(PyExc_TypeError,
523 "gid should be integer, not %.200s",
524 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200525 return 0;
526 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700527
528 /*
529 * Handling gid_t is complicated for two reasons:
530 * * Although gid_t is (always?) unsigned, it still
531 * accepts -1.
532 * * We don't know its size in advance--it may be
533 * bigger than an int, or it may be smaller than
534 * a long.
535 *
536 * So a bit of defensive programming is in order.
537 * Start with interpreting the value passed
538 * in as a signed long and see if it works.
539 */
540
541 result = PyLong_AsLongAndOverflow(index, &overflow);
542
543 if (!overflow) {
544 gid = (gid_t)result;
545
546 if (result == -1) {
547 if (PyErr_Occurred())
548 goto fail;
549 /* It's a legitimate -1, we're done. */
550 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200551 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700552
553 /* Any other negative number is disallowed. */
554 if (result < 0) {
555 goto underflow;
556 }
557
558 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200559 if (sizeof(gid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700560 (long)gid != result)
561 goto underflow;
562 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200563 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700564
565 if (overflow < 0)
566 goto underflow;
567
568 /*
569 * Okay, the value overflowed a signed long. If it
570 * fits in an *unsigned* long, it may still be okay,
571 * as gid_t may be unsigned long on this platform.
572 */
573 uresult = PyLong_AsUnsignedLong(index);
574 if (PyErr_Occurred()) {
575 if (PyErr_ExceptionMatches(PyExc_OverflowError))
576 goto overflow;
577 goto fail;
578 }
579
580 gid = (gid_t)uresult;
581
582 /*
583 * If gid == (gid_t)-1, the user actually passed in ULONG_MAX,
584 * but this value would get interpreted as (gid_t)-1 by chown
585 * and its siblings. That's not what the user meant! So we
586 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100587 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700588 */
589 if (gid == (gid_t)-1)
590 goto overflow;
591
592 /* Ensure the value wasn't truncated. */
593 if (sizeof(gid_t) < sizeof(long) &&
594 (unsigned long)gid != uresult)
595 goto overflow;
596 /* fallthrough */
597
598success:
599 Py_DECREF(index);
600 *(gid_t *)p = gid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200601 return 1;
602
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700603underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200604 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700605 "gid is less than minimum");
606 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200607
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700608overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200609 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700610 "gid is greater than maximum");
611 /* fallthrough */
612
613fail:
614 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200615 return 0;
616}
617#endif /* MS_WINDOWS */
618
619
Serhiy Storchakab2653b32015-01-18 11:12:11 +0200620#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
621static int
622_Py_Dev_Converter(PyObject *obj, void *p)
623{
624#ifdef HAVE_LONG_LONG
625 *((dev_t *)p) = PyLong_AsUnsignedLongLong(obj);
626#else
627 *((dev_t *)p) = PyLong_AsUnsignedLong(obj);
628#endif
629 if (PyErr_Occurred())
630 return 0;
631 return 1;
632}
633
634#ifdef HAVE_LONG_LONG
635# define _PyLong_FromDev PyLong_FromLongLong
636#else
637# define _PyLong_FromDev PyLong_FromLong
638#endif
639
640#endif
641
642
Larry Hastings9cf065c2012-06-22 16:30:09 -0700643#ifdef AT_FDCWD
Trent Nelson9a461052012-09-18 21:50:06 -0400644/*
645 * Why the (int) cast? Solaris 10 defines AT_FDCWD as 0xffd19553 (-3041965);
646 * without the int cast, the value gets interpreted as uint (4291925331),
647 * which doesn't play nicely with all the initializer lines in this file that
648 * look like this:
649 * int dir_fd = DEFAULT_DIR_FD;
650 */
651#define DEFAULT_DIR_FD (int)AT_FDCWD
Larry Hastings9cf065c2012-06-22 16:30:09 -0700652#else
653#define DEFAULT_DIR_FD (-100)
654#endif
655
656static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200657_fd_converter(PyObject *o, int *p, const char *allowed)
658{
659 int overflow;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700660 long long_value;
661
662 PyObject *index = PyNumber_Index(o);
663 if (index == NULL) {
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200664 PyErr_Format(PyExc_TypeError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700665 "argument should be %s, not %.200s",
666 allowed, Py_TYPE(o)->tp_name);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700667 return 0;
668 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700669
670 long_value = PyLong_AsLongAndOverflow(index, &overflow);
671 Py_DECREF(index);
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200672 if (overflow > 0 || long_value > INT_MAX) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700673 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700674 "fd is greater than maximum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700675 return 0;
676 }
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200677 if (overflow < 0 || long_value < INT_MIN) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700678 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700679 "fd is less than minimum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700680 return 0;
681 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700682
Larry Hastings9cf065c2012-06-22 16:30:09 -0700683 *p = (int)long_value;
684 return 1;
685}
686
687static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200688dir_fd_converter(PyObject *o, void *p)
689{
690 if (o == Py_None) {
691 *(int *)p = DEFAULT_DIR_FD;
692 return 1;
693 }
694 return _fd_converter(o, (int *)p, "integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700695}
696
697
Larry Hastings9cf065c2012-06-22 16:30:09 -0700698/*
699 * A PyArg_ParseTuple "converter" function
700 * that handles filesystem paths in the manner
701 * preferred by the os module.
702 *
703 * path_converter accepts (Unicode) strings and their
704 * subclasses, and bytes and their subclasses. What
705 * it does with the argument depends on the platform:
706 *
707 * * On Windows, if we get a (Unicode) string we
708 * extract the wchar_t * and return it; if we get
709 * bytes we extract the char * and return that.
710 *
711 * * On all other platforms, strings are encoded
712 * to bytes using PyUnicode_FSConverter, then we
713 * extract the char * from the bytes object and
714 * return that.
715 *
716 * path_converter also optionally accepts signed
717 * integers (representing open file descriptors) instead
718 * of path strings.
719 *
720 * Input fields:
721 * path.nullable
722 * If nonzero, the path is permitted to be None.
723 * path.allow_fd
724 * If nonzero, the path is permitted to be a file handle
725 * (a signed int) instead of a string.
726 * path.function_name
727 * If non-NULL, path_converter will use that as the name
728 * of the function in error messages.
Larry Hastings31826802013-10-19 00:09:25 -0700729 * (If path.function_name is NULL it omits the function name.)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700730 * path.argument_name
731 * If non-NULL, path_converter will use that as the name
732 * of the parameter in error messages.
733 * (If path.argument_name is NULL it uses "path".)
734 *
735 * Output fields:
736 * path.wide
737 * Points to the path if it was expressed as Unicode
738 * and was not encoded. (Only used on Windows.)
739 * path.narrow
740 * Points to the path if it was expressed as bytes,
741 * or it was Unicode and was encoded to bytes.
742 * path.fd
743 * Contains a file descriptor if path.accept_fd was true
744 * and the caller provided a signed integer instead of any
745 * sort of string.
746 *
747 * WARNING: if your "path" parameter is optional, and is
748 * unspecified, path_converter will never get called.
749 * So if you set allow_fd, you *MUST* initialize path.fd = -1
750 * yourself!
751 * path.length
752 * The length of the path in characters, if specified as
753 * a string.
754 * path.object
755 * The original object passed in.
756 * path.cleanup
757 * For internal use only. May point to a temporary object.
758 * (Pay no attention to the man behind the curtain.)
759 *
760 * At most one of path.wide or path.narrow will be non-NULL.
761 * If path was None and path.nullable was set,
762 * or if path was an integer and path.allow_fd was set,
763 * both path.wide and path.narrow will be NULL
764 * and path.length will be 0.
Georg Brandlf7875592012-06-24 13:58:31 +0200765 *
Larry Hastings9cf065c2012-06-22 16:30:09 -0700766 * path_converter takes care to not write to the path_t
767 * unless it's successful. However it must reset the
768 * "cleanup" field each time it's called.
769 *
770 * Use as follows:
771 * path_t path;
772 * memset(&path, 0, sizeof(path));
773 * PyArg_ParseTuple(args, "O&", path_converter, &path);
774 * // ... use values from path ...
775 * path_cleanup(&path);
776 *
777 * (Note that if PyArg_Parse fails you don't need to call
778 * path_cleanup(). However it is safe to do so.)
779 */
780typedef struct {
Victor Stinner292c8352012-10-30 02:17:38 +0100781 const char *function_name;
782 const char *argument_name;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700783 int nullable;
784 int allow_fd;
785 wchar_t *wide;
786 char *narrow;
787 int fd;
788 Py_ssize_t length;
789 PyObject *object;
790 PyObject *cleanup;
791} path_t;
792
Larry Hastings2f936352014-08-05 14:04:04 +1000793#define PATH_T_INITIALIZE(function_name, argument_name, nullable, allow_fd) \
794 {function_name, argument_name, nullable, allow_fd, NULL, NULL, -1, 0, NULL, NULL}
Larry Hastings31826802013-10-19 00:09:25 -0700795
Larry Hastings9cf065c2012-06-22 16:30:09 -0700796static void
797path_cleanup(path_t *path) {
798 if (path->cleanup) {
Serhiy Storchaka505ff752014-02-09 13:33:53 +0200799 Py_CLEAR(path->cleanup);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700800 }
801}
802
803static int
804path_converter(PyObject *o, void *p) {
805 path_t *path = (path_t *)p;
806 PyObject *unicode, *bytes;
807 Py_ssize_t length;
808 char *narrow;
809
810#define FORMAT_EXCEPTION(exc, fmt) \
811 PyErr_Format(exc, "%s%s" fmt, \
812 path->function_name ? path->function_name : "", \
813 path->function_name ? ": " : "", \
814 path->argument_name ? path->argument_name : "path")
815
816 /* Py_CLEANUP_SUPPORTED support */
817 if (o == NULL) {
818 path_cleanup(path);
819 return 1;
820 }
821
822 /* ensure it's always safe to call path_cleanup() */
823 path->cleanup = NULL;
824
825 if (o == Py_None) {
826 if (!path->nullable) {
827 FORMAT_EXCEPTION(PyExc_TypeError,
828 "can't specify None for %s argument");
829 return 0;
830 }
831 path->wide = NULL;
832 path->narrow = NULL;
833 path->length = 0;
834 path->object = o;
835 path->fd = -1;
836 return 1;
837 }
838
839 unicode = PyUnicode_FromObject(o);
840 if (unicode) {
841#ifdef MS_WINDOWS
842 wchar_t *wide;
Victor Stinner59799a82013-11-13 14:17:30 +0100843
844 wide = PyUnicode_AsUnicodeAndSize(unicode, &length);
845 if (!wide) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700846 Py_DECREF(unicode);
847 return 0;
848 }
Victor Stinner59799a82013-11-13 14:17:30 +0100849 if (length > 32767) {
850 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700851 Py_DECREF(unicode);
852 return 0;
853 }
854
855 path->wide = wide;
856 path->narrow = NULL;
857 path->length = length;
858 path->object = o;
859 path->fd = -1;
860 path->cleanup = unicode;
861 return Py_CLEANUP_SUPPORTED;
862#else
863 int converted = PyUnicode_FSConverter(unicode, &bytes);
864 Py_DECREF(unicode);
865 if (!converted)
866 bytes = NULL;
867#endif
868 }
869 else {
870 PyErr_Clear();
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200871 if (PyObject_CheckBuffer(o))
872 bytes = PyBytes_FromObject(o);
873 else
874 bytes = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700875 if (!bytes) {
876 PyErr_Clear();
877 if (path->allow_fd) {
878 int fd;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200879 int result = _fd_converter(o, &fd,
880 "string, bytes or integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700881 if (result) {
882 path->wide = NULL;
883 path->narrow = NULL;
884 path->length = 0;
885 path->object = o;
886 path->fd = fd;
887 return result;
888 }
889 }
890 }
891 }
892
893 if (!bytes) {
894 if (!PyErr_Occurred())
895 FORMAT_EXCEPTION(PyExc_TypeError, "illegal type for %s parameter");
896 return 0;
897 }
898
899#ifdef MS_WINDOWS
900 if (win32_warn_bytes_api()) {
901 Py_DECREF(bytes);
902 return 0;
903 }
904#endif
905
906 length = PyBytes_GET_SIZE(bytes);
907#ifdef MS_WINDOWS
Victor Stinner75875072013-11-24 19:23:25 +0100908 if (length > MAX_PATH-1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700909 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
910 Py_DECREF(bytes);
911 return 0;
912 }
913#endif
914
915 narrow = PyBytes_AS_STRING(bytes);
Victor Stinner706768c2014-08-16 01:03:39 +0200916 if ((size_t)length != strlen(narrow)) {
Serhiy Storchakad8a14472014-09-06 20:07:17 +0300917 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700918 Py_DECREF(bytes);
919 return 0;
920 }
921
922 path->wide = NULL;
923 path->narrow = narrow;
924 path->length = length;
925 path->object = o;
926 path->fd = -1;
927 path->cleanup = bytes;
928 return Py_CLEANUP_SUPPORTED;
929}
930
931static void
932argument_unavailable_error(char *function_name, char *argument_name) {
933 PyErr_Format(PyExc_NotImplementedError,
934 "%s%s%s unavailable on this platform",
935 (function_name != NULL) ? function_name : "",
936 (function_name != NULL) ? ": ": "",
937 argument_name);
938}
939
940static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200941dir_fd_unavailable(PyObject *o, void *p)
942{
943 int dir_fd;
944 if (!dir_fd_converter(o, &dir_fd))
Larry Hastings9cf065c2012-06-22 16:30:09 -0700945 return 0;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200946 if (dir_fd != DEFAULT_DIR_FD) {
947 argument_unavailable_error(NULL, "dir_fd");
948 return 0;
949 }
950 *(int *)p = dir_fd;
951 return 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700952}
953
954static int
955fd_specified(char *function_name, int fd) {
956 if (fd == -1)
957 return 0;
958
959 argument_unavailable_error(function_name, "fd");
960 return 1;
961}
962
963static int
964follow_symlinks_specified(char *function_name, int follow_symlinks) {
965 if (follow_symlinks)
966 return 0;
967
968 argument_unavailable_error(function_name, "follow_symlinks");
969 return 1;
970}
971
972static int
973path_and_dir_fd_invalid(char *function_name, path_t *path, int dir_fd) {
974 if (!path->narrow && !path->wide && (dir_fd != DEFAULT_DIR_FD)) {
975 PyErr_Format(PyExc_ValueError,
976 "%s: can't specify dir_fd without matching path",
977 function_name);
978 return 1;
979 }
980 return 0;
981}
982
983static int
984dir_fd_and_fd_invalid(char *function_name, int dir_fd, int fd) {
985 if ((dir_fd != DEFAULT_DIR_FD) && (fd != -1)) {
986 PyErr_Format(PyExc_ValueError,
987 "%s: can't specify both dir_fd and fd",
988 function_name);
989 return 1;
990 }
991 return 0;
992}
993
994static int
995fd_and_follow_symlinks_invalid(char *function_name, int fd,
996 int follow_symlinks) {
997 if ((fd > 0) && (!follow_symlinks)) {
998 PyErr_Format(PyExc_ValueError,
999 "%s: cannot use fd and follow_symlinks together",
1000 function_name);
1001 return 1;
1002 }
1003 return 0;
1004}
1005
1006static int
1007dir_fd_and_follow_symlinks_invalid(char *function_name, int dir_fd,
1008 int follow_symlinks) {
1009 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
1010 PyErr_Format(PyExc_ValueError,
1011 "%s: cannot use dir_fd and follow_symlinks together",
1012 function_name);
1013 return 1;
1014 }
1015 return 0;
1016}
1017
Larry Hastings2f936352014-08-05 14:04:04 +10001018#ifdef MS_WINDOWS
1019 typedef PY_LONG_LONG Py_off_t;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001020#else
Larry Hastings2f936352014-08-05 14:04:04 +10001021 typedef off_t Py_off_t;
1022#endif
1023
1024static int
1025Py_off_t_converter(PyObject *arg, void *addr)
1026{
1027#ifdef HAVE_LARGEFILE_SUPPORT
1028 *((Py_off_t *)addr) = PyLong_AsLongLong(arg);
1029#else
1030 *((Py_off_t *)addr) = PyLong_AsLong(arg);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001031#endif
1032 if (PyErr_Occurred())
1033 return 0;
1034 return 1;
1035}
Larry Hastings2f936352014-08-05 14:04:04 +10001036
1037static PyObject *
1038PyLong_FromPy_off_t(Py_off_t offset)
1039{
1040#ifdef HAVE_LARGEFILE_SUPPORT
1041 return PyLong_FromLongLong(offset);
1042#else
1043 return PyLong_FromLong(offset);
Ross Lagerwallb1e5d592011-09-19 08:30:43 +02001044#endif
Larry Hastings2f936352014-08-05 14:04:04 +10001045}
1046
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001047
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001048#if defined _MSC_VER && _MSC_VER >= 1400
1049/* Microsoft CRT in VS2005 and higher will verify that a filehandle is
Andrew Svetlov737fb892012-12-18 21:14:22 +02001050 * valid and raise an assertion if it isn't.
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001051 * Normally, an invalid fd is likely to be a C program error and therefore
1052 * an assertion can be useful, but it does contradict the POSIX standard
1053 * which for write(2) states:
1054 * "Otherwise, -1 shall be returned and errno set to indicate the error."
1055 * "[EBADF] The fildes argument is not a valid file descriptor open for
1056 * writing."
1057 * Furthermore, python allows the user to enter any old integer
1058 * as a fd and should merely raise a python exception on error.
1059 * The Microsoft CRT doesn't provide an official way to check for the
1060 * validity of a file descriptor, but we can emulate its internal behaviour
Victor Stinner8c62be82010-05-06 00:08:46 +00001061 * by using the exported __pinfo data member and knowledge of the
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001062 * internal structures involved.
1063 * The structures below must be updated for each version of visual studio
1064 * according to the file internal.h in the CRT source, until MS comes
1065 * up with a less hacky way to do this.
1066 * (all of this is to avoid globally modifying the CRT behaviour using
1067 * _set_invalid_parameter_handler() and _CrtSetReportMode())
1068 */
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001069/* The actual size of the structure is determined at runtime.
1070 * Only the first items must be present.
1071 */
Steve Dower65e4cb12014-11-22 12:54:57 -08001072
1073#if _MSC_VER >= 1900
1074
1075typedef struct {
1076 CRITICAL_SECTION lock;
1077 intptr_t osfhnd;
1078 __int64 startpos;
1079 char osfile;
1080} my_ioinfo;
1081
1082#define IOINFO_L2E 6
1083#define IOINFO_ARRAYS 128
1084
1085#else
1086
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001087typedef struct {
Victor Stinner8c62be82010-05-06 00:08:46 +00001088 intptr_t osfhnd;
1089 char osfile;
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001090} my_ioinfo;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001091
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001092#define IOINFO_L2E 5
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001093#define IOINFO_ARRAYS 64
Steve Dower65e4cb12014-11-22 12:54:57 -08001094
1095#endif
1096
1097extern __declspec(dllimport) char * __pioinfo[];
1098#define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001099#define _NHANDLE_ (IOINFO_ARRAYS * IOINFO_ARRAY_ELTS)
1100#define FOPEN 0x01
1101#define _NO_CONSOLE_FILENO (intptr_t)-2
1102
1103/* This function emulates what the windows CRT does to validate file handles */
1104int
1105_PyVerify_fd(int fd)
1106{
Victor Stinner8c62be82010-05-06 00:08:46 +00001107 const int i1 = fd >> IOINFO_L2E;
1108 const int i2 = fd & ((1 << IOINFO_L2E) - 1);
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001109
Antoine Pitrou22e41552010-08-15 18:07:50 +00001110 static size_t sizeof_ioinfo = 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001111
Victor Stinner8c62be82010-05-06 00:08:46 +00001112 /* Determine the actual size of the ioinfo structure,
1113 * as used by the CRT loaded in memory
1114 */
1115 if (sizeof_ioinfo == 0 && __pioinfo[0] != NULL) {
1116 sizeof_ioinfo = _msize(__pioinfo[0]) / IOINFO_ARRAY_ELTS;
1117 }
1118 if (sizeof_ioinfo == 0) {
1119 /* This should not happen... */
1120 goto fail;
1121 }
1122
1123 /* See that it isn't a special CLEAR fileno */
1124 if (fd != _NO_CONSOLE_FILENO) {
1125 /* Microsoft CRT would check that 0<=fd<_nhandle but we can't do that. Instead
1126 * we check pointer validity and other info
1127 */
1128 if (0 <= i1 && i1 < IOINFO_ARRAYS && __pioinfo[i1] != NULL) {
1129 /* finally, check that the file is open */
1130 my_ioinfo* info = (my_ioinfo*)(__pioinfo[i1] + i2 * sizeof_ioinfo);
1131 if (info->osfile & FOPEN) {
1132 return 1;
1133 }
1134 }
1135 }
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001136 fail:
Victor Stinner8c62be82010-05-06 00:08:46 +00001137 errno = EBADF;
1138 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001139}
1140
1141/* the special case of checking dup2. The target fd must be in a sensible range */
1142static int
1143_PyVerify_fd_dup2(int fd1, int fd2)
1144{
Victor Stinner8c62be82010-05-06 00:08:46 +00001145 if (!_PyVerify_fd(fd1))
1146 return 0;
1147 if (fd2 == _NO_CONSOLE_FILENO)
1148 return 0;
1149 if ((unsigned)fd2 < _NHANDLE_)
1150 return 1;
1151 else
1152 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001153}
1154#else
1155/* dummy version. _PyVerify_fd() is already defined in fileobject.h */
1156#define _PyVerify_fd_dup2(A, B) (1)
1157#endif
1158
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001159#ifdef MS_WINDOWS
Brian Curtinf5e76d02010-11-24 13:14:05 +00001160
1161static int
Brian Curtind25aef52011-06-13 15:16:04 -05001162win32_get_reparse_tag(HANDLE reparse_point_handle, ULONG *reparse_tag)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001163{
1164 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
1165 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
1166 DWORD n_bytes_returned;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001167
1168 if (0 == DeviceIoControl(
1169 reparse_point_handle,
1170 FSCTL_GET_REPARSE_POINT,
1171 NULL, 0, /* in buffer */
1172 target_buffer, sizeof(target_buffer),
1173 &n_bytes_returned,
1174 NULL)) /* we're not using OVERLAPPED_IO */
Brian Curtind25aef52011-06-13 15:16:04 -05001175 return FALSE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001176
1177 if (reparse_tag)
1178 *reparse_tag = rdb->ReparseTag;
1179
Brian Curtind25aef52011-06-13 15:16:04 -05001180 return TRUE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001181}
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001182
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001183#endif /* MS_WINDOWS */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001184
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001185/* Return a dictionary corresponding to the POSIX environment table */
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001186#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Jack Jansenea0c3822002-08-01 21:57:49 +00001187/* On Darwin/MacOSX a shared library or framework has no access to
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001188** environ directly, we must obtain it with _NSGetEnviron(). See also
1189** man environ(7).
Jack Jansenea0c3822002-08-01 21:57:49 +00001190*/
1191#include <crt_externs.h>
1192static char **environ;
1193#elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001194extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001195#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001196
Barry Warsaw53699e91996-12-10 23:23:01 +00001197static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001198convertenviron(void)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001199{
Victor Stinner8c62be82010-05-06 00:08:46 +00001200 PyObject *d;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001201#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00001202 wchar_t **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001203#else
Victor Stinner8c62be82010-05-06 00:08:46 +00001204 char **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001205#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00001206
Victor Stinner8c62be82010-05-06 00:08:46 +00001207 d = PyDict_New();
1208 if (d == NULL)
1209 return NULL;
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001210#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Victor Stinner8c62be82010-05-06 00:08:46 +00001211 if (environ == NULL)
1212 environ = *_NSGetEnviron();
1213#endif
1214#ifdef MS_WINDOWS
1215 /* _wenviron must be initialized in this way if the program is started
1216 through main() instead of wmain(). */
1217 _wgetenv(L"");
1218 if (_wenviron == NULL)
1219 return d;
1220 /* This part ignores errors */
1221 for (e = _wenviron; *e != NULL; e++) {
1222 PyObject *k;
1223 PyObject *v;
1224 wchar_t *p = wcschr(*e, L'=');
1225 if (p == NULL)
1226 continue;
1227 k = PyUnicode_FromWideChar(*e, (Py_ssize_t)(p-*e));
1228 if (k == NULL) {
1229 PyErr_Clear();
1230 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001231 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001232 v = PyUnicode_FromWideChar(p+1, wcslen(p+1));
1233 if (v == NULL) {
1234 PyErr_Clear();
1235 Py_DECREF(k);
1236 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001237 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001238 if (PyDict_GetItem(d, k) == NULL) {
1239 if (PyDict_SetItem(d, k, v) != 0)
1240 PyErr_Clear();
1241 }
1242 Py_DECREF(k);
1243 Py_DECREF(v);
1244 }
1245#else
1246 if (environ == NULL)
1247 return d;
1248 /* This part ignores errors */
1249 for (e = environ; *e != NULL; e++) {
1250 PyObject *k;
1251 PyObject *v;
1252 char *p = strchr(*e, '=');
1253 if (p == NULL)
1254 continue;
Victor Stinner84ae1182010-05-06 22:05:07 +00001255 k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
Victor Stinner8c62be82010-05-06 00:08:46 +00001256 if (k == NULL) {
1257 PyErr_Clear();
1258 continue;
1259 }
Victor Stinner84ae1182010-05-06 22:05:07 +00001260 v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
Victor Stinner8c62be82010-05-06 00:08:46 +00001261 if (v == NULL) {
1262 PyErr_Clear();
1263 Py_DECREF(k);
1264 continue;
1265 }
1266 if (PyDict_GetItem(d, k) == NULL) {
1267 if (PyDict_SetItem(d, k, v) != 0)
1268 PyErr_Clear();
1269 }
1270 Py_DECREF(k);
1271 Py_DECREF(v);
Guido van Rossumd48f2521997-12-05 22:19:34 +00001272 }
1273#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001274 return d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001275}
1276
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001277/* Set a POSIX-specific error from errno, and return NULL */
1278
Barry Warsawd58d7641998-07-23 16:14:40 +00001279static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001280posix_error(void)
Guido van Rossumad0ee831995-03-01 10:34:45 +00001281{
Victor Stinner8c62be82010-05-06 00:08:46 +00001282 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001283}
Mark Hammondef8b6542001-05-13 08:04:26 +00001284
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00001285#ifdef MS_WINDOWS
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001286static PyObject *
Brian Curtind40e6f72010-07-08 21:39:08 +00001287win32_error(char* function, const char* filename)
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001288{
Victor Stinner8c62be82010-05-06 00:08:46 +00001289 /* XXX We should pass the function name along in the future.
1290 (winreg.c also wants to pass the function name.)
1291 This would however require an additional param to the
1292 Windows error object, which is non-trivial.
1293 */
1294 errno = GetLastError();
1295 if (filename)
1296 return PyErr_SetFromWindowsErrWithFilename(errno, filename);
1297 else
1298 return PyErr_SetFromWindowsErr(errno);
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001299}
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001300
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001301static PyObject *
Victor Stinnereb5657a2011-09-30 01:44:27 +02001302win32_error_object(char* function, PyObject* filename)
1303{
1304 /* XXX - see win32_error for comments on 'function' */
1305 errno = GetLastError();
1306 if (filename)
1307 return PyErr_SetExcFromWindowsErrWithFilenameObject(
Andrew Svetlov2606a6f2012-12-19 14:33:35 +02001308 PyExc_OSError,
Victor Stinnereb5657a2011-09-30 01:44:27 +02001309 errno,
1310 filename);
1311 else
1312 return PyErr_SetFromWindowsErr(errno);
1313}
1314
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001315#endif /* MS_WINDOWS */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001316
Larry Hastings9cf065c2012-06-22 16:30:09 -07001317static PyObject *
Victor Stinner292c8352012-10-30 02:17:38 +01001318path_error(path_t *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001319{
1320#ifdef MS_WINDOWS
Victor Stinner292c8352012-10-30 02:17:38 +01001321 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
1322 0, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001323#else
Victor Stinner292c8352012-10-30 02:17:38 +01001324 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001325#endif
1326}
1327
Larry Hastings31826802013-10-19 00:09:25 -07001328
Larry Hastingsb0827312014-02-09 22:05:19 -08001329static PyObject *
1330path_error2(path_t *path, path_t *path2)
1331{
1332#ifdef MS_WINDOWS
1333 return PyErr_SetExcFromWindowsErrWithFilenameObjects(PyExc_OSError,
1334 0, path->object, path2->object);
1335#else
1336 return PyErr_SetFromErrnoWithFilenameObjects(PyExc_OSError,
1337 path->object, path2->object);
1338#endif
1339}
1340
1341
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001342/* POSIX generic methods */
1343
Larry Hastings2f936352014-08-05 14:04:04 +10001344static int
1345fildes_converter(PyObject *o, void *p)
Fred Drake4d1e64b2002-04-15 19:40:07 +00001346{
Victor Stinner8c62be82010-05-06 00:08:46 +00001347 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +10001348 int *pointer = (int *)p;
1349 fd = PyObject_AsFileDescriptor(o);
Victor Stinner8c62be82010-05-06 00:08:46 +00001350 if (fd < 0)
Larry Hastings2f936352014-08-05 14:04:04 +10001351 return 0;
1352 if (!_PyVerify_fd(fd)) {
1353 posix_error();
1354 return 0;
1355 }
1356 *pointer = fd;
1357 return 1;
1358}
1359
1360static PyObject *
1361posix_fildes_fd(int fd, int (*func)(int))
1362{
1363 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00001364 Py_BEGIN_ALLOW_THREADS
1365 res = (*func)(fd);
1366 Py_END_ALLOW_THREADS
1367 if (res < 0)
1368 return posix_error();
1369 Py_INCREF(Py_None);
1370 return Py_None;
Fred Drake4d1e64b2002-04-15 19:40:07 +00001371}
Guido van Rossum21142a01999-01-08 21:05:37 +00001372
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001373
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001374#ifdef MS_WINDOWS
Thomas Wouters477c8d52006-05-27 19:21:47 +00001375/* This is a reimplementation of the C library's chdir function,
1376 but one that produces Win32 errors instead of DOS error codes.
1377 chdir is essentially a wrapper around SetCurrentDirectory; however,
1378 it also needs to set "magic" environment variables indicating
1379 the per-drive current directory, which are of the form =<drive>: */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001380static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001381win32_chdir(LPCSTR path)
1382{
Victor Stinner75875072013-11-24 19:23:25 +01001383 char new_path[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00001384 int result;
1385 char env[4] = "=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001386
Victor Stinner8c62be82010-05-06 00:08:46 +00001387 if(!SetCurrentDirectoryA(path))
1388 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001389 result = GetCurrentDirectoryA(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001390 if (!result)
1391 return FALSE;
1392 /* In the ANSI API, there should not be any paths longer
Victor Stinner75875072013-11-24 19:23:25 +01001393 than MAX_PATH-1 (not including the final null character). */
1394 assert(result < Py_ARRAY_LENGTH(new_path));
Victor Stinner8c62be82010-05-06 00:08:46 +00001395 if (strncmp(new_path, "\\\\", 2) == 0 ||
1396 strncmp(new_path, "//", 2) == 0)
1397 /* UNC path, nothing to do. */
1398 return TRUE;
1399 env[1] = new_path[0];
1400 return SetEnvironmentVariableA(env, new_path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001401}
1402
1403/* The Unicode version differs from the ANSI version
1404 since the current directory might exceed MAX_PATH characters */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001405static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001406win32_wchdir(LPCWSTR path)
1407{
Victor Stinner75875072013-11-24 19:23:25 +01001408 wchar_t _new_path[MAX_PATH], *new_path = _new_path;
Victor Stinner8c62be82010-05-06 00:08:46 +00001409 int result;
1410 wchar_t env[4] = L"=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001411
Victor Stinner8c62be82010-05-06 00:08:46 +00001412 if(!SetCurrentDirectoryW(path))
1413 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001414 result = GetCurrentDirectoryW(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001415 if (!result)
1416 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001417 if (result > Py_ARRAY_LENGTH(new_path)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001418 new_path = PyMem_RawMalloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00001419 if (!new_path) {
1420 SetLastError(ERROR_OUTOFMEMORY);
1421 return FALSE;
1422 }
1423 result = GetCurrentDirectoryW(result, new_path);
1424 if (!result) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001425 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001426 return FALSE;
1427 }
1428 }
1429 if (wcsncmp(new_path, L"\\\\", 2) == 0 ||
1430 wcsncmp(new_path, L"//", 2) == 0)
1431 /* UNC path, nothing to do. */
1432 return TRUE;
1433 env[1] = new_path[0];
1434 result = SetEnvironmentVariableW(env, new_path);
1435 if (new_path != _new_path)
Victor Stinnerb6404912013-07-07 16:21:41 +02001436 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001437 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001438}
1439#endif
1440
Martin v. Löwis14694662006-02-03 12:54:16 +00001441#ifdef MS_WINDOWS
1442/* The CRT of Windows has a number of flaws wrt. its stat() implementation:
1443 - time stamps are restricted to second resolution
1444 - file modification times suffer from forth-and-back conversions between
1445 UTC and local time
1446 Therefore, we implement our own stat, based on the Win32 API directly.
1447*/
Victor Stinner8c62be82010-05-06 00:08:46 +00001448#define HAVE_STAT_NSEC 1
Zachary Ware63f277b2014-06-19 09:46:37 -05001449#define HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES 1
Martin v. Löwis14694662006-02-03 12:54:16 +00001450
1451struct win32_stat{
Brian Curtin87e63a22012-12-31 11:59:48 -06001452 unsigned long st_dev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001453 __int64 st_ino;
1454 unsigned short st_mode;
1455 int st_nlink;
1456 int st_uid;
1457 int st_gid;
Brian Curtin87e63a22012-12-31 11:59:48 -06001458 unsigned long st_rdev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001459 __int64 st_size;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001460 time_t st_atime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001461 int st_atime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001462 time_t st_mtime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001463 int st_mtime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001464 time_t st_ctime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001465 int st_ctime_nsec;
Zachary Ware63f277b2014-06-19 09:46:37 -05001466 unsigned long st_file_attributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001467};
1468
1469static __int64 secs_between_epochs = 11644473600; /* Seconds between 1.1.1601 and 1.1.1970 */
1470
1471static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001472FILE_TIME_to_time_t_nsec(FILETIME *in_ptr, time_t *time_out, int* nsec_out)
Martin v. Löwis14694662006-02-03 12:54:16 +00001473{
Victor Stinner8c62be82010-05-06 00:08:46 +00001474 /* XXX endianness. Shouldn't matter, as all Windows implementations are little-endian */
1475 /* Cannot simply cast and dereference in_ptr,
1476 since it might not be aligned properly */
1477 __int64 in;
1478 memcpy(&in, in_ptr, sizeof(in));
1479 *nsec_out = (int)(in % 10000000) * 100; /* FILETIME is in units of 100 nsec. */
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001480 *time_out = Py_SAFE_DOWNCAST((in / 10000000) - secs_between_epochs, __int64, time_t);
Martin v. Löwis14694662006-02-03 12:54:16 +00001481}
1482
Thomas Wouters477c8d52006-05-27 19:21:47 +00001483static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001484time_t_to_FILE_TIME(time_t time_in, int nsec_in, FILETIME *out_ptr)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001485{
Victor Stinner8c62be82010-05-06 00:08:46 +00001486 /* XXX endianness */
1487 __int64 out;
1488 out = time_in + secs_between_epochs;
1489 out = out * 10000000 + nsec_in / 100;
1490 memcpy(out_ptr, &out, sizeof(out));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001491}
1492
Martin v. Löwis14694662006-02-03 12:54:16 +00001493/* Below, we *know* that ugo+r is 0444 */
1494#if _S_IREAD != 0400
1495#error Unsupported C library
1496#endif
1497static int
1498attributes_to_mode(DWORD attr)
1499{
Victor Stinner8c62be82010-05-06 00:08:46 +00001500 int m = 0;
1501 if (attr & FILE_ATTRIBUTE_DIRECTORY)
1502 m |= _S_IFDIR | 0111; /* IFEXEC for user,group,other */
1503 else
1504 m |= _S_IFREG;
1505 if (attr & FILE_ATTRIBUTE_READONLY)
1506 m |= 0444;
1507 else
1508 m |= 0666;
1509 return m;
Martin v. Löwis14694662006-02-03 12:54:16 +00001510}
1511
1512static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001513attribute_data_to_stat(BY_HANDLE_FILE_INFORMATION *info, ULONG reparse_tag, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001514{
Victor Stinner8c62be82010-05-06 00:08:46 +00001515 memset(result, 0, sizeof(*result));
1516 result->st_mode = attributes_to_mode(info->dwFileAttributes);
1517 result->st_size = (((__int64)info->nFileSizeHigh)<<32) + info->nFileSizeLow;
Brian Curtin490b32a2012-12-26 07:03:03 -06001518 result->st_dev = info->dwVolumeSerialNumber;
1519 result->st_rdev = result->st_dev;
Victor Stinner8c62be82010-05-06 00:08:46 +00001520 FILE_TIME_to_time_t_nsec(&info->ftCreationTime, &result->st_ctime, &result->st_ctime_nsec);
1521 FILE_TIME_to_time_t_nsec(&info->ftLastWriteTime, &result->st_mtime, &result->st_mtime_nsec);
1522 FILE_TIME_to_time_t_nsec(&info->ftLastAccessTime, &result->st_atime, &result->st_atime_nsec);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001523 result->st_nlink = info->nNumberOfLinks;
Brian Curtin1b9df392010-11-24 20:24:31 +00001524 result->st_ino = (((__int64)info->nFileIndexHigh)<<32) + info->nFileIndexLow;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001525 if (reparse_tag == IO_REPARSE_TAG_SYMLINK) {
1526 /* first clear the S_IFMT bits */
Christian Heimes99d61352013-06-23 23:56:05 +02001527 result->st_mode ^= (result->st_mode & S_IFMT);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001528 /* now set the bits that make this a symlink */
Christian Heimes99d61352013-06-23 23:56:05 +02001529 result->st_mode |= S_IFLNK;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001530 }
Zachary Ware63f277b2014-06-19 09:46:37 -05001531 result->st_file_attributes = info->dwFileAttributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001532
Victor Stinner8c62be82010-05-06 00:08:46 +00001533 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001534}
1535
Guido van Rossumd8faa362007-04-27 19:54:29 +00001536static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001537attributes_from_dir(LPCSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001538{
Victor Stinner8c62be82010-05-06 00:08:46 +00001539 HANDLE hFindFile;
1540 WIN32_FIND_DATAA FileData;
1541 hFindFile = FindFirstFileA(pszFile, &FileData);
1542 if (hFindFile == INVALID_HANDLE_VALUE)
1543 return FALSE;
1544 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001545 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001546 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001547 info->dwFileAttributes = FileData.dwFileAttributes;
1548 info->ftCreationTime = FileData.ftCreationTime;
1549 info->ftLastAccessTime = FileData.ftLastAccessTime;
1550 info->ftLastWriteTime = FileData.ftLastWriteTime;
1551 info->nFileSizeHigh = FileData.nFileSizeHigh;
1552 info->nFileSizeLow = FileData.nFileSizeLow;
1553/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001554 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1555 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001556 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001557}
1558
1559static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001560attributes_from_dir_w(LPCWSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001561{
Victor Stinner8c62be82010-05-06 00:08:46 +00001562 HANDLE hFindFile;
1563 WIN32_FIND_DATAW FileData;
1564 hFindFile = FindFirstFileW(pszFile, &FileData);
1565 if (hFindFile == INVALID_HANDLE_VALUE)
1566 return FALSE;
1567 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001568 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001569 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001570 info->dwFileAttributes = FileData.dwFileAttributes;
1571 info->ftCreationTime = FileData.ftCreationTime;
1572 info->ftLastAccessTime = FileData.ftLastAccessTime;
1573 info->ftLastWriteTime = FileData.ftLastWriteTime;
1574 info->nFileSizeHigh = FileData.nFileSizeHigh;
1575 info->nFileSizeLow = FileData.nFileSizeLow;
1576/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001577 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1578 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001579 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001580}
1581
Brian Curtind25aef52011-06-13 15:16:04 -05001582/* Grab GetFinalPathNameByHandle dynamically from kernel32 */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001583static int has_GetFinalPathNameByHandle = -1;
Brian Curtind25aef52011-06-13 15:16:04 -05001584static DWORD (CALLBACK *Py_GetFinalPathNameByHandleW)(HANDLE, LPWSTR, DWORD,
1585 DWORD);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001586static int
Brian Curtind25aef52011-06-13 15:16:04 -05001587check_GetFinalPathNameByHandle()
Brian Curtinf5e76d02010-11-24 13:14:05 +00001588{
Brian Curtind25aef52011-06-13 15:16:04 -05001589 HINSTANCE hKernel32;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001590 DWORD (CALLBACK *Py_GetFinalPathNameByHandleA)(HANDLE, LPSTR, DWORD,
1591 DWORD);
1592
Brian Curtind25aef52011-06-13 15:16:04 -05001593 /* only recheck */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001594 if (-1 == has_GetFinalPathNameByHandle)
Brian Curtind25aef52011-06-13 15:16:04 -05001595 {
Martin v. Löwis50590f12012-01-14 17:54:09 +01001596 hKernel32 = GetModuleHandleW(L"KERNEL32");
Brian Curtind25aef52011-06-13 15:16:04 -05001597 *(FARPROC*)&Py_GetFinalPathNameByHandleA = GetProcAddress(hKernel32,
1598 "GetFinalPathNameByHandleA");
1599 *(FARPROC*)&Py_GetFinalPathNameByHandleW = GetProcAddress(hKernel32,
1600 "GetFinalPathNameByHandleW");
1601 has_GetFinalPathNameByHandle = Py_GetFinalPathNameByHandleA &&
1602 Py_GetFinalPathNameByHandleW;
1603 }
1604 return has_GetFinalPathNameByHandle;
1605}
1606
1607static BOOL
1608get_target_path(HANDLE hdl, wchar_t **target_path)
1609{
1610 int buf_size, result_length;
1611 wchar_t *buf;
1612
1613 /* We have a good handle to the target, use it to determine
1614 the target path name (then we'll call lstat on it). */
1615 buf_size = Py_GetFinalPathNameByHandleW(hdl, 0, 0,
1616 VOLUME_NAME_DOS);
1617 if(!buf_size)
1618 return FALSE;
1619
Victor Stinnerb6404912013-07-07 16:21:41 +02001620 buf = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtinc8be8402011-06-14 09:52:50 -05001621 if (!buf) {
1622 SetLastError(ERROR_OUTOFMEMORY);
1623 return FALSE;
1624 }
1625
Brian Curtind25aef52011-06-13 15:16:04 -05001626 result_length = Py_GetFinalPathNameByHandleW(hdl,
1627 buf, buf_size, VOLUME_NAME_DOS);
1628
1629 if(!result_length) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001630 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001631 return FALSE;
1632 }
1633
1634 if(!CloseHandle(hdl)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001635 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001636 return FALSE;
1637 }
1638
1639 buf[result_length] = 0;
1640
1641 *target_path = buf;
1642 return TRUE;
1643}
1644
1645static int
1646win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1647 BOOL traverse);
1648static int
1649win32_xstat_impl(const char *path, struct win32_stat *result,
1650 BOOL traverse)
1651{
Victor Stinner26de69d2011-06-17 15:15:38 +02001652 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001653 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001654 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001655 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001656 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001657 const char *dot;
1658
Brian Curtind25aef52011-06-13 15:16:04 -05001659 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001660 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1661 traverse reparse point. */
1662 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001663 }
1664
Brian Curtinf5e76d02010-11-24 13:14:05 +00001665 hFile = CreateFileA(
1666 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001667 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001668 0, /* share mode */
1669 NULL, /* security attributes */
1670 OPEN_EXISTING,
1671 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001672 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1673 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001674 the symlink path again and not the actual final path. */
Brian Curtind25aef52011-06-13 15:16:04 -05001675 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
1676 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001677 NULL);
1678
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001679 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001680 /* Either the target doesn't exist, or we don't have access to
1681 get a handle to it. If the former, we need to return an error.
1682 If the latter, we can use attributes_from_dir. */
1683 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001684 return -1;
1685 /* Could not get attributes on open file. Fall back to
1686 reading the directory. */
1687 if (!attributes_from_dir(path, &info, &reparse_tag))
1688 /* Very strange. This should not fail now */
1689 return -1;
1690 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1691 if (traverse) {
1692 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001693 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001694 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001695 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001696 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001697 } else {
1698 if (!GetFileInformationByHandle(hFile, &info)) {
1699 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001700 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001701 }
1702 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001703 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1704 return -1;
1705
1706 /* Close the outer open file handle now that we're about to
1707 reopen it with different flags. */
1708 if (!CloseHandle(hFile))
1709 return -1;
1710
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001711 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001712 /* In order to call GetFinalPathNameByHandle we need to open
1713 the file without the reparse handling flag set. */
1714 hFile2 = CreateFileA(
1715 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1716 NULL, OPEN_EXISTING,
1717 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1718 NULL);
1719 if (hFile2 == INVALID_HANDLE_VALUE)
1720 return -1;
1721
1722 if (!get_target_path(hFile2, &target_path))
1723 return -1;
1724
1725 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001726 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001727 return code;
1728 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001729 } else
1730 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001731 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001732 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001733
1734 /* Set S_IEXEC if it is an .exe, .bat, ... */
1735 dot = strrchr(path, '.');
1736 if (dot) {
1737 if (stricmp(dot, ".bat") == 0 || stricmp(dot, ".cmd") == 0 ||
1738 stricmp(dot, ".exe") == 0 || stricmp(dot, ".com") == 0)
1739 result->st_mode |= 0111;
1740 }
1741 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001742}
1743
1744static int
Brian Curtind25aef52011-06-13 15:16:04 -05001745win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1746 BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001747{
1748 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001749 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001750 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001751 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001752 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001753 const wchar_t *dot;
1754
Brian Curtind25aef52011-06-13 15:16:04 -05001755 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001756 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1757 traverse reparse point. */
1758 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001759 }
1760
Brian Curtinf5e76d02010-11-24 13:14:05 +00001761 hFile = CreateFileW(
1762 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001763 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001764 0, /* share mode */
1765 NULL, /* security attributes */
1766 OPEN_EXISTING,
1767 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001768 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1769 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001770 the symlink path again and not the actual final path. */
Victor Stinner26de69d2011-06-17 15:15:38 +02001771 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
Brian Curtind25aef52011-06-13 15:16:04 -05001772 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001773 NULL);
1774
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001775 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001776 /* Either the target doesn't exist, or we don't have access to
1777 get a handle to it. If the former, we need to return an error.
1778 If the latter, we can use attributes_from_dir. */
1779 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001780 return -1;
1781 /* Could not get attributes on open file. Fall back to
1782 reading the directory. */
1783 if (!attributes_from_dir_w(path, &info, &reparse_tag))
1784 /* Very strange. This should not fail now */
1785 return -1;
1786 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1787 if (traverse) {
1788 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001789 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001790 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001791 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001792 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001793 } else {
1794 if (!GetFileInformationByHandle(hFile, &info)) {
1795 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001796 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001797 }
1798 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001799 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1800 return -1;
1801
1802 /* Close the outer open file handle now that we're about to
1803 reopen it with different flags. */
1804 if (!CloseHandle(hFile))
1805 return -1;
1806
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001807 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001808 /* In order to call GetFinalPathNameByHandle we need to open
1809 the file without the reparse handling flag set. */
1810 hFile2 = CreateFileW(
1811 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1812 NULL, OPEN_EXISTING,
1813 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1814 NULL);
1815 if (hFile2 == INVALID_HANDLE_VALUE)
1816 return -1;
1817
1818 if (!get_target_path(hFile2, &target_path))
1819 return -1;
1820
1821 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001822 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001823 return code;
1824 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001825 } else
1826 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001827 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001828 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001829
1830 /* Set S_IEXEC if it is an .exe, .bat, ... */
1831 dot = wcsrchr(path, '.');
1832 if (dot) {
1833 if (_wcsicmp(dot, L".bat") == 0 || _wcsicmp(dot, L".cmd") == 0 ||
1834 _wcsicmp(dot, L".exe") == 0 || _wcsicmp(dot, L".com") == 0)
1835 result->st_mode |= 0111;
1836 }
1837 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001838}
1839
1840static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001841win32_xstat(const char *path, struct win32_stat *result, BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001842{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001843 /* Protocol violation: we explicitly clear errno, instead of
1844 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001845 int code = win32_xstat_impl(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001846 errno = 0;
1847 return code;
1848}
Brian Curtinf5e76d02010-11-24 13:14:05 +00001849
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001850static int
1851win32_xstat_w(const wchar_t *path, struct win32_stat *result, BOOL traverse)
1852{
1853 /* Protocol violation: we explicitly clear errno, instead of
1854 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001855 int code = win32_xstat_impl_w(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001856 errno = 0;
1857 return code;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001858}
Brian Curtind25aef52011-06-13 15:16:04 -05001859/* About the following functions: win32_lstat_w, win32_stat, win32_stat_w
Brian Curtind40e6f72010-07-08 21:39:08 +00001860
1861 In Posix, stat automatically traverses symlinks and returns the stat
1862 structure for the target. In Windows, the equivalent GetFileAttributes by
1863 default does not traverse symlinks and instead returns attributes for
1864 the symlink.
1865
1866 Therefore, win32_lstat will get the attributes traditionally, and
1867 win32_stat will first explicitly resolve the symlink target and then will
1868 call win32_lstat on that result.
1869
Ezio Melotti4969f702011-03-15 05:59:46 +02001870 The _w represent Unicode equivalents of the aforementioned ANSI functions. */
Brian Curtind40e6f72010-07-08 21:39:08 +00001871
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001872static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001873win32_lstat(const char* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001874{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001875 return win32_xstat(path, result, FALSE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001876}
1877
Victor Stinner8c62be82010-05-06 00:08:46 +00001878static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001879win32_lstat_w(const wchar_t* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001880{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001881 return win32_xstat_w(path, result, FALSE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001882}
1883
1884static int
1885win32_stat(const char* path, struct win32_stat *result)
1886{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001887 return win32_xstat(path, result, TRUE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001888}
1889
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001890static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001891win32_stat_w(const wchar_t* path, struct win32_stat *result)
1892{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001893 return win32_xstat_w(path, result, TRUE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001894}
1895
1896static int
1897win32_fstat(int file_number, struct win32_stat *result)
1898{
Victor Stinner8c62be82010-05-06 00:08:46 +00001899 BY_HANDLE_FILE_INFORMATION info;
1900 HANDLE h;
1901 int type;
Martin v. Löwis14694662006-02-03 12:54:16 +00001902
Richard Oudkerk2240ac12012-07-06 12:05:32 +01001903 if (!_PyVerify_fd(file_number))
1904 h = INVALID_HANDLE_VALUE;
1905 else
1906 h = (HANDLE)_get_osfhandle(file_number);
Martin v. Löwis14694662006-02-03 12:54:16 +00001907
Victor Stinner8c62be82010-05-06 00:08:46 +00001908 /* Protocol violation: we explicitly clear errno, instead of
1909 setting it to a POSIX error. Callers should use GetLastError. */
1910 errno = 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001911
Victor Stinner8c62be82010-05-06 00:08:46 +00001912 if (h == INVALID_HANDLE_VALUE) {
1913 /* This is really a C library error (invalid file handle).
1914 We set the Win32 error to the closes one matching. */
1915 SetLastError(ERROR_INVALID_HANDLE);
1916 return -1;
1917 }
1918 memset(result, 0, sizeof(*result));
Martin v. Löwis14694662006-02-03 12:54:16 +00001919
Victor Stinner8c62be82010-05-06 00:08:46 +00001920 type = GetFileType(h);
1921 if (type == FILE_TYPE_UNKNOWN) {
1922 DWORD error = GetLastError();
1923 if (error != 0) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001924 return -1;
Victor Stinner8c62be82010-05-06 00:08:46 +00001925 }
1926 /* else: valid but unknown file */
1927 }
Martin v. Löwis14694662006-02-03 12:54:16 +00001928
Victor Stinner8c62be82010-05-06 00:08:46 +00001929 if (type != FILE_TYPE_DISK) {
1930 if (type == FILE_TYPE_CHAR)
1931 result->st_mode = _S_IFCHR;
1932 else if (type == FILE_TYPE_PIPE)
1933 result->st_mode = _S_IFIFO;
1934 return 0;
1935 }
1936
1937 if (!GetFileInformationByHandle(h, &info)) {
1938 return -1;
1939 }
1940
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001941 attribute_data_to_stat(&info, 0, result);
Victor Stinner8c62be82010-05-06 00:08:46 +00001942 /* specific to fstat() */
Victor Stinner8c62be82010-05-06 00:08:46 +00001943 result->st_ino = (((__int64)info.nFileIndexHigh)<<32) + info.nFileIndexLow;
1944 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001945}
1946
1947#endif /* MS_WINDOWS */
1948
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001949PyDoc_STRVAR(stat_result__doc__,
Larry Hastings9cf065c2012-06-22 16:30:09 -07001950"stat_result: Result from stat, fstat, or lstat.\n\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001951This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001952 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001953or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
1954\n\
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001955Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
1956or st_flags, they are available as attributes only.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001957\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001958See os.stat for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001959
1960static PyStructSequence_Field stat_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001961 {"st_mode", "protection bits"},
1962 {"st_ino", "inode"},
1963 {"st_dev", "device"},
1964 {"st_nlink", "number of hard links"},
1965 {"st_uid", "user ID of owner"},
1966 {"st_gid", "group ID of owner"},
1967 {"st_size", "total size, in bytes"},
1968 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
1969 {NULL, "integer time of last access"},
1970 {NULL, "integer time of last modification"},
1971 {NULL, "integer time of last change"},
1972 {"st_atime", "time of last access"},
1973 {"st_mtime", "time of last modification"},
1974 {"st_ctime", "time of last change"},
Larry Hastings6fe20b32012-04-19 15:07:49 -07001975 {"st_atime_ns", "time of last access in nanoseconds"},
1976 {"st_mtime_ns", "time of last modification in nanoseconds"},
1977 {"st_ctime_ns", "time of last change in nanoseconds"},
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001978#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00001979 {"st_blksize", "blocksize for filesystem I/O"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001980#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001981#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00001982 {"st_blocks", "number of blocks allocated"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001983#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001984#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00001985 {"st_rdev", "device type (if inode device)"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001986#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001987#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00001988 {"st_flags", "user defined flags for file"},
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001989#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001990#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00001991 {"st_gen", "generation number"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001992#endif
1993#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00001994 {"st_birthtime", "time of creation"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001995#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05001996#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1997 {"st_file_attributes", "Windows file attribute bits"},
1998#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001999 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002000};
2001
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002002#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Larry Hastings6fe20b32012-04-19 15:07:49 -07002003#define ST_BLKSIZE_IDX 16
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002004#else
Larry Hastings6fe20b32012-04-19 15:07:49 -07002005#define ST_BLKSIZE_IDX 15
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002006#endif
2007
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002008#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002009#define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
2010#else
2011#define ST_BLOCKS_IDX ST_BLKSIZE_IDX
2012#endif
2013
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002014#ifdef HAVE_STRUCT_STAT_ST_RDEV
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002015#define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
2016#else
2017#define ST_RDEV_IDX ST_BLOCKS_IDX
2018#endif
2019
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002020#ifdef HAVE_STRUCT_STAT_ST_FLAGS
2021#define ST_FLAGS_IDX (ST_RDEV_IDX+1)
2022#else
2023#define ST_FLAGS_IDX ST_RDEV_IDX
2024#endif
2025
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002026#ifdef HAVE_STRUCT_STAT_ST_GEN
Martin v. Löwisf09582e2005-08-14 21:42:34 +00002027#define ST_GEN_IDX (ST_FLAGS_IDX+1)
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002028#else
Martin v. Löwisf09582e2005-08-14 21:42:34 +00002029#define ST_GEN_IDX ST_FLAGS_IDX
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002030#endif
2031
2032#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
2033#define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
2034#else
2035#define ST_BIRTHTIME_IDX ST_GEN_IDX
2036#endif
2037
Zachary Ware63f277b2014-06-19 09:46:37 -05002038#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2039#define ST_FILE_ATTRIBUTES_IDX (ST_BIRTHTIME_IDX+1)
2040#else
2041#define ST_FILE_ATTRIBUTES_IDX ST_BIRTHTIME_IDX
2042#endif
2043
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002044static PyStructSequence_Desc stat_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002045 "stat_result", /* name */
2046 stat_result__doc__, /* doc */
2047 stat_result_fields,
2048 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002049};
2050
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002051PyDoc_STRVAR(statvfs_result__doc__,
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002052"statvfs_result: Result from statvfs or fstatvfs.\n\n\
2053This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00002054 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
Guido van Rossuma4dc73e2001-10-18 20:53:15 +00002055or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002056\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002057See os.statvfs for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002058
2059static PyStructSequence_Field statvfs_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002060 {"f_bsize", },
2061 {"f_frsize", },
2062 {"f_blocks", },
2063 {"f_bfree", },
2064 {"f_bavail", },
2065 {"f_files", },
2066 {"f_ffree", },
2067 {"f_favail", },
2068 {"f_flag", },
2069 {"f_namemax",},
2070 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002071};
2072
2073static PyStructSequence_Desc statvfs_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002074 "statvfs_result", /* name */
2075 statvfs_result__doc__, /* doc */
2076 statvfs_result_fields,
2077 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002078};
2079
Ross Lagerwall7807c352011-03-17 20:20:30 +02002080#if defined(HAVE_WAITID) && !defined(__APPLE__)
2081PyDoc_STRVAR(waitid_result__doc__,
2082"waitid_result: Result from waitid.\n\n\
2083This object may be accessed either as a tuple of\n\
2084 (si_pid, si_uid, si_signo, si_status, si_code),\n\
2085or via the attributes si_pid, si_uid, and so on.\n\
2086\n\
2087See os.waitid for more information.");
2088
2089static PyStructSequence_Field waitid_result_fields[] = {
2090 {"si_pid", },
2091 {"si_uid", },
2092 {"si_signo", },
2093 {"si_status", },
2094 {"si_code", },
2095 {0}
2096};
2097
2098static PyStructSequence_Desc waitid_result_desc = {
2099 "waitid_result", /* name */
2100 waitid_result__doc__, /* doc */
2101 waitid_result_fields,
2102 5
2103};
2104static PyTypeObject WaitidResultType;
2105#endif
2106
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00002107static int initialized;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002108static PyTypeObject StatResultType;
2109static PyTypeObject StatVFSResultType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002110#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05002111static PyTypeObject SchedParamType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002112#endif
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002113static newfunc structseq_new;
2114
2115static PyObject *
2116statresult_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2117{
Victor Stinner8c62be82010-05-06 00:08:46 +00002118 PyStructSequence *result;
2119 int i;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002120
Victor Stinner8c62be82010-05-06 00:08:46 +00002121 result = (PyStructSequence*)structseq_new(type, args, kwds);
2122 if (!result)
2123 return NULL;
2124 /* If we have been initialized from a tuple,
2125 st_?time might be set to None. Initialize it
2126 from the int slots. */
2127 for (i = 7; i <= 9; i++) {
2128 if (result->ob_item[i+3] == Py_None) {
2129 Py_DECREF(Py_None);
2130 Py_INCREF(result->ob_item[i]);
2131 result->ob_item[i+3] = result->ob_item[i];
2132 }
2133 }
2134 return (PyObject*)result;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002135}
2136
2137
2138
2139/* If true, st_?time is float. */
Martin v. Löwisfe33d0b2005-01-16 08:57:39 +00002140static int _stat_float_times = 1;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002141
2142PyDoc_STRVAR(stat_float_times__doc__,
2143"stat_float_times([newval]) -> oldval\n\n\
2144Determine whether os.[lf]stat represents time stamps as float objects.\n\
Larry Hastings2f936352014-08-05 14:04:04 +10002145\n\
2146If value is True, future calls to stat() return floats; if it is False,\n\
2147future calls return ints.\n\
2148If value is omitted, return the current setting.\n");
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002149
Larry Hastings2f936352014-08-05 14:04:04 +10002150/* AC 3.5: the public default value should be None, not ready for that yet */
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002151static PyObject*
2152stat_float_times(PyObject* self, PyObject *args)
2153{
Victor Stinner8c62be82010-05-06 00:08:46 +00002154 int newval = -1;
2155 if (!PyArg_ParseTuple(args, "|i:stat_float_times", &newval))
2156 return NULL;
Victor Stinner034d0aa2012-06-05 01:22:15 +02002157 if (PyErr_WarnEx(PyExc_DeprecationWarning,
2158 "stat_float_times() is deprecated",
2159 1))
2160 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00002161 if (newval == -1)
2162 /* Return old value */
2163 return PyBool_FromLong(_stat_float_times);
2164 _stat_float_times = newval;
2165 Py_INCREF(Py_None);
2166 return Py_None;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002167}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002168
Larry Hastings6fe20b32012-04-19 15:07:49 -07002169static PyObject *billion = NULL;
2170
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002171static void
Victor Stinner4195b5c2012-02-08 23:03:19 +01002172fill_time(PyObject *v, int index, time_t sec, unsigned long nsec)
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002173{
Larry Hastings6fe20b32012-04-19 15:07:49 -07002174 PyObject *s = _PyLong_FromTime_t(sec);
2175 PyObject *ns_fractional = PyLong_FromUnsignedLong(nsec);
2176 PyObject *s_in_ns = NULL;
2177 PyObject *ns_total = NULL;
2178 PyObject *float_s = NULL;
2179
2180 if (!(s && ns_fractional))
2181 goto exit;
2182
2183 s_in_ns = PyNumber_Multiply(s, billion);
2184 if (!s_in_ns)
2185 goto exit;
2186
2187 ns_total = PyNumber_Add(s_in_ns, ns_fractional);
2188 if (!ns_total)
2189 goto exit;
2190
Victor Stinner4195b5c2012-02-08 23:03:19 +01002191 if (_stat_float_times) {
Larry Hastings6fe20b32012-04-19 15:07:49 -07002192 float_s = PyFloat_FromDouble(sec + 1e-9*nsec);
2193 if (!float_s)
2194 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00002195 }
Larry Hastings6fe20b32012-04-19 15:07:49 -07002196 else {
2197 float_s = s;
2198 Py_INCREF(float_s);
2199 }
2200
2201 PyStructSequence_SET_ITEM(v, index, s);
2202 PyStructSequence_SET_ITEM(v, index+3, float_s);
2203 PyStructSequence_SET_ITEM(v, index+6, ns_total);
2204 s = NULL;
2205 float_s = NULL;
2206 ns_total = NULL;
2207exit:
2208 Py_XDECREF(s);
2209 Py_XDECREF(ns_fractional);
2210 Py_XDECREF(s_in_ns);
2211 Py_XDECREF(ns_total);
2212 Py_XDECREF(float_s);
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002213}
2214
Tim Peters5aa91602002-01-30 05:46:57 +00002215/* pack a system stat C structure into the Python stat tuple
Fred Drake699f3522000-06-29 21:12:41 +00002216 (used by posix_stat() and posix_fstat()) */
2217static PyObject*
Victor Stinner4195b5c2012-02-08 23:03:19 +01002218_pystat_fromstructstat(STRUCT_STAT *st)
Fred Drake699f3522000-06-29 21:12:41 +00002219{
Victor Stinner8c62be82010-05-06 00:08:46 +00002220 unsigned long ansec, mnsec, cnsec;
2221 PyObject *v = PyStructSequence_New(&StatResultType);
2222 if (v == NULL)
2223 return NULL;
Fred Drake699f3522000-06-29 21:12:41 +00002224
Victor Stinner8c62be82010-05-06 00:08:46 +00002225 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long)st->st_mode));
Fred Drake699f3522000-06-29 21:12:41 +00002226#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002227 PyStructSequence_SET_ITEM(v, 1,
2228 PyLong_FromLongLong((PY_LONG_LONG)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002229#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002230 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002231#endif
Serhiy Storchaka404fa922013-01-02 18:22:23 +02002232#ifdef MS_WINDOWS
2233 PyStructSequence_SET_ITEM(v, 2, PyLong_FromUnsignedLong(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002234#else
Serhiy Storchakab2653b32015-01-18 11:12:11 +02002235 PyStructSequence_SET_ITEM(v, 2, _PyLong_FromDev(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002236#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002237 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long)st->st_nlink));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02002238#if defined(MS_WINDOWS)
2239 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong(0));
2240 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong(0));
2241#else
2242 PyStructSequence_SET_ITEM(v, 4, _PyLong_FromUid(st->st_uid));
2243 PyStructSequence_SET_ITEM(v, 5, _PyLong_FromGid(st->st_gid));
2244#endif
Fred Drake699f3522000-06-29 21:12:41 +00002245#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002246 PyStructSequence_SET_ITEM(v, 6,
2247 PyLong_FromLongLong((PY_LONG_LONG)st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002248#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002249 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong(st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002250#endif
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002251
Martin v. Löwis14694662006-02-03 12:54:16 +00002252#if defined(HAVE_STAT_TV_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002253 ansec = st->st_atim.tv_nsec;
2254 mnsec = st->st_mtim.tv_nsec;
2255 cnsec = st->st_ctim.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002256#elif defined(HAVE_STAT_TV_NSEC2)
Victor Stinner8c62be82010-05-06 00:08:46 +00002257 ansec = st->st_atimespec.tv_nsec;
2258 mnsec = st->st_mtimespec.tv_nsec;
2259 cnsec = st->st_ctimespec.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002260#elif defined(HAVE_STAT_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002261 ansec = st->st_atime_nsec;
2262 mnsec = st->st_mtime_nsec;
2263 cnsec = st->st_ctime_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002264#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002265 ansec = mnsec = cnsec = 0;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002266#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002267 fill_time(v, 7, st->st_atime, ansec);
2268 fill_time(v, 8, st->st_mtime, mnsec);
2269 fill_time(v, 9, st->st_ctime, cnsec);
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002270
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002271#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00002272 PyStructSequence_SET_ITEM(v, ST_BLKSIZE_IDX,
2273 PyLong_FromLong((long)st->st_blksize));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002274#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002275#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00002276 PyStructSequence_SET_ITEM(v, ST_BLOCKS_IDX,
2277 PyLong_FromLong((long)st->st_blocks));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002278#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002279#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00002280 PyStructSequence_SET_ITEM(v, ST_RDEV_IDX,
2281 PyLong_FromLong((long)st->st_rdev));
Fred Drake699f3522000-06-29 21:12:41 +00002282#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002283#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00002284 PyStructSequence_SET_ITEM(v, ST_GEN_IDX,
2285 PyLong_FromLong((long)st->st_gen));
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002286#endif
2287#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00002288 {
Victor Stinner4195b5c2012-02-08 23:03:19 +01002289 PyObject *val;
2290 unsigned long bsec,bnsec;
2291 bsec = (long)st->st_birthtime;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002292#ifdef HAVE_STAT_TV_NSEC2
Victor Stinner4195b5c2012-02-08 23:03:19 +01002293 bnsec = st->st_birthtimespec.tv_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002294#else
Victor Stinner4195b5c2012-02-08 23:03:19 +01002295 bnsec = 0;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002296#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002297 if (_stat_float_times) {
2298 val = PyFloat_FromDouble(bsec + 1e-9*bnsec);
2299 } else {
2300 val = PyLong_FromLong((long)bsec);
2301 }
2302 PyStructSequence_SET_ITEM(v, ST_BIRTHTIME_IDX,
2303 val);
Victor Stinner8c62be82010-05-06 00:08:46 +00002304 }
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002305#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002306#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00002307 PyStructSequence_SET_ITEM(v, ST_FLAGS_IDX,
2308 PyLong_FromLong((long)st->st_flags));
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002309#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05002310#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2311 PyStructSequence_SET_ITEM(v, ST_FILE_ATTRIBUTES_IDX,
2312 PyLong_FromUnsignedLong(st->st_file_attributes));
2313#endif
Fred Drake699f3522000-06-29 21:12:41 +00002314
Victor Stinner8c62be82010-05-06 00:08:46 +00002315 if (PyErr_Occurred()) {
2316 Py_DECREF(v);
2317 return NULL;
2318 }
Fred Drake699f3522000-06-29 21:12:41 +00002319
Victor Stinner8c62be82010-05-06 00:08:46 +00002320 return v;
Fred Drake699f3522000-06-29 21:12:41 +00002321}
2322
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002323/* POSIX methods */
2324
Guido van Rossum94f6f721999-01-06 18:42:14 +00002325
2326static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07002327posix_do_stat(char *function_name, path_t *path,
2328 int dir_fd, int follow_symlinks)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002329{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002330 STRUCT_STAT st;
2331 int result;
2332
2333#if !defined(MS_WINDOWS) && !defined(HAVE_FSTATAT) && !defined(HAVE_LSTAT)
2334 if (follow_symlinks_specified(function_name, follow_symlinks))
2335 return NULL;
2336#endif
2337
2338 if (path_and_dir_fd_invalid("stat", path, dir_fd) ||
2339 dir_fd_and_fd_invalid("stat", dir_fd, path->fd) ||
2340 fd_and_follow_symlinks_invalid("stat", path->fd, follow_symlinks))
2341 return NULL;
2342
2343 Py_BEGIN_ALLOW_THREADS
2344 if (path->fd != -1)
2345 result = FSTAT(path->fd, &st);
2346 else
2347#ifdef MS_WINDOWS
2348 if (path->wide) {
2349 if (follow_symlinks)
2350 result = win32_stat_w(path->wide, &st);
2351 else
2352 result = win32_lstat_w(path->wide, &st);
2353 }
2354 else
2355#endif
2356#if defined(HAVE_LSTAT) || defined(MS_WINDOWS)
2357 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
2358 result = LSTAT(path->narrow, &st);
2359 else
2360#endif
2361#ifdef HAVE_FSTATAT
2362 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks)
2363 result = fstatat(dir_fd, path->narrow, &st,
2364 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2365 else
2366#endif
2367 result = STAT(path->narrow, &st);
2368 Py_END_ALLOW_THREADS
2369
Victor Stinner292c8352012-10-30 02:17:38 +01002370 if (result != 0) {
2371 return path_error(path);
2372 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07002373
2374 return _pystat_fromstructstat(&st);
2375}
2376
Larry Hastings2f936352014-08-05 14:04:04 +10002377/*[python input]
2378
2379for s in """
2380
2381FACCESSAT
2382FCHMODAT
2383FCHOWNAT
2384FSTATAT
2385LINKAT
2386MKDIRAT
2387MKFIFOAT
2388MKNODAT
2389OPENAT
2390READLINKAT
2391SYMLINKAT
2392UNLINKAT
2393
2394""".strip().split():
2395 s = s.strip()
2396 print("""
2397#ifdef HAVE_{s}
2398 #define {s}_DIR_FD_CONVERTER dir_fd_converter
Larry Hastings31826802013-10-19 00:09:25 -07002399#else
Larry Hastings2f936352014-08-05 14:04:04 +10002400 #define {s}_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings31826802013-10-19 00:09:25 -07002401#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002402""".rstrip().format(s=s))
2403
2404for s in """
2405
2406FCHDIR
2407FCHMOD
2408FCHOWN
2409FDOPENDIR
2410FEXECVE
2411FPATHCONF
2412FSTATVFS
2413FTRUNCATE
2414
2415""".strip().split():
2416 s = s.strip()
2417 print("""
2418#ifdef HAVE_{s}
2419 #define PATH_HAVE_{s} 1
2420#else
2421 #define PATH_HAVE_{s} 0
2422#endif
2423
2424""".rstrip().format(s=s))
2425[python start generated code]*/
2426
2427#ifdef HAVE_FACCESSAT
2428 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_converter
2429#else
2430 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_unavailable
2431#endif
2432
2433#ifdef HAVE_FCHMODAT
2434 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_converter
2435#else
2436 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_unavailable
2437#endif
2438
2439#ifdef HAVE_FCHOWNAT
2440 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_converter
2441#else
2442 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_unavailable
2443#endif
2444
2445#ifdef HAVE_FSTATAT
2446 #define FSTATAT_DIR_FD_CONVERTER dir_fd_converter
2447#else
2448 #define FSTATAT_DIR_FD_CONVERTER dir_fd_unavailable
2449#endif
2450
2451#ifdef HAVE_LINKAT
2452 #define LINKAT_DIR_FD_CONVERTER dir_fd_converter
2453#else
2454 #define LINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2455#endif
2456
2457#ifdef HAVE_MKDIRAT
2458 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_converter
2459#else
2460 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_unavailable
2461#endif
2462
2463#ifdef HAVE_MKFIFOAT
2464 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_converter
2465#else
2466 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_unavailable
2467#endif
2468
2469#ifdef HAVE_MKNODAT
2470 #define MKNODAT_DIR_FD_CONVERTER dir_fd_converter
2471#else
2472 #define MKNODAT_DIR_FD_CONVERTER dir_fd_unavailable
2473#endif
2474
2475#ifdef HAVE_OPENAT
2476 #define OPENAT_DIR_FD_CONVERTER dir_fd_converter
2477#else
2478 #define OPENAT_DIR_FD_CONVERTER dir_fd_unavailable
2479#endif
2480
2481#ifdef HAVE_READLINKAT
2482 #define READLINKAT_DIR_FD_CONVERTER dir_fd_converter
2483#else
2484 #define READLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2485#endif
2486
2487#ifdef HAVE_SYMLINKAT
2488 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_converter
2489#else
2490 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2491#endif
2492
2493#ifdef HAVE_UNLINKAT
2494 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_converter
2495#else
2496 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2497#endif
2498
2499#ifdef HAVE_FCHDIR
2500 #define PATH_HAVE_FCHDIR 1
2501#else
2502 #define PATH_HAVE_FCHDIR 0
2503#endif
2504
2505#ifdef HAVE_FCHMOD
2506 #define PATH_HAVE_FCHMOD 1
2507#else
2508 #define PATH_HAVE_FCHMOD 0
2509#endif
2510
2511#ifdef HAVE_FCHOWN
2512 #define PATH_HAVE_FCHOWN 1
2513#else
2514 #define PATH_HAVE_FCHOWN 0
2515#endif
2516
2517#ifdef HAVE_FDOPENDIR
2518 #define PATH_HAVE_FDOPENDIR 1
2519#else
2520 #define PATH_HAVE_FDOPENDIR 0
2521#endif
2522
2523#ifdef HAVE_FEXECVE
2524 #define PATH_HAVE_FEXECVE 1
2525#else
2526 #define PATH_HAVE_FEXECVE 0
2527#endif
2528
2529#ifdef HAVE_FPATHCONF
2530 #define PATH_HAVE_FPATHCONF 1
2531#else
2532 #define PATH_HAVE_FPATHCONF 0
2533#endif
2534
2535#ifdef HAVE_FSTATVFS
2536 #define PATH_HAVE_FSTATVFS 1
2537#else
2538 #define PATH_HAVE_FSTATVFS 0
2539#endif
2540
2541#ifdef HAVE_FTRUNCATE
2542 #define PATH_HAVE_FTRUNCATE 1
2543#else
2544 #define PATH_HAVE_FTRUNCATE 0
2545#endif
2546/*[python end generated code: output=4bd4f6f7d41267f1 input=80b4c890b6774ea5]*/
Larry Hastings31826802013-10-19 00:09:25 -07002547
2548
Larry Hastings61272b72014-01-07 12:41:53 -08002549/*[python input]
Larry Hastings31826802013-10-19 00:09:25 -07002550
2551class path_t_converter(CConverter):
2552
2553 type = "path_t"
2554 impl_by_reference = True
2555 parse_by_reference = True
2556
2557 converter = 'path_converter'
2558
2559 def converter_init(self, *, allow_fd=False, nullable=False):
Larry Hastings31826802013-10-19 00:09:25 -07002560 # right now path_t doesn't support default values.
2561 # to support a default value, you'll need to override initialize().
Larry Hastings2f936352014-08-05 14:04:04 +10002562 if self.default not in (unspecified, None):
Larry Hastings7726ac92014-01-31 22:03:12 -08002563 fail("Can't specify a default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002564
Larry Hastings2f936352014-08-05 14:04:04 +10002565 if self.c_default not in (None, 'Py_None'):
2566 raise RuntimeError("Can't specify a c_default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002567
2568 self.nullable = nullable
2569 self.allow_fd = allow_fd
2570
Larry Hastings7726ac92014-01-31 22:03:12 -08002571 def pre_render(self):
2572 def strify(value):
Larry Hastings2f936352014-08-05 14:04:04 +10002573 if isinstance(value, str):
2574 return value
Larry Hastings7726ac92014-01-31 22:03:12 -08002575 return str(int(bool(value)))
2576
2577 # add self.py_name here when merging with posixmodule conversion
Larry Hastings2f936352014-08-05 14:04:04 +10002578 self.c_default = 'PATH_T_INITIALIZE("{}", "{}", {}, {})'.format(
Larry Hastings31826802013-10-19 00:09:25 -07002579 self.function.name,
Larry Hastings2f936352014-08-05 14:04:04 +10002580 self.name,
Larry Hastings7726ac92014-01-31 22:03:12 -08002581 strify(self.nullable),
2582 strify(self.allow_fd),
Larry Hastings31826802013-10-19 00:09:25 -07002583 )
2584
2585 def cleanup(self):
2586 return "path_cleanup(&" + self.name + ");\n"
2587
2588
2589class dir_fd_converter(CConverter):
2590 type = 'int'
Larry Hastings31826802013-10-19 00:09:25 -07002591
Larry Hastings2f936352014-08-05 14:04:04 +10002592 def converter_init(self, requires=None):
Larry Hastings31826802013-10-19 00:09:25 -07002593 if self.default in (unspecified, None):
2594 self.c_default = 'DEFAULT_DIR_FD'
Larry Hastings2f936352014-08-05 14:04:04 +10002595 if isinstance(requires, str):
2596 self.converter = requires.upper() + '_DIR_FD_CONVERTER'
2597 else:
2598 self.converter = 'dir_fd_converter'
Larry Hastings31826802013-10-19 00:09:25 -07002599
Larry Hastings2f936352014-08-05 14:04:04 +10002600class fildes_converter(CConverter):
2601 type = 'int'
2602 converter = 'fildes_converter'
2603
2604class uid_t_converter(CConverter):
2605 type = "uid_t"
2606 converter = '_Py_Uid_Converter'
2607
2608class gid_t_converter(CConverter):
2609 type = "gid_t"
2610 converter = '_Py_Gid_Converter'
2611
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002612class dev_t_converter(CConverter):
2613 type = 'dev_t'
2614 converter = '_Py_Dev_Converter'
2615
2616class dev_t_return_converter(unsigned_long_return_converter):
2617 type = 'dev_t'
2618 conversion_fn = '_PyLong_FromDev'
2619 unsigned_cast = '(dev_t)'
2620
Larry Hastings2f936352014-08-05 14:04:04 +10002621class FSConverter_converter(CConverter):
2622 type = 'PyObject *'
2623 converter = 'PyUnicode_FSConverter'
2624 def converter_init(self):
2625 if self.default is not unspecified:
2626 fail("FSConverter_converter does not support default values")
2627 self.c_default = 'NULL'
2628
2629 def cleanup(self):
2630 return "Py_XDECREF(" + self.name + ");\n"
2631
2632class pid_t_converter(CConverter):
2633 type = 'pid_t'
2634 format_unit = '" _Py_PARSE_PID "'
2635
2636class idtype_t_converter(int_converter):
2637 type = 'idtype_t'
2638
2639class id_t_converter(CConverter):
2640 type = 'id_t'
2641 format_unit = '" _Py_PARSE_PID "'
2642
2643class Py_intptr_t_converter(CConverter):
2644 type = 'Py_intptr_t'
2645 format_unit = '" _Py_PARSE_INTPTR "'
2646
2647class Py_off_t_converter(CConverter):
2648 type = 'Py_off_t'
2649 converter = 'Py_off_t_converter'
2650
2651class Py_off_t_return_converter(long_return_converter):
2652 type = 'Py_off_t'
2653 conversion_fn = 'PyLong_FromPy_off_t'
2654
2655class path_confname_converter(CConverter):
2656 type="int"
2657 converter="conv_path_confname"
2658
2659class confstr_confname_converter(path_confname_converter):
2660 converter='conv_confstr_confname'
2661
2662class sysconf_confname_converter(path_confname_converter):
2663 converter="conv_sysconf_confname"
2664
2665class sched_param_converter(CConverter):
2666 type = 'struct sched_param'
2667 converter = 'convert_sched_param'
2668 impl_by_reference = True;
Larry Hastings31826802013-10-19 00:09:25 -07002669
Larry Hastings61272b72014-01-07 12:41:53 -08002670[python start generated code]*/
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002671/*[python end generated code: output=da39a3ee5e6b4b0d input=affe68316f160401]*/
Larry Hastings31826802013-10-19 00:09:25 -07002672
Larry Hastings61272b72014-01-07 12:41:53 -08002673/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002674
Larry Hastings2a727912014-01-16 11:32:01 -08002675os.stat
Larry Hastings31826802013-10-19 00:09:25 -07002676
2677 path : path_t(allow_fd=True)
2678 Path to be examined; can be string, bytes, or open-file-descriptor int.
2679
2680 *
2681
Larry Hastings2f936352014-08-05 14:04:04 +10002682 dir_fd : dir_fd(requires='fstatat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002683 If not None, it should be a file descriptor open to a directory,
2684 and path should be a relative string; path will then be relative to
2685 that directory.
2686
2687 follow_symlinks: bool = True
2688 If False, and the last element of the path is a symbolic link,
2689 stat will examine the symbolic link itself instead of the file
2690 the link points to.
2691
2692Perform a stat system call on the given path.
2693
2694dir_fd and follow_symlinks may not be implemented
2695 on your platform. If they are unavailable, using them will raise a
2696 NotImplementedError.
2697
2698It's an error to use dir_fd or follow_symlinks when specifying path as
2699 an open file descriptor.
2700
Larry Hastings61272b72014-01-07 12:41:53 -08002701[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002702
2703PyDoc_STRVAR(os_stat__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002704"stat($module, /, path, *, dir_fd=None, follow_symlinks=True)\n"
2705"--\n"
2706"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002707"Perform a stat system call on the given path.\n"
2708"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002709" path\n"
2710" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
2711" dir_fd\n"
2712" If not None, it should be a file descriptor open to a directory,\n"
2713" and path should be a relative string; path will then be relative to\n"
2714" that directory.\n"
2715" follow_symlinks\n"
2716" If False, and the last element of the path is a symbolic link,\n"
2717" stat will examine the symbolic link itself instead of the file\n"
2718" the link points to.\n"
2719"\n"
2720"dir_fd and follow_symlinks may not be implemented\n"
2721" on your platform. If they are unavailable, using them will raise a\n"
2722" NotImplementedError.\n"
2723"\n"
2724"It\'s an error to use dir_fd or follow_symlinks when specifying path as\n"
2725" an open file descriptor.");
2726
2727#define OS_STAT_METHODDEF \
2728 {"stat", (PyCFunction)os_stat, METH_VARARGS|METH_KEYWORDS, os_stat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002729
2730static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002731os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002732
2733static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002734os_stat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002735{
Larry Hastings31826802013-10-19 00:09:25 -07002736 PyObject *return_value = NULL;
2737 static char *_keywords[] = {"path", "dir_fd", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002738 path_t path = PATH_T_INITIALIZE("stat", "path", 0, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002739 int dir_fd = DEFAULT_DIR_FD;
2740 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002741
Larry Hastings31826802013-10-19 00:09:25 -07002742 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2743 "O&|$O&p:stat", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002744 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002745 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08002746 return_value = os_stat_impl(module, &path, dir_fd, follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002747
2748exit:
2749 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002750 path_cleanup(&path);
Larry Hastings31826802013-10-19 00:09:25 -07002751
Larry Hastings9cf065c2012-06-22 16:30:09 -07002752 return return_value;
2753}
2754
Larry Hastings31826802013-10-19 00:09:25 -07002755static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002756os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002757/*[clinic end generated code: output=0e9f9508fa0c0607 input=099d356c306fa24a]*/
Larry Hastings31826802013-10-19 00:09:25 -07002758{
2759 return posix_do_stat("stat", path, dir_fd, follow_symlinks);
2760}
2761
Larry Hastings2f936352014-08-05 14:04:04 +10002762
2763/*[clinic input]
2764os.lstat
2765
2766 path : path_t
2767
2768 *
2769
2770 dir_fd : dir_fd(requires='fstatat') = None
2771
2772Perform a stat system call on the given path, without following symbolic links.
2773
2774Like stat(), but do not follow symbolic links.
2775Equivalent to stat(path, follow_symlinks=False).
2776[clinic start generated code]*/
2777
2778PyDoc_STRVAR(os_lstat__doc__,
2779"lstat($module, /, path, *, dir_fd=None)\n"
2780"--\n"
2781"\n"
2782"Perform a stat system call on the given path, without following symbolic links.\n"
2783"\n"
2784"Like stat(), but do not follow symbolic links.\n"
2785"Equivalent to stat(path, follow_symlinks=False).");
2786
2787#define OS_LSTAT_METHODDEF \
2788 {"lstat", (PyCFunction)os_lstat, METH_VARARGS|METH_KEYWORDS, os_lstat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002789
2790static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10002791os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002792
Larry Hastings2f936352014-08-05 14:04:04 +10002793static PyObject *
2794os_lstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
2795{
2796 PyObject *return_value = NULL;
2797 static char *_keywords[] = {"path", "dir_fd", NULL};
2798 path_t path = PATH_T_INITIALIZE("lstat", "path", 0, 0);
2799 int dir_fd = DEFAULT_DIR_FD;
2800
2801 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2802 "O&|$O&:lstat", _keywords,
2803 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd))
2804 goto exit;
2805 return_value = os_lstat_impl(module, &path, dir_fd);
2806
2807exit:
2808 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002809 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10002810
Larry Hastings9cf065c2012-06-22 16:30:09 -07002811 return return_value;
2812}
2813
Larry Hastings2f936352014-08-05 14:04:04 +10002814static PyObject *
2815os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd)
2816/*[clinic end generated code: output=85702247224a2b1c input=0b7474765927b925]*/
2817{
2818 int follow_symlinks = 0;
2819 return posix_do_stat("lstat", path, dir_fd, follow_symlinks);
2820}
Larry Hastings31826802013-10-19 00:09:25 -07002821
Larry Hastings2f936352014-08-05 14:04:04 +10002822
Larry Hastings61272b72014-01-07 12:41:53 -08002823/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +10002824os.access -> bool
Larry Hastings31826802013-10-19 00:09:25 -07002825
2826 path: path_t(allow_fd=True)
2827 Path to be tested; can be string, bytes, or open-file-descriptor int.
2828
2829 mode: int
2830 Operating-system mode bitfield. Can be F_OK to test existence,
2831 or the inclusive-OR of R_OK, W_OK, and X_OK.
2832
2833 *
2834
Larry Hastings2f936352014-08-05 14:04:04 +10002835 dir_fd : dir_fd(requires='faccessat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002836 If not None, it should be a file descriptor open to a directory,
2837 and path should be relative; path will then be relative to that
2838 directory.
2839
2840 effective_ids: bool = False
2841 If True, access will use the effective uid/gid instead of
2842 the real uid/gid.
2843
2844 follow_symlinks: bool = True
2845 If False, and the last element of the path is a symbolic link,
2846 access will examine the symbolic link itself instead of the file
2847 the link points to.
2848
2849Use the real uid/gid to test for access to a path.
2850
2851{parameters}
2852dir_fd, effective_ids, and follow_symlinks may not be implemented
2853 on your platform. If they are unavailable, using them will raise a
2854 NotImplementedError.
2855
2856Note that most operations will use the effective uid/gid, therefore this
2857 routine can be used in a suid/sgid environment to test if the invoking user
2858 has the specified access to the path.
2859
Larry Hastings61272b72014-01-07 12:41:53 -08002860[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002861
2862PyDoc_STRVAR(os_access__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002863"access($module, /, path, mode, *, dir_fd=None, effective_ids=False,\n"
2864" follow_symlinks=True)\n"
2865"--\n"
2866"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002867"Use the real uid/gid to test for access to a path.\n"
2868"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002869" path\n"
2870" Path to be tested; can be string, bytes, or open-file-descriptor int.\n"
2871" mode\n"
2872" Operating-system mode bitfield. Can be F_OK to test existence,\n"
2873" or the inclusive-OR of R_OK, W_OK, and X_OK.\n"
2874" dir_fd\n"
2875" If not None, it should be a file descriptor open to a directory,\n"
2876" and path should be relative; path will then be relative to that\n"
2877" directory.\n"
2878" effective_ids\n"
2879" If True, access will use the effective uid/gid instead of\n"
2880" the real uid/gid.\n"
2881" follow_symlinks\n"
2882" If False, and the last element of the path is a symbolic link,\n"
2883" access will examine the symbolic link itself instead of the file\n"
2884" the link points to.\n"
2885"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002886"dir_fd, effective_ids, and follow_symlinks may not be implemented\n"
2887" on your platform. If they are unavailable, using them will raise a\n"
2888" NotImplementedError.\n"
2889"\n"
2890"Note that most operations will use the effective uid/gid, therefore this\n"
2891" routine can be used in a suid/sgid environment to test if the invoking user\n"
2892" has the specified access to the path.");
2893
2894#define OS_ACCESS_METHODDEF \
2895 {"access", (PyCFunction)os_access, METH_VARARGS|METH_KEYWORDS, os_access__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002896
Larry Hastings2f936352014-08-05 14:04:04 +10002897static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002898os_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 -07002899
2900static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002901os_access(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002902{
Larry Hastings31826802013-10-19 00:09:25 -07002903 PyObject *return_value = NULL;
2904 static char *_keywords[] = {"path", "mode", "dir_fd", "effective_ids", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002905 path_t path = PATH_T_INITIALIZE("access", "path", 0, 1);
Victor Stinner8c62be82010-05-06 00:08:46 +00002906 int mode;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002907 int dir_fd = DEFAULT_DIR_FD;
2908 int effective_ids = 0;
2909 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10002910 int _return_value;
Larry Hastings31826802013-10-19 00:09:25 -07002911
2912 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2913 "O&i|$O&pp:access", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002914 path_converter, &path, &mode, FACCESSAT_DIR_FD_CONVERTER, &dir_fd, &effective_ids, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002915 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +10002916 _return_value = os_access_impl(module, &path, mode, dir_fd, effective_ids, follow_symlinks);
2917 if ((_return_value == -1) && PyErr_Occurred())
2918 goto exit;
2919 return_value = PyBool_FromLong((long)_return_value);
Larry Hastings31826802013-10-19 00:09:25 -07002920
2921exit:
2922 /* Cleanup for path */
2923 path_cleanup(&path);
2924
2925 return return_value;
2926}
2927
Larry Hastings2f936352014-08-05 14:04:04 +10002928static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002929os_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 +10002930/*[clinic end generated code: output=dfd404666906f012 input=b75a756797af45ec]*/
Larry Hastings31826802013-10-19 00:09:25 -07002931{
Larry Hastings2f936352014-08-05 14:04:04 +10002932 int return_value;
Victor Stinner8c62be82010-05-06 00:08:46 +00002933
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002934#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002935 DWORD attr;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002936#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07002937 int result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002938#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07002939
Larry Hastings9cf065c2012-06-22 16:30:09 -07002940#ifndef HAVE_FACCESSAT
2941 if (follow_symlinks_specified("access", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002942 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002943
2944 if (effective_ids) {
2945 argument_unavailable_error("access", "effective_ids");
Larry Hastings2f936352014-08-05 14:04:04 +10002946 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002947 }
2948#endif
2949
2950#ifdef MS_WINDOWS
2951 Py_BEGIN_ALLOW_THREADS
Christian Heimesebe83f92013-10-19 22:36:17 +02002952 if (path->wide != NULL)
2953 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002954 else
Christian Heimesebe83f92013-10-19 22:36:17 +02002955 attr = GetFileAttributesA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002956 Py_END_ALLOW_THREADS
2957
2958 /*
Georg Brandlf7875592012-06-24 13:58:31 +02002959 * Access is possible if
Larry Hastings9cf065c2012-06-22 16:30:09 -07002960 * * we didn't get a -1, and
2961 * * write access wasn't requested,
2962 * * or the file isn't read-only,
2963 * * or it's a directory.
2964 * (Directories cannot be read-only on Windows.)
2965 */
Larry Hastings2f936352014-08-05 14:04:04 +10002966 return_value = (attr != INVALID_FILE_ATTRIBUTES) &&
Georg Brandl5bb7aa92012-06-23 12:48:40 +02002967 (!(mode & 2) ||
Larry Hastings9cf065c2012-06-22 16:30:09 -07002968 !(attr & FILE_ATTRIBUTE_READONLY) ||
Larry Hastings2f936352014-08-05 14:04:04 +10002969 (attr & FILE_ATTRIBUTE_DIRECTORY));
Larry Hastings9cf065c2012-06-22 16:30:09 -07002970#else
2971
2972 Py_BEGIN_ALLOW_THREADS
2973#ifdef HAVE_FACCESSAT
2974 if ((dir_fd != DEFAULT_DIR_FD) ||
2975 effective_ids ||
2976 !follow_symlinks) {
2977 int flags = 0;
2978 if (!follow_symlinks)
2979 flags |= AT_SYMLINK_NOFOLLOW;
2980 if (effective_ids)
2981 flags |= AT_EACCESS;
Larry Hastings31826802013-10-19 00:09:25 -07002982 result = faccessat(dir_fd, path->narrow, mode, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002983 }
2984 else
2985#endif
Larry Hastings31826802013-10-19 00:09:25 -07002986 result = access(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002987 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002988 return_value = !result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002989#endif
2990
Larry Hastings9cf065c2012-06-22 16:30:09 -07002991 return return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002992}
2993
Guido van Rossumd371ff11999-01-25 16:12:23 +00002994#ifndef F_OK
2995#define F_OK 0
2996#endif
2997#ifndef R_OK
2998#define R_OK 4
2999#endif
3000#ifndef W_OK
3001#define W_OK 2
3002#endif
3003#ifndef X_OK
3004#define X_OK 1
3005#endif
3006
Larry Hastings31826802013-10-19 00:09:25 -07003007
Guido van Rossumd371ff11999-01-25 16:12:23 +00003008#ifdef HAVE_TTYNAME
Larry Hastings61272b72014-01-07 12:41:53 -08003009/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07003010os.ttyname -> DecodeFSDefault
3011
3012 fd: int
3013 Integer file descriptor handle.
3014
3015 /
3016
3017Return the name of the terminal device connected to 'fd'.
Larry Hastings61272b72014-01-07 12:41:53 -08003018[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07003019
3020PyDoc_STRVAR(os_ttyname__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08003021"ttyname($module, fd, /)\n"
3022"--\n"
3023"\n"
Larry Hastings31826802013-10-19 00:09:25 -07003024"Return the name of the terminal device connected to \'fd\'.\n"
3025"\n"
Larry Hastings31826802013-10-19 00:09:25 -07003026" fd\n"
3027" Integer file descriptor handle.");
3028
3029#define OS_TTYNAME_METHODDEF \
3030 {"ttyname", (PyCFunction)os_ttyname, METH_VARARGS, os_ttyname__doc__},
3031
3032static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003033os_ttyname_impl(PyModuleDef *module, int fd);
Guido van Rossum94f6f721999-01-06 18:42:14 +00003034
3035static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003036os_ttyname(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +00003037{
Larry Hastings31826802013-10-19 00:09:25 -07003038 PyObject *return_value = NULL;
3039 int fd;
3040 char *_return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003041
Larry Hastings31826802013-10-19 00:09:25 -07003042 if (!PyArg_ParseTuple(args,
3043 "i:ttyname",
3044 &fd))
3045 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08003046 _return_value = os_ttyname_impl(module, fd);
Larry Hastings31826802013-10-19 00:09:25 -07003047 if (_return_value == NULL)
3048 goto exit;
3049 return_value = PyUnicode_DecodeFSDefault(_return_value);
3050
3051exit:
3052 return return_value;
3053}
3054
3055static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003056os_ttyname_impl(PyModuleDef *module, int fd)
Larry Hastings2623c8c2014-02-08 22:15:29 -08003057/*[clinic end generated code: output=cee7bc4cffec01a2 input=5f72ca83e76b3b45]*/
Larry Hastings31826802013-10-19 00:09:25 -07003058{
3059 char *ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003060
Larry Hastings31826802013-10-19 00:09:25 -07003061 ret = ttyname(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00003062 if (ret == NULL)
Larry Hastings31826802013-10-19 00:09:25 -07003063 posix_error();
3064 return ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003065}
Guido van Rossumd371ff11999-01-25 16:12:23 +00003066#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00003067
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003068#ifdef HAVE_CTERMID
Larry Hastings2f936352014-08-05 14:04:04 +10003069/*[clinic input]
3070os.ctermid
3071
3072Return the name of the controlling terminal for this process.
3073[clinic start generated code]*/
3074
3075PyDoc_STRVAR(os_ctermid__doc__,
3076"ctermid($module, /)\n"
3077"--\n"
3078"\n"
3079"Return the name of the controlling terminal for this process.");
3080
3081#define OS_CTERMID_METHODDEF \
3082 {"ctermid", (PyCFunction)os_ctermid, METH_NOARGS, os_ctermid__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003083
3084static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003085os_ctermid_impl(PyModuleDef *module);
3086
3087static PyObject *
3088os_ctermid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3089{
3090 return os_ctermid_impl(module);
3091}
3092
3093static PyObject *
3094os_ctermid_impl(PyModuleDef *module)
3095/*[clinic end generated code: output=277bf7964ec2d782 input=3b87fdd52556382d]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003096{
Victor Stinner8c62be82010-05-06 00:08:46 +00003097 char *ret;
3098 char buffer[L_ctermid];
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003099
Greg Wardb48bc172000-03-01 21:51:56 +00003100#ifdef USE_CTERMID_R
Victor Stinner8c62be82010-05-06 00:08:46 +00003101 ret = ctermid_r(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003102#else
Victor Stinner8c62be82010-05-06 00:08:46 +00003103 ret = ctermid(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003104#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00003105 if (ret == NULL)
3106 return posix_error();
Victor Stinner5fe6de82010-08-15 09:12:51 +00003107 return PyUnicode_DecodeFSDefault(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003108}
Larry Hastings2f936352014-08-05 14:04:04 +10003109#endif /* HAVE_CTERMID */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003110
Larry Hastings2f936352014-08-05 14:04:04 +10003111
3112/*[clinic input]
3113os.chdir
3114
3115 path: path_t(allow_fd='PATH_HAVE_FCHDIR')
3116
3117Change the current working directory to the specified path.
3118
3119path may always be specified as a string.
3120On some platforms, path may also be specified as an open file descriptor.
3121 If this functionality is unavailable, using it raises an exception.
3122[clinic start generated code]*/
3123
3124PyDoc_STRVAR(os_chdir__doc__,
3125"chdir($module, /, path)\n"
3126"--\n"
3127"\n"
3128"Change the current working directory to the specified path.\n"
3129"\n"
3130"path may always be specified as a string.\n"
3131"On some platforms, path may also be specified as an open file descriptor.\n"
3132" If this functionality is unavailable, using it raises an exception.");
3133
3134#define OS_CHDIR_METHODDEF \
3135 {"chdir", (PyCFunction)os_chdir, METH_VARARGS|METH_KEYWORDS, os_chdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003136
Barry Warsaw53699e91996-12-10 23:23:01 +00003137static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003138os_chdir_impl(PyModuleDef *module, path_t *path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003139
Larry Hastings2f936352014-08-05 14:04:04 +10003140static PyObject *
3141os_chdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3142{
3143 PyObject *return_value = NULL;
3144 static char *_keywords[] = {"path", NULL};
3145 path_t path = PATH_T_INITIALIZE("chdir", "path", 0, PATH_HAVE_FCHDIR);
3146
3147 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3148 "O&:chdir", _keywords,
3149 path_converter, &path))
3150 goto exit;
3151 return_value = os_chdir_impl(module, &path);
3152
3153exit:
3154 /* Cleanup for path */
3155 path_cleanup(&path);
3156
3157 return return_value;
3158}
3159
3160static PyObject *
3161os_chdir_impl(PyModuleDef *module, path_t *path)
3162/*[clinic end generated code: output=cc07592dd23ca9e0 input=1a4a15b4d12cb15d]*/
3163{
3164 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003165
3166 Py_BEGIN_ALLOW_THREADS
3167#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10003168 if (path->wide)
3169 result = win32_wchdir(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003170 else
Larry Hastings2f936352014-08-05 14:04:04 +10003171 result = win32_chdir(path->narrow);
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03003172 result = !result; /* on unix, success = 0, on windows, success = !0 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003173#else
3174#ifdef HAVE_FCHDIR
Larry Hastings2f936352014-08-05 14:04:04 +10003175 if (path->fd != -1)
3176 result = fchdir(path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003177 else
3178#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003179 result = chdir(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003180#endif
3181 Py_END_ALLOW_THREADS
3182
3183 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003184 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003185 }
3186
Larry Hastings2f936352014-08-05 14:04:04 +10003187 Py_RETURN_NONE;
3188}
3189
3190
3191#ifdef HAVE_FCHDIR
3192/*[clinic input]
3193os.fchdir
3194
3195 fd: fildes
3196
3197Change to the directory of the given file descriptor.
3198
3199fd must be opened on a directory, not a file.
3200Equivalent to os.chdir(fd).
3201
3202[clinic start generated code]*/
3203
3204PyDoc_STRVAR(os_fchdir__doc__,
3205"fchdir($module, /, fd)\n"
3206"--\n"
3207"\n"
3208"Change to the directory of the given file descriptor.\n"
3209"\n"
3210"fd must be opened on a directory, not a file.\n"
3211"Equivalent to os.chdir(fd).");
3212
3213#define OS_FCHDIR_METHODDEF \
3214 {"fchdir", (PyCFunction)os_fchdir, METH_VARARGS|METH_KEYWORDS, os_fchdir__doc__},
3215
3216static PyObject *
3217os_fchdir_impl(PyModuleDef *module, int fd);
3218
3219static PyObject *
3220os_fchdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3221{
3222 PyObject *return_value = NULL;
3223 static char *_keywords[] = {"fd", NULL};
3224 int fd;
3225
3226 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3227 "O&:fchdir", _keywords,
3228 fildes_converter, &fd))
3229 goto exit;
3230 return_value = os_fchdir_impl(module, fd);
Georg Brandlf7875592012-06-24 13:58:31 +02003231
Larry Hastings9cf065c2012-06-22 16:30:09 -07003232exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07003233 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003234}
3235
Fred Drake4d1e64b2002-04-15 19:40:07 +00003236static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003237os_fchdir_impl(PyModuleDef *module, int fd)
3238/*[clinic end generated code: output=9f6dbc89b2778834 input=18e816479a2fa985]*/
Fred Drake4d1e64b2002-04-15 19:40:07 +00003239{
Larry Hastings2f936352014-08-05 14:04:04 +10003240 return posix_fildes_fd(fd, fchdir);
Fred Drake4d1e64b2002-04-15 19:40:07 +00003241}
3242#endif /* HAVE_FCHDIR */
3243
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003244
Larry Hastings2f936352014-08-05 14:04:04 +10003245/*[clinic input]
3246os.chmod
3247
3248 path: path_t(allow_fd='PATH_HAVE_FCHMOD')
3249 Path to be modified. May always be specified as a str or bytes.
3250 On some platforms, path may also be specified as an open file descriptor.
3251 If this functionality is unavailable, using it raises an exception.
3252
3253 mode: int
3254 Operating-system mode bitfield.
3255
3256 *
3257
3258 dir_fd : dir_fd(requires='fchmodat') = None
3259 If not None, it should be a file descriptor open to a directory,
3260 and path should be relative; path will then be relative to that
3261 directory.
3262
3263 follow_symlinks: bool = True
3264 If False, and the last element of the path is a symbolic link,
3265 chmod will modify the symbolic link itself instead of the file
3266 the link points to.
3267
3268Change the access permissions of a file.
3269
3270It is an error to use dir_fd or follow_symlinks when specifying path as
3271 an open file descriptor.
3272dir_fd and follow_symlinks may not be implemented on your platform.
3273 If they are unavailable, using them will raise a NotImplementedError.
3274
3275[clinic start generated code]*/
3276
3277PyDoc_STRVAR(os_chmod__doc__,
3278"chmod($module, /, path, mode, *, dir_fd=None, follow_symlinks=True)\n"
3279"--\n"
3280"\n"
3281"Change the access permissions of a file.\n"
3282"\n"
3283" path\n"
3284" Path to be modified. May always be specified as a str or bytes.\n"
3285" On some platforms, path may also be specified as an open file descriptor.\n"
3286" If this functionality is unavailable, using it raises an exception.\n"
3287" mode\n"
3288" Operating-system mode bitfield.\n"
3289" dir_fd\n"
3290" If not None, it should be a file descriptor open to a directory,\n"
3291" and path should be relative; path will then be relative to that\n"
3292" directory.\n"
3293" follow_symlinks\n"
3294" If False, and the last element of the path is a symbolic link,\n"
3295" chmod will modify the symbolic link itself instead of the file\n"
3296" the link points to.\n"
3297"\n"
3298"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3299" an open file descriptor.\n"
3300"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3301" If they are unavailable, using them will raise a NotImplementedError.");
3302
3303#define OS_CHMOD_METHODDEF \
3304 {"chmod", (PyCFunction)os_chmod, METH_VARARGS|METH_KEYWORDS, os_chmod__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003305
Barry Warsaw53699e91996-12-10 23:23:01 +00003306static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003307os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks);
3308
3309static PyObject *
3310os_chmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003311{
Larry Hastings2f936352014-08-05 14:04:04 +10003312 PyObject *return_value = NULL;
3313 static char *_keywords[] = {"path", "mode", "dir_fd", "follow_symlinks", NULL};
3314 path_t path = PATH_T_INITIALIZE("chmod", "path", 0, PATH_HAVE_FCHMOD);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003315 int mode;
3316 int dir_fd = DEFAULT_DIR_FD;
3317 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10003318
3319 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3320 "O&i|$O&p:chmod", _keywords,
3321 path_converter, &path, &mode, FCHMODAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3322 goto exit;
3323 return_value = os_chmod_impl(module, &path, mode, dir_fd, follow_symlinks);
3324
3325exit:
3326 /* Cleanup for path */
3327 path_cleanup(&path);
3328
3329 return return_value;
3330}
3331
3332static PyObject *
3333os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks)
3334/*[clinic end generated code: output=1e9db031aea46422 input=7f1618e5e15cc196]*/
3335{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003336 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003337
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003338#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003339 DWORD attr;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003340#endif
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00003341
Larry Hastings9cf065c2012-06-22 16:30:09 -07003342#ifdef HAVE_FCHMODAT
3343 int fchmodat_nofollow_unsupported = 0;
3344#endif
3345
Larry Hastings9cf065c2012-06-22 16:30:09 -07003346#if !(defined(HAVE_FCHMODAT) || defined(HAVE_LCHMOD))
3347 if (follow_symlinks_specified("chmod", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003348 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003349#endif
3350
3351#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003352 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003353 if (path->wide)
3354 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003355 else
Larry Hastings2f936352014-08-05 14:04:04 +10003356 attr = GetFileAttributesA(path->narrow);
Tim Golden23005082013-10-25 11:22:37 +01003357 if (attr == INVALID_FILE_ATTRIBUTES)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003358 result = 0;
3359 else {
3360 if (mode & _S_IWRITE)
Victor Stinner8c62be82010-05-06 00:08:46 +00003361 attr &= ~FILE_ATTRIBUTE_READONLY;
3362 else
3363 attr |= FILE_ATTRIBUTE_READONLY;
Larry Hastings2f936352014-08-05 14:04:04 +10003364 if (path->wide)
3365 result = SetFileAttributesW(path->wide, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003366 else
Larry Hastings2f936352014-08-05 14:04:04 +10003367 result = SetFileAttributesA(path->narrow, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003368 }
3369 Py_END_ALLOW_THREADS
3370
3371 if (!result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003372 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003373 }
3374#else /* MS_WINDOWS */
3375 Py_BEGIN_ALLOW_THREADS
3376#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003377 if (path->fd != -1)
3378 result = fchmod(path->fd, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003379 else
3380#endif
3381#ifdef HAVE_LCHMOD
3382 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003383 result = lchmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003384 else
3385#endif
3386#ifdef HAVE_FCHMODAT
3387 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks) {
3388 /*
3389 * fchmodat() doesn't currently support AT_SYMLINK_NOFOLLOW!
3390 * The documentation specifically shows how to use it,
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003391 * and then says it isn't implemented yet.
3392 * (true on linux with glibc 2.15, and openindiana 3.x)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003393 *
3394 * Once it is supported, os.chmod will automatically
3395 * support dir_fd and follow_symlinks=False. (Hopefully.)
3396 * Until then, we need to be careful what exception we raise.
3397 */
Larry Hastings2f936352014-08-05 14:04:04 +10003398 result = fchmodat(dir_fd, path->narrow, mode,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003399 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3400 /*
3401 * But wait! We can't throw the exception without allowing threads,
3402 * and we can't do that in this nested scope. (Macro trickery, sigh.)
3403 */
3404 fchmodat_nofollow_unsupported =
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003405 result &&
3406 ((errno == ENOTSUP) || (errno == EOPNOTSUPP)) &&
3407 !follow_symlinks;
Victor Stinner8c62be82010-05-06 00:08:46 +00003408 }
3409 else
Thomas Wouters477c8d52006-05-27 19:21:47 +00003410#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003411 result = chmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003412 Py_END_ALLOW_THREADS
3413
3414 if (result) {
3415#ifdef HAVE_FCHMODAT
3416 if (fchmodat_nofollow_unsupported) {
3417 if (dir_fd != DEFAULT_DIR_FD)
3418 dir_fd_and_follow_symlinks_invalid("chmod",
3419 dir_fd, follow_symlinks);
3420 else
3421 follow_symlinks_specified("chmod", follow_symlinks);
3422 }
3423 else
3424#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003425 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003426 }
3427#endif
3428
Larry Hastings2f936352014-08-05 14:04:04 +10003429 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003430}
3431
Larry Hastings9cf065c2012-06-22 16:30:09 -07003432
Christian Heimes4e30a842007-11-30 22:12:06 +00003433#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003434/*[clinic input]
3435os.fchmod
3436
3437 fd: int
3438 mode: int
3439
3440Change the access permissions of the file given by file descriptor fd.
3441
3442Equivalent to os.chmod(fd, mode).
3443[clinic start generated code]*/
3444
3445PyDoc_STRVAR(os_fchmod__doc__,
3446"fchmod($module, /, fd, mode)\n"
3447"--\n"
3448"\n"
3449"Change the access permissions of the file given by file descriptor fd.\n"
3450"\n"
3451"Equivalent to os.chmod(fd, mode).");
3452
3453#define OS_FCHMOD_METHODDEF \
3454 {"fchmod", (PyCFunction)os_fchmod, METH_VARARGS|METH_KEYWORDS, os_fchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003455
3456static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003457os_fchmod_impl(PyModuleDef *module, int fd, int mode);
3458
3459static PyObject *
3460os_fchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003461{
Larry Hastings2f936352014-08-05 14:04:04 +10003462 PyObject *return_value = NULL;
3463 static char *_keywords[] = {"fd", "mode", NULL};
3464 int fd;
3465 int mode;
3466
3467 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3468 "ii:fchmod", _keywords,
3469 &fd, &mode))
3470 goto exit;
3471 return_value = os_fchmod_impl(module, fd, mode);
3472
3473exit:
3474 return return_value;
3475}
3476
3477static PyObject *
3478os_fchmod_impl(PyModuleDef *module, int fd, int mode)
3479/*[clinic end generated code: output=3c19fbfd724a8e0f input=8ab11975ca01ee5b]*/
3480{
3481 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003482 Py_BEGIN_ALLOW_THREADS
3483 res = fchmod(fd, mode);
3484 Py_END_ALLOW_THREADS
3485 if (res < 0)
3486 return posix_error();
3487 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003488}
3489#endif /* HAVE_FCHMOD */
3490
Larry Hastings2f936352014-08-05 14:04:04 +10003491
Christian Heimes4e30a842007-11-30 22:12:06 +00003492#ifdef HAVE_LCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003493/*[clinic input]
3494os.lchmod
3495
3496 path: path_t
3497 mode: int
3498
3499Change the access permissions of a file, without following symbolic links.
3500
3501If path is a symlink, this affects the link itself rather than the target.
3502Equivalent to chmod(path, mode, follow_symlinks=False)."
3503[clinic start generated code]*/
3504
3505PyDoc_STRVAR(os_lchmod__doc__,
3506"lchmod($module, /, path, mode)\n"
3507"--\n"
3508"\n"
3509"Change the access permissions of a file, without following symbolic links.\n"
3510"\n"
3511"If path is a symlink, this affects the link itself rather than the target.\n"
3512"Equivalent to chmod(path, mode, follow_symlinks=False).\"");
3513
3514#define OS_LCHMOD_METHODDEF \
3515 {"lchmod", (PyCFunction)os_lchmod, METH_VARARGS|METH_KEYWORDS, os_lchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003516
3517static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003518os_lchmod_impl(PyModuleDef *module, path_t *path, int mode);
3519
3520static PyObject *
3521os_lchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003522{
Larry Hastings2f936352014-08-05 14:04:04 +10003523 PyObject *return_value = NULL;
3524 static char *_keywords[] = {"path", "mode", NULL};
3525 path_t path = PATH_T_INITIALIZE("lchmod", "path", 0, 0);
3526 int mode;
3527
3528 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3529 "O&i:lchmod", _keywords,
3530 path_converter, &path, &mode))
3531 goto exit;
3532 return_value = os_lchmod_impl(module, &path, mode);
3533
3534exit:
3535 /* Cleanup for path */
3536 path_cleanup(&path);
3537
3538 return return_value;
3539}
3540
3541static PyObject *
3542os_lchmod_impl(PyModuleDef *module, path_t *path, int mode)
3543/*[clinic end generated code: output=2849977d65f8c68c input=90c5663c7465d24f]*/
3544{
Victor Stinner8c62be82010-05-06 00:08:46 +00003545 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003546 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003547 res = lchmod(path->narrow, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +00003548 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003549 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003550 path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003551 return NULL;
3552 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003553 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003554}
3555#endif /* HAVE_LCHMOD */
3556
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003557
Thomas Wouterscf297e42007-02-23 15:07:44 +00003558#ifdef HAVE_CHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003559/*[clinic input]
3560os.chflags
3561
3562 path: path_t
3563 flags: unsigned_long(bitwise=True)
3564 follow_symlinks: bool=True
3565
3566Set file flags.
3567
3568If follow_symlinks is False, and the last element of the path is a symbolic
3569 link, chflags will change flags on the symbolic link itself instead of the
3570 file the link points to.
3571follow_symlinks may not be implemented on your platform. If it is
3572unavailable, using it will raise a NotImplementedError.
3573
3574[clinic start generated code]*/
3575
3576PyDoc_STRVAR(os_chflags__doc__,
3577"chflags($module, /, path, flags, follow_symlinks=True)\n"
3578"--\n"
3579"\n"
3580"Set file flags.\n"
3581"\n"
3582"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3583" link, chflags will change flags on the symbolic link itself instead of the\n"
3584" file the link points to.\n"
3585"follow_symlinks may not be implemented on your platform. If it is\n"
3586"unavailable, using it will raise a NotImplementedError.");
3587
3588#define OS_CHFLAGS_METHODDEF \
3589 {"chflags", (PyCFunction)os_chflags, METH_VARARGS|METH_KEYWORDS, os_chflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003590
3591static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003592os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks);
3593
3594static PyObject *
3595os_chflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003596{
Larry Hastings2f936352014-08-05 14:04:04 +10003597 PyObject *return_value = NULL;
3598 static char *_keywords[] = {"path", "flags", "follow_symlinks", NULL};
3599 path_t path = PATH_T_INITIALIZE("chflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003600 unsigned long flags;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003601 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003602
Larry Hastings2f936352014-08-05 14:04:04 +10003603 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3604 "O&k|p:chflags", _keywords,
3605 path_converter, &path, &flags, &follow_symlinks))
3606 goto exit;
3607 return_value = os_chflags_impl(module, &path, flags, follow_symlinks);
3608
3609exit:
3610 /* Cleanup for path */
3611 path_cleanup(&path);
3612
3613 return return_value;
3614}
3615
3616static PyObject *
3617os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks)
3618/*[clinic end generated code: output=2767927bf071e3cf input=0327e29feb876236]*/
3619{
3620 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003621
3622#ifndef HAVE_LCHFLAGS
3623 if (follow_symlinks_specified("chflags", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003624 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003625#endif
3626
Victor Stinner8c62be82010-05-06 00:08:46 +00003627 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003628#ifdef HAVE_LCHFLAGS
3629 if (!follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10003630 result = lchflags(path->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003631 else
3632#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003633 result = chflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003634 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003635
Larry Hastings2f936352014-08-05 14:04:04 +10003636 if (result)
3637 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003638
Larry Hastings2f936352014-08-05 14:04:04 +10003639 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003640}
3641#endif /* HAVE_CHFLAGS */
3642
Larry Hastings2f936352014-08-05 14:04:04 +10003643
Thomas Wouterscf297e42007-02-23 15:07:44 +00003644#ifdef HAVE_LCHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003645/*[clinic input]
3646os.lchflags
3647
3648 path: path_t
3649 flags: unsigned_long(bitwise=True)
3650
3651Set file flags.
3652
3653This function will not follow symbolic links.
3654Equivalent to chflags(path, flags, follow_symlinks=False).
3655[clinic start generated code]*/
3656
3657PyDoc_STRVAR(os_lchflags__doc__,
3658"lchflags($module, /, path, flags)\n"
3659"--\n"
3660"\n"
3661"Set file flags.\n"
3662"\n"
3663"This function will not follow symbolic links.\n"
3664"Equivalent to chflags(path, flags, follow_symlinks=False).");
3665
3666#define OS_LCHFLAGS_METHODDEF \
3667 {"lchflags", (PyCFunction)os_lchflags, METH_VARARGS|METH_KEYWORDS, os_lchflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003668
3669static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003670os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags);
3671
3672static PyObject *
3673os_lchflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003674{
Larry Hastings2f936352014-08-05 14:04:04 +10003675 PyObject *return_value = NULL;
3676 static char *_keywords[] = {"path", "flags", NULL};
3677 path_t path = PATH_T_INITIALIZE("lchflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003678 unsigned long flags;
Larry Hastings2f936352014-08-05 14:04:04 +10003679
3680 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3681 "O&k:lchflags", _keywords,
3682 path_converter, &path, &flags))
3683 goto exit;
3684 return_value = os_lchflags_impl(module, &path, flags);
3685
3686exit:
3687 /* Cleanup for path */
3688 path_cleanup(&path);
3689
3690 return return_value;
3691}
3692
3693static PyObject *
3694os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags)
3695/*[clinic end generated code: output=bb93b6b8a5e45aa7 input=f9f82ea8b585ca9d]*/
3696{
Victor Stinner8c62be82010-05-06 00:08:46 +00003697 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003698 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003699 res = lchflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003700 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003701 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003702 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003703 }
Victor Stinner292c8352012-10-30 02:17:38 +01003704 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003705}
3706#endif /* HAVE_LCHFLAGS */
3707
Larry Hastings2f936352014-08-05 14:04:04 +10003708
Martin v. Löwis244edc82001-10-04 22:44:26 +00003709#ifdef HAVE_CHROOT
Larry Hastings2f936352014-08-05 14:04:04 +10003710/*[clinic input]
3711os.chroot
3712 path: path_t
3713
3714Change root directory to path.
3715
3716[clinic start generated code]*/
3717
3718PyDoc_STRVAR(os_chroot__doc__,
3719"chroot($module, /, path)\n"
3720"--\n"
3721"\n"
3722"Change root directory to path.");
3723
3724#define OS_CHROOT_METHODDEF \
3725 {"chroot", (PyCFunction)os_chroot, METH_VARARGS|METH_KEYWORDS, os_chroot__doc__},
Martin v. Löwis244edc82001-10-04 22:44:26 +00003726
3727static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003728os_chroot_impl(PyModuleDef *module, path_t *path);
3729
3730static PyObject *
3731os_chroot(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis244edc82001-10-04 22:44:26 +00003732{
Larry Hastings2f936352014-08-05 14:04:04 +10003733 PyObject *return_value = NULL;
3734 static char *_keywords[] = {"path", NULL};
3735 path_t path = PATH_T_INITIALIZE("chroot", "path", 0, 0);
3736
3737 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3738 "O&:chroot", _keywords,
3739 path_converter, &path))
3740 goto exit;
3741 return_value = os_chroot_impl(module, &path);
3742
3743exit:
3744 /* Cleanup for path */
3745 path_cleanup(&path);
3746
3747 return return_value;
Martin v. Löwis244edc82001-10-04 22:44:26 +00003748}
Larry Hastings2f936352014-08-05 14:04:04 +10003749
3750static PyObject *
3751os_chroot_impl(PyModuleDef *module, path_t *path)
3752/*[clinic end generated code: output=15b1256cbe4f24a1 input=14822965652c3dc3]*/
3753{
3754 int res;
3755 Py_BEGIN_ALLOW_THREADS
3756 res = chroot(path->narrow);
3757 Py_END_ALLOW_THREADS
3758 if (res < 0)
3759 return path_error(path);
3760 Py_RETURN_NONE;
3761}
3762#endif /* HAVE_CHROOT */
3763
Martin v. Löwis244edc82001-10-04 22:44:26 +00003764
Guido van Rossum21142a01999-01-08 21:05:37 +00003765#ifdef HAVE_FSYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003766/*[clinic input]
3767os.fsync
3768
3769 fd: fildes
3770
3771Force write of fd to disk.
3772[clinic start generated code]*/
3773
3774PyDoc_STRVAR(os_fsync__doc__,
3775"fsync($module, /, fd)\n"
3776"--\n"
3777"\n"
3778"Force write of fd to disk.");
3779
3780#define OS_FSYNC_METHODDEF \
3781 {"fsync", (PyCFunction)os_fsync, METH_VARARGS|METH_KEYWORDS, os_fsync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003782
3783static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003784os_fsync_impl(PyModuleDef *module, int fd);
3785
3786static PyObject *
3787os_fsync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003788{
Larry Hastings2f936352014-08-05 14:04:04 +10003789 PyObject *return_value = NULL;
3790 static char *_keywords[] = {"fd", NULL};
3791 int fd;
3792
3793 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3794 "O&:fsync", _keywords,
3795 fildes_converter, &fd))
3796 goto exit;
3797 return_value = os_fsync_impl(module, fd);
3798
3799exit:
3800 return return_value;
3801}
3802
3803static PyObject *
3804os_fsync_impl(PyModuleDef *module, int fd)
3805/*[clinic end generated code: output=59f32d3a0b360133 input=21c3645c056967f2]*/
3806{
3807 return posix_fildes_fd(fd, fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003808}
3809#endif /* HAVE_FSYNC */
3810
Larry Hastings2f936352014-08-05 14:04:04 +10003811
Ross Lagerwall7807c352011-03-17 20:20:30 +02003812#ifdef HAVE_SYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003813/*[clinic input]
3814os.sync
3815
3816Force write of everything to disk.
3817[clinic start generated code]*/
3818
3819PyDoc_STRVAR(os_sync__doc__,
3820"sync($module, /)\n"
3821"--\n"
3822"\n"
3823"Force write of everything to disk.");
3824
3825#define OS_SYNC_METHODDEF \
3826 {"sync", (PyCFunction)os_sync, METH_NOARGS, os_sync__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02003827
3828static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003829os_sync_impl(PyModuleDef *module);
3830
3831static PyObject *
3832os_sync(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3833{
3834 return os_sync_impl(module);
3835}
3836
3837static PyObject *
3838os_sync_impl(PyModuleDef *module)
3839/*[clinic end generated code: output=526c495683d0bb38 input=84749fe5e9b404ff]*/
Ross Lagerwall7807c352011-03-17 20:20:30 +02003840{
3841 Py_BEGIN_ALLOW_THREADS
3842 sync();
3843 Py_END_ALLOW_THREADS
3844 Py_RETURN_NONE;
3845}
Larry Hastings2f936352014-08-05 14:04:04 +10003846#endif /* HAVE_SYNC */
3847
Ross Lagerwall7807c352011-03-17 20:20:30 +02003848
Guido van Rossum21142a01999-01-08 21:05:37 +00003849#ifdef HAVE_FDATASYNC
Guido van Rossum7f58e2e2000-09-22 17:26:14 +00003850#ifdef __hpux
Guido van Rossumecc23b02000-09-22 16:01:05 +00003851extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
3852#endif
3853
Larry Hastings2f936352014-08-05 14:04:04 +10003854/*[clinic input]
3855os.fdatasync
3856
3857 fd: fildes
3858
3859Force write of fd to disk without forcing update of metadata.
3860[clinic start generated code]*/
3861
3862PyDoc_STRVAR(os_fdatasync__doc__,
3863"fdatasync($module, /, fd)\n"
3864"--\n"
3865"\n"
3866"Force write of fd to disk without forcing update of metadata.");
3867
3868#define OS_FDATASYNC_METHODDEF \
3869 {"fdatasync", (PyCFunction)os_fdatasync, METH_VARARGS|METH_KEYWORDS, os_fdatasync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003870
3871static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003872os_fdatasync_impl(PyModuleDef *module, int fd);
3873
3874static PyObject *
3875os_fdatasync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003876{
Larry Hastings2f936352014-08-05 14:04:04 +10003877 PyObject *return_value = NULL;
3878 static char *_keywords[] = {"fd", NULL};
3879 int fd;
3880
3881 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3882 "O&:fdatasync", _keywords,
3883 fildes_converter, &fd))
3884 goto exit;
3885 return_value = os_fdatasync_impl(module, fd);
3886
3887exit:
3888 return return_value;
3889}
3890
3891static PyObject *
3892os_fdatasync_impl(PyModuleDef *module, int fd)
3893/*[clinic end generated code: output=2335fdfd37c92180 input=bc74791ee54dd291]*/
3894{
3895 return posix_fildes_fd(fd, fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003896}
3897#endif /* HAVE_FDATASYNC */
3898
3899
Fredrik Lundh10723342000-07-10 16:38:09 +00003900#ifdef HAVE_CHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003901/*[clinic input]
3902os.chown
3903
3904 path : path_t(allow_fd='PATH_HAVE_FCHOWN')
3905 Path to be examined; can be string, bytes, or open-file-descriptor int.
3906
3907 uid: uid_t
3908
3909 gid: gid_t
3910
3911 *
3912
3913 dir_fd : dir_fd(requires='fchownat') = None
3914 If not None, it should be a file descriptor open to a directory,
3915 and path should be relative; path will then be relative to that
3916 directory.
3917
3918 follow_symlinks: bool = True
3919 If False, and the last element of the path is a symbolic link,
3920 stat will examine the symbolic link itself instead of the file
3921 the link points to.
3922
3923Change the owner and group id of path to the numeric uid and gid.\
3924
3925path may always be specified as a string.
3926On some platforms, path may also be specified as an open file descriptor.
3927 If this functionality is unavailable, using it raises an exception.
3928If dir_fd is not None, it should be a file descriptor open to a directory,
3929 and path should be relative; path will then be relative to that directory.
3930If follow_symlinks is False, and the last element of the path is a symbolic
3931 link, chown will modify the symbolic link itself instead of the file the
3932 link points to.
3933It is an error to use dir_fd or follow_symlinks when specifying path as
3934 an open file descriptor.
3935dir_fd and follow_symlinks may not be implemented on your platform.
3936 If they are unavailable, using them will raise a NotImplementedError.
3937
3938[clinic start generated code]*/
3939
3940PyDoc_STRVAR(os_chown__doc__,
3941"chown($module, /, path, uid, gid, *, dir_fd=None, follow_symlinks=True)\n"
3942"--\n"
3943"\n"
3944"Change the owner and group id of path to the numeric uid and gid.\\\n"
3945"\n"
3946" path\n"
3947" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
3948" dir_fd\n"
3949" If not None, it should be a file descriptor open to a directory,\n"
3950" and path should be relative; path will then be relative to that\n"
3951" directory.\n"
3952" follow_symlinks\n"
3953" If False, and the last element of the path is a symbolic link,\n"
3954" stat will examine the symbolic link itself instead of the file\n"
3955" the link points to.\n"
3956"\n"
3957"path may always be specified as a string.\n"
3958"On some platforms, path may also be specified as an open file descriptor.\n"
3959" If this functionality is unavailable, using it raises an exception.\n"
3960"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
3961" and path should be relative; path will then be relative to that directory.\n"
3962"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3963" link, chown will modify the symbolic link itself instead of the file the\n"
3964" link points to.\n"
3965"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3966" an open file descriptor.\n"
3967"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3968" If they are unavailable, using them will raise a NotImplementedError.");
3969
3970#define OS_CHOWN_METHODDEF \
3971 {"chown", (PyCFunction)os_chown, METH_VARARGS|METH_KEYWORDS, os_chown__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003972
Barry Warsaw53699e91996-12-10 23:23:01 +00003973static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003974os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks);
3975
3976static PyObject *
3977os_chown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumb6775db1994-08-01 11:34:53 +00003978{
Larry Hastings2f936352014-08-05 14:04:04 +10003979 PyObject *return_value = NULL;
3980 static char *_keywords[] = {"path", "uid", "gid", "dir_fd", "follow_symlinks", NULL};
3981 path_t path = PATH_T_INITIALIZE("chown", "path", 0, PATH_HAVE_FCHOWN);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003982 uid_t uid;
3983 gid_t gid;
3984 int dir_fd = DEFAULT_DIR_FD;
3985 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003986
Larry Hastings2f936352014-08-05 14:04:04 +10003987 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3988 "O&O&O&|$O&p:chown", _keywords,
3989 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid, FCHOWNAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3990 goto exit;
3991 return_value = os_chown_impl(module, &path, uid, gid, dir_fd, follow_symlinks);
3992
3993exit:
3994 /* Cleanup for path */
3995 path_cleanup(&path);
3996
3997 return return_value;
3998}
3999
4000static PyObject *
4001os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks)
4002/*[clinic end generated code: output=22f011e3b4f9ff49 input=a61cc35574814d5d]*/
4003{
4004 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004005
4006#if !(defined(HAVE_LCHOWN) || defined(HAVE_FCHOWNAT))
4007 if (follow_symlinks_specified("chown", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004008 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004009#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004010 if (dir_fd_and_fd_invalid("chown", dir_fd, path->fd) ||
4011 fd_and_follow_symlinks_invalid("chown", path->fd, follow_symlinks))
4012 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004013
4014#ifdef __APPLE__
4015 /*
4016 * This is for Mac OS X 10.3, which doesn't have lchown.
4017 * (But we still have an lchown symbol because of weak-linking.)
4018 * It doesn't have fchownat either. So there's no possibility
4019 * of a graceful failover.
Georg Brandlf7875592012-06-24 13:58:31 +02004020 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004021 if ((!follow_symlinks) && (lchown == NULL)) {
4022 follow_symlinks_specified("chown", follow_symlinks);
Larry Hastings2f936352014-08-05 14:04:04 +10004023 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004024 }
4025#endif
4026
Victor Stinner8c62be82010-05-06 00:08:46 +00004027 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004028#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004029 if (path->fd != -1)
4030 result = fchown(path->fd, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004031 else
4032#endif
4033#ifdef HAVE_LCHOWN
4034 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10004035 result = lchown(path->narrow, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004036 else
4037#endif
4038#ifdef HAVE_FCHOWNAT
4039 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004040 result = fchownat(dir_fd, path->narrow, uid, gid,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004041 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
4042 else
4043#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004044 result = chown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004045 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004046
Larry Hastings2f936352014-08-05 14:04:04 +10004047 if (result)
4048 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004049
Larry Hastings2f936352014-08-05 14:04:04 +10004050 Py_RETURN_NONE;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004051}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004052#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004053
Larry Hastings2f936352014-08-05 14:04:04 +10004054
Christian Heimes4e30a842007-11-30 22:12:06 +00004055#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004056/*[clinic input]
4057os.fchown
4058
4059 fd: int
4060 uid: uid_t
4061 gid: gid_t
4062
4063Change the owner and group id of the file specified by file descriptor.
4064
4065Equivalent to os.chown(fd, uid, gid).
4066
4067[clinic start generated code]*/
4068
4069PyDoc_STRVAR(os_fchown__doc__,
4070"fchown($module, /, fd, uid, gid)\n"
4071"--\n"
4072"\n"
4073"Change the owner and group id of the file specified by file descriptor.\n"
4074"\n"
4075"Equivalent to os.chown(fd, uid, gid).");
4076
4077#define OS_FCHOWN_METHODDEF \
4078 {"fchown", (PyCFunction)os_fchown, METH_VARARGS|METH_KEYWORDS, os_fchown__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00004079
4080static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004081os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid);
4082
4083static PyObject *
4084os_fchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00004085{
Larry Hastings2f936352014-08-05 14:04:04 +10004086 PyObject *return_value = NULL;
4087 static char *_keywords[] = {"fd", "uid", "gid", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00004088 int fd;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004089 uid_t uid;
4090 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004091
4092 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4093 "iO&O&:fchown", _keywords,
4094 &fd, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4095 goto exit;
4096 return_value = os_fchown_impl(module, fd, uid, gid);
4097
4098exit:
4099 return return_value;
4100}
4101
4102static PyObject *
4103os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid)
4104/*[clinic end generated code: output=687781cb7d8974d6 input=3af544ba1b13a0d7]*/
4105{
Victor Stinner8c62be82010-05-06 00:08:46 +00004106 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004107 Py_BEGIN_ALLOW_THREADS
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004108 res = fchown(fd, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004109 Py_END_ALLOW_THREADS
4110 if (res < 0)
4111 return posix_error();
4112 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00004113}
4114#endif /* HAVE_FCHOWN */
4115
Larry Hastings2f936352014-08-05 14:04:04 +10004116
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004117#ifdef HAVE_LCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004118/*[clinic input]
4119os.lchown
4120
4121 path : path_t
4122 uid: uid_t
4123 gid: gid_t
4124
4125Change the owner and group id of path to the numeric uid and gid.
4126
4127This function will not follow symbolic links.
4128Equivalent to os.chown(path, uid, gid, follow_symlinks=False).
4129[clinic start generated code]*/
4130
4131PyDoc_STRVAR(os_lchown__doc__,
4132"lchown($module, /, path, uid, gid)\n"
4133"--\n"
4134"\n"
4135"Change the owner and group id of path to the numeric uid and gid.\n"
4136"\n"
4137"This function will not follow symbolic links.\n"
4138"Equivalent to os.chown(path, uid, gid, follow_symlinks=False).");
4139
4140#define OS_LCHOWN_METHODDEF \
4141 {"lchown", (PyCFunction)os_lchown, METH_VARARGS|METH_KEYWORDS, os_lchown__doc__},
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004142
4143static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004144os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid);
4145
4146static PyObject *
4147os_lchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004148{
Larry Hastings2f936352014-08-05 14:04:04 +10004149 PyObject *return_value = NULL;
4150 static char *_keywords[] = {"path", "uid", "gid", NULL};
4151 path_t path = PATH_T_INITIALIZE("lchown", "path", 0, 0);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004152 uid_t uid;
4153 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004154
4155 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4156 "O&O&O&:lchown", _keywords,
4157 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4158 goto exit;
4159 return_value = os_lchown_impl(module, &path, uid, gid);
4160
4161exit:
4162 /* Cleanup for path */
4163 path_cleanup(&path);
4164
4165 return return_value;
4166}
4167
4168static PyObject *
4169os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid)
4170/*[clinic end generated code: output=bf25fdb0d25130e2 input=b1c6014d563a7161]*/
4171{
Victor Stinner8c62be82010-05-06 00:08:46 +00004172 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004173 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004174 res = lchown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004175 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01004176 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10004177 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01004178 }
Larry Hastings2f936352014-08-05 14:04:04 +10004179 Py_RETURN_NONE;
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004180}
4181#endif /* HAVE_LCHOWN */
4182
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004183
Barry Warsaw53699e91996-12-10 23:23:01 +00004184static PyObject *
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004185posix_getcwd(int use_bytes)
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004186{
Victor Stinner8c62be82010-05-06 00:08:46 +00004187 char buf[1026];
4188 char *res;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004189
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004190#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00004191 if (!use_bytes) {
4192 wchar_t wbuf[1026];
4193 wchar_t *wbuf2 = wbuf;
4194 PyObject *resobj;
4195 DWORD len;
4196 Py_BEGIN_ALLOW_THREADS
Victor Stinner75875072013-11-24 19:23:25 +01004197 len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004198 /* If the buffer is large enough, len does not include the
4199 terminating \0. If the buffer is too small, len includes
4200 the space needed for the terminator. */
Victor Stinner75875072013-11-24 19:23:25 +01004201 if (len >= Py_ARRAY_LENGTH(wbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004202 wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004203 if (wbuf2)
4204 len = GetCurrentDirectoryW(len, wbuf2);
4205 }
4206 Py_END_ALLOW_THREADS
4207 if (!wbuf2) {
4208 PyErr_NoMemory();
4209 return NULL;
4210 }
4211 if (!len) {
Victor Stinnerb024e842012-10-31 22:24:06 +01004212 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004213 PyMem_RawFree(wbuf2);
Victor Stinnerb024e842012-10-31 22:24:06 +01004214 return PyErr_SetFromWindowsErr(0);
Victor Stinner8c62be82010-05-06 00:08:46 +00004215 }
4216 resobj = PyUnicode_FromWideChar(wbuf2, len);
Victor Stinnerb024e842012-10-31 22:24:06 +01004217 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004218 PyMem_RawFree(wbuf2);
Victor Stinner8c62be82010-05-06 00:08:46 +00004219 return resobj;
4220 }
Victor Stinnerf7c5ae22011-11-16 23:43:07 +01004221
4222 if (win32_warn_bytes_api())
4223 return NULL;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004224#endif
4225
Victor Stinner8c62be82010-05-06 00:08:46 +00004226 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004227 res = getcwd(buf, sizeof buf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004228 Py_END_ALLOW_THREADS
4229 if (res == NULL)
4230 return posix_error();
4231 if (use_bytes)
4232 return PyBytes_FromStringAndSize(buf, strlen(buf));
Victor Stinner97c18ab2010-05-07 16:34:53 +00004233 return PyUnicode_DecodeFSDefault(buf);
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004234}
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004235
Larry Hastings2f936352014-08-05 14:04:04 +10004236
4237/*[clinic input]
4238os.getcwd
4239
4240Return a unicode string representing the current working directory.
4241[clinic start generated code]*/
4242
4243PyDoc_STRVAR(os_getcwd__doc__,
4244"getcwd($module, /)\n"
4245"--\n"
4246"\n"
4247"Return a unicode string representing the current working directory.");
4248
4249#define OS_GETCWD_METHODDEF \
4250 {"getcwd", (PyCFunction)os_getcwd, METH_NOARGS, os_getcwd__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004251
4252static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004253os_getcwd_impl(PyModuleDef *module);
4254
4255static PyObject *
4256os_getcwd(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4257{
4258 return os_getcwd_impl(module);
4259}
4260
4261static PyObject *
4262os_getcwd_impl(PyModuleDef *module)
4263/*[clinic end generated code: output=d70b281db5c78ff7 input=f069211bb70e3d39]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004264{
4265 return posix_getcwd(0);
4266}
4267
Larry Hastings2f936352014-08-05 14:04:04 +10004268
4269/*[clinic input]
4270os.getcwdb
4271
4272Return a bytes string representing the current working directory.
4273[clinic start generated code]*/
4274
4275PyDoc_STRVAR(os_getcwdb__doc__,
4276"getcwdb($module, /)\n"
4277"--\n"
4278"\n"
4279"Return a bytes string representing the current working directory.");
4280
4281#define OS_GETCWDB_METHODDEF \
4282 {"getcwdb", (PyCFunction)os_getcwdb, METH_NOARGS, os_getcwdb__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004283
4284static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004285os_getcwdb_impl(PyModuleDef *module);
4286
4287static PyObject *
4288os_getcwdb(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4289{
4290 return os_getcwdb_impl(module);
4291}
4292
4293static PyObject *
4294os_getcwdb_impl(PyModuleDef *module)
4295/*[clinic end generated code: output=75da47f2d75f9166 input=f6f6a378dad3d9cb]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004296{
4297 return posix_getcwd(1);
4298}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004299
Larry Hastings2f936352014-08-05 14:04:04 +10004300
Larry Hastings9cf065c2012-06-22 16:30:09 -07004301#if ((!defined(HAVE_LINK)) && defined(MS_WINDOWS))
4302#define HAVE_LINK 1
4303#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004304
Guido van Rossumb6775db1994-08-01 11:34:53 +00004305#ifdef HAVE_LINK
Larry Hastings2f936352014-08-05 14:04:04 +10004306/*[clinic input]
4307
4308os.link
4309
4310 src : path_t
4311 dst : path_t
4312 *
4313 src_dir_fd : dir_fd = None
4314 dst_dir_fd : dir_fd = None
4315 follow_symlinks: bool = True
4316
4317Create a hard link to a file.
4318
4319If either src_dir_fd or dst_dir_fd is not None, it should be a file
4320 descriptor open to a directory, and the respective path string (src or dst)
4321 should be relative; the path will then be relative to that directory.
4322If follow_symlinks is False, and the last element of src is a symbolic
4323 link, link will create a link to the symbolic link itself instead of the
4324 file the link points to.
4325src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your
4326 platform. If they are unavailable, using them will raise a
4327 NotImplementedError.
4328[clinic start generated code]*/
4329
4330PyDoc_STRVAR(os_link__doc__,
4331"link($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None,\n"
4332" follow_symlinks=True)\n"
4333"--\n"
4334"\n"
4335"Create a hard link to a file.\n"
4336"\n"
4337"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
4338" descriptor open to a directory, and the respective path string (src or dst)\n"
4339" should be relative; the path will then be relative to that directory.\n"
4340"If follow_symlinks is False, and the last element of src is a symbolic\n"
4341" link, link will create a link to the symbolic link itself instead of the\n"
4342" file the link points to.\n"
4343"src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your\n"
4344" platform. If they are unavailable, using them will raise a\n"
4345" NotImplementedError.");
4346
4347#define OS_LINK_METHODDEF \
4348 {"link", (PyCFunction)os_link, METH_VARARGS|METH_KEYWORDS, os_link__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004349
Barry Warsaw53699e91996-12-10 23:23:01 +00004350static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004351os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks);
4352
4353static PyObject *
4354os_link(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004355{
Larry Hastings2f936352014-08-05 14:04:04 +10004356 PyObject *return_value = NULL;
4357 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", "follow_symlinks", NULL};
4358 path_t src = PATH_T_INITIALIZE("link", "src", 0, 0);
4359 path_t dst = PATH_T_INITIALIZE("link", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004360 int src_dir_fd = DEFAULT_DIR_FD;
4361 int dst_dir_fd = DEFAULT_DIR_FD;
4362 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10004363
4364 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4365 "O&O&|$O&O&p:link", _keywords,
4366 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd, &follow_symlinks))
4367 goto exit;
4368 return_value = os_link_impl(module, &src, &dst, src_dir_fd, dst_dir_fd, follow_symlinks);
4369
4370exit:
4371 /* Cleanup for src */
4372 path_cleanup(&src);
4373 /* Cleanup for dst */
4374 path_cleanup(&dst);
4375
4376 return return_value;
4377}
4378
4379static PyObject *
4380os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks)
4381/*[clinic end generated code: output=53477662fe02e183 input=b0095ebbcbaa7e04]*/
4382{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004383#ifdef MS_WINDOWS
4384 BOOL result;
4385#else
4386 int result;
4387#endif
4388
Larry Hastings9cf065c2012-06-22 16:30:09 -07004389#ifndef HAVE_LINKAT
4390 if ((src_dir_fd != DEFAULT_DIR_FD) || (dst_dir_fd != DEFAULT_DIR_FD)) {
4391 argument_unavailable_error("link", "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10004392 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004393 }
4394#endif
4395
Larry Hastings2f936352014-08-05 14:04:04 +10004396 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004397 PyErr_SetString(PyExc_NotImplementedError,
4398 "link: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10004399 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004400 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004401
Brian Curtin1b9df392010-11-24 20:24:31 +00004402#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004403 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004404 if (src->wide)
4405 result = CreateHardLinkW(dst->wide, src->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004406 else
Larry Hastings2f936352014-08-05 14:04:04 +10004407 result = CreateHardLinkA(dst->narrow, src->narrow, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004408 Py_END_ALLOW_THREADS
Brian Curtin1b9df392010-11-24 20:24:31 +00004409
Larry Hastings2f936352014-08-05 14:04:04 +10004410 if (!result)
4411 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004412#else
4413 Py_BEGIN_ALLOW_THREADS
Larry Hastings67cbf7b2012-06-22 17:06:48 -07004414#ifdef HAVE_LINKAT
Larry Hastings9cf065c2012-06-22 16:30:09 -07004415 if ((src_dir_fd != DEFAULT_DIR_FD) ||
4416 (dst_dir_fd != DEFAULT_DIR_FD) ||
4417 (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004418 result = linkat(src_dir_fd, src->narrow,
4419 dst_dir_fd, dst->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004420 follow_symlinks ? AT_SYMLINK_FOLLOW : 0);
4421 else
4422#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004423 result = link(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004424 Py_END_ALLOW_THREADS
Brian Curtinfc889c42010-11-28 23:59:46 +00004425
Larry Hastings2f936352014-08-05 14:04:04 +10004426 if (result)
4427 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004428#endif
4429
Larry Hastings2f936352014-08-05 14:04:04 +10004430 Py_RETURN_NONE;
Brian Curtin1b9df392010-11-24 20:24:31 +00004431}
Larry Hastings9cf065c2012-06-22 16:30:09 -07004432#endif
4433
Brian Curtin1b9df392010-11-24 20:24:31 +00004434
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004435#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
Barry Warsaw53699e91996-12-10 23:23:01 +00004436static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004437_listdir_windows_no_opendir(path_t *path, PyObject *list)
Guido van Rossumb6775db1994-08-01 11:34:53 +00004438{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004439 PyObject *v;
4440 HANDLE hFindFile = INVALID_HANDLE_VALUE;
4441 BOOL result;
4442 WIN32_FIND_DATA FileData;
Victor Stinner75875072013-11-24 19:23:25 +01004443 char namebuf[MAX_PATH+4]; /* Overallocate for "\*.*" */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004444 char *bufptr = namebuf;
4445 /* only claim to have space for MAX_PATH */
Victor Stinner75875072013-11-24 19:23:25 +01004446 Py_ssize_t len = Py_ARRAY_LENGTH(namebuf)-4;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004447 PyObject *po = NULL;
4448 wchar_t *wnamebuf = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004449
Gregory P. Smith40a21602013-03-20 20:52:50 -07004450 if (!path->narrow) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004451 WIN32_FIND_DATAW wFileData;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004452 wchar_t *po_wchars;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004453
Gregory P. Smith40a21602013-03-20 20:52:50 -07004454 if (!path->wide) { /* Default arg: "." */
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004455 po_wchars = L".";
4456 len = 1;
4457 } else {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004458 po_wchars = path->wide;
4459 len = wcslen(path->wide);
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004460 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004461 /* The +5 is so we can append "\\*.*\0" */
Victor Stinnerb6404912013-07-07 16:21:41 +02004462 wnamebuf = PyMem_Malloc((len + 5) * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004463 if (!wnamebuf) {
4464 PyErr_NoMemory();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004465 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004466 }
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004467 wcscpy(wnamebuf, po_wchars);
Victor Stinner8c62be82010-05-06 00:08:46 +00004468 if (len > 0) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004469 wchar_t wch = wnamebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004470 if (wch != SEP && wch != ALTSEP && wch != L':')
4471 wnamebuf[len++] = SEP;
Victor Stinner8c62be82010-05-06 00:08:46 +00004472 wcscpy(wnamebuf + len, L"*.*");
4473 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004474 if ((list = PyList_New(0)) == NULL) {
4475 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004476 }
Antoine Pitroub73caab2010-08-09 23:39:31 +00004477 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004478 hFindFile = FindFirstFileW(wnamebuf, &wFileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004479 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004480 if (hFindFile == INVALID_HANDLE_VALUE) {
4481 int error = GetLastError();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004482 if (error == ERROR_FILE_NOT_FOUND)
4483 goto exit;
4484 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004485 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004486 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004487 }
4488 do {
4489 /* Skip over . and .. */
4490 if (wcscmp(wFileData.cFileName, L".") != 0 &&
4491 wcscmp(wFileData.cFileName, L"..") != 0) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004492 v = PyUnicode_FromWideChar(wFileData.cFileName,
4493 wcslen(wFileData.cFileName));
Victor Stinner8c62be82010-05-06 00:08:46 +00004494 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004495 Py_DECREF(list);
4496 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004497 break;
4498 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004499 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004500 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004501 Py_DECREF(list);
4502 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004503 break;
4504 }
4505 Py_DECREF(v);
4506 }
4507 Py_BEGIN_ALLOW_THREADS
4508 result = FindNextFileW(hFindFile, &wFileData);
4509 Py_END_ALLOW_THREADS
4510 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4511 it got to the end of the directory. */
4512 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004513 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004514 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004515 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004516 }
4517 } while (result == TRUE);
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00004518
Larry Hastings9cf065c2012-06-22 16:30:09 -07004519 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004520 }
Gregory P. Smith40a21602013-03-20 20:52:50 -07004521 strcpy(namebuf, path->narrow);
4522 len = path->length;
Victor Stinner8c62be82010-05-06 00:08:46 +00004523 if (len > 0) {
4524 char ch = namebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004525 if (ch != '\\' && ch != '/' && ch != ':')
4526 namebuf[len++] = '\\';
Victor Stinner8c62be82010-05-06 00:08:46 +00004527 strcpy(namebuf + len, "*.*");
4528 }
Guido van Rossumb6775db1994-08-01 11:34:53 +00004529
Larry Hastings9cf065c2012-06-22 16:30:09 -07004530 if ((list = PyList_New(0)) == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +00004531 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004532
Antoine Pitroub73caab2010-08-09 23:39:31 +00004533 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004534 hFindFile = FindFirstFile(namebuf, &FileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004535 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004536 if (hFindFile == INVALID_HANDLE_VALUE) {
4537 int error = GetLastError();
4538 if (error == ERROR_FILE_NOT_FOUND)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004539 goto exit;
4540 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004541 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004542 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004543 }
4544 do {
4545 /* Skip over . and .. */
4546 if (strcmp(FileData.cFileName, ".") != 0 &&
4547 strcmp(FileData.cFileName, "..") != 0) {
4548 v = PyBytes_FromString(FileData.cFileName);
4549 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004550 Py_DECREF(list);
4551 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004552 break;
4553 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004554 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004555 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004556 Py_DECREF(list);
4557 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004558 break;
4559 }
4560 Py_DECREF(v);
4561 }
4562 Py_BEGIN_ALLOW_THREADS
4563 result = FindNextFile(hFindFile, &FileData);
4564 Py_END_ALLOW_THREADS
4565 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4566 it got to the end of the directory. */
4567 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004568 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004569 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004570 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004571 }
4572 } while (result == TRUE);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004573
Larry Hastings9cf065c2012-06-22 16:30:09 -07004574exit:
4575 if (hFindFile != INVALID_HANDLE_VALUE) {
4576 if (FindClose(hFindFile) == FALSE) {
4577 if (list != NULL) {
4578 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004579 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004580 }
4581 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004582 }
Victor Stinnerb6404912013-07-07 16:21:41 +02004583 PyMem_Free(wnamebuf);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004584
Larry Hastings9cf065c2012-06-22 16:30:09 -07004585 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004586} /* end of _listdir_windows_no_opendir */
4587
4588#else /* thus POSIX, ie: not (MS_WINDOWS and not HAVE_OPENDIR) */
4589
4590static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004591_posix_listdir(path_t *path, PyObject *list)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004592{
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004593 PyObject *v;
4594 DIR *dirp = NULL;
4595 struct dirent *ep;
4596 int return_str; /* if false, return bytes */
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004597#ifdef HAVE_FDOPENDIR
4598 int fd = -1;
4599#endif
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004600
Victor Stinner8c62be82010-05-06 00:08:46 +00004601 errno = 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004602#ifdef HAVE_FDOPENDIR
Gregory P. Smith40a21602013-03-20 20:52:50 -07004603 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004604 /* closedir() closes the FD, so we duplicate it */
Victor Stinnerdaf45552013-08-28 00:53:59 +02004605 fd = _Py_dup(path->fd);
Victor Stinnerf3266652013-12-19 13:24:49 +01004606 if (fd == -1)
4607 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004608
Larry Hastingsfdaea062012-06-25 04:42:23 -07004609 return_str = 1;
4610
Larry Hastings9cf065c2012-06-22 16:30:09 -07004611 Py_BEGIN_ALLOW_THREADS
4612 dirp = fdopendir(fd);
4613 Py_END_ALLOW_THREADS
4614 }
4615 else
4616#endif
4617 {
Larry Hastingsfdaea062012-06-25 04:42:23 -07004618 char *name;
Gregory P. Smith40a21602013-03-20 20:52:50 -07004619 if (path->narrow) {
4620 name = path->narrow;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004621 /* only return bytes if they specified a bytes object */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004622 return_str = !(PyBytes_Check(path->object));
Larry Hastingsfdaea062012-06-25 04:42:23 -07004623 }
4624 else {
4625 name = ".";
4626 return_str = 1;
4627 }
4628
Larry Hastings9cf065c2012-06-22 16:30:09 -07004629 Py_BEGIN_ALLOW_THREADS
4630 dirp = opendir(name);
4631 Py_END_ALLOW_THREADS
4632 }
4633
4634 if (dirp == NULL) {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004635 list = path_error(path);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004636#ifdef HAVE_FDOPENDIR
4637 if (fd != -1) {
4638 Py_BEGIN_ALLOW_THREADS
4639 close(fd);
4640 Py_END_ALLOW_THREADS
4641 }
4642#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004643 goto exit;
4644 }
4645 if ((list = PyList_New(0)) == NULL) {
4646 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004647 }
4648 for (;;) {
4649 errno = 0;
4650 Py_BEGIN_ALLOW_THREADS
4651 ep = readdir(dirp);
4652 Py_END_ALLOW_THREADS
4653 if (ep == NULL) {
4654 if (errno == 0) {
4655 break;
4656 } else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004657 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004658 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004659 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004660 }
4661 }
4662 if (ep->d_name[0] == '.' &&
4663 (NAMLEN(ep) == 1 ||
4664 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
4665 continue;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004666 if (return_str)
Victor Stinnera45598a2010-05-14 16:35:39 +00004667 v = PyUnicode_DecodeFSDefaultAndSize(ep->d_name, NAMLEN(ep));
4668 else
4669 v = PyBytes_FromStringAndSize(ep->d_name, NAMLEN(ep));
Victor Stinner8c62be82010-05-06 00:08:46 +00004670 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004671 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004672 break;
4673 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004674 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004675 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004676 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004677 break;
4678 }
4679 Py_DECREF(v);
4680 }
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00004681
Larry Hastings9cf065c2012-06-22 16:30:09 -07004682exit:
4683 if (dirp != NULL) {
4684 Py_BEGIN_ALLOW_THREADS
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004685#ifdef HAVE_FDOPENDIR
Larry Hastings9cf065c2012-06-22 16:30:09 -07004686 if (fd > -1)
4687 rewinddir(dirp);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004688#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004689 closedir(dirp);
4690 Py_END_ALLOW_THREADS
4691 }
4692
Larry Hastings9cf065c2012-06-22 16:30:09 -07004693 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004694} /* end of _posix_listdir */
4695#endif /* which OS */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004696
Larry Hastings2f936352014-08-05 14:04:04 +10004697
4698/*[clinic input]
4699os.listdir
4700
4701 path : path_t(nullable=True, allow_fd='PATH_HAVE_FDOPENDIR') = None
4702
4703Return a list containing the names of the files in the directory.
4704
4705path can be specified as either str or bytes. If path is bytes,
4706 the filenames returned will also be bytes; in all other circumstances
4707 the filenames returned will be str.
4708If path is None, uses the path='.'.
4709On some platforms, path may also be specified as an open file descriptor;\
4710 the file descriptor must refer to a directory.
4711 If this functionality is unavailable, using it raises NotImplementedError.
4712
4713The list is in arbitrary order. It does not include the special
4714entries '.' and '..' even if they are present in the directory.
4715
4716
4717[clinic start generated code]*/
4718
4719PyDoc_STRVAR(os_listdir__doc__,
4720"listdir($module, /, path=None)\n"
4721"--\n"
4722"\n"
4723"Return a list containing the names of the files in the directory.\n"
4724"\n"
4725"path can be specified as either str or bytes. If path is bytes,\n"
4726" the filenames returned will also be bytes; in all other circumstances\n"
4727" the filenames returned will be str.\n"
4728"If path is None, uses the path=\'.\'.\n"
4729"On some platforms, path may also be specified as an open file descriptor;\\\n"
4730" the file descriptor must refer to a directory.\n"
4731" If this functionality is unavailable, using it raises NotImplementedError.\n"
4732"\n"
4733"The list is in arbitrary order. It does not include the special\n"
4734"entries \'.\' and \'..\' even if they are present in the directory.");
4735
4736#define OS_LISTDIR_METHODDEF \
4737 {"listdir", (PyCFunction)os_listdir, METH_VARARGS|METH_KEYWORDS, os_listdir__doc__},
4738
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004739static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004740os_listdir_impl(PyModuleDef *module, path_t *path);
4741
4742static PyObject *
4743os_listdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004744{
Larry Hastings2f936352014-08-05 14:04:04 +10004745 PyObject *return_value = NULL;
4746 static char *_keywords[] = {"path", NULL};
4747 path_t path = PATH_T_INITIALIZE("listdir", "path", 1, PATH_HAVE_FDOPENDIR);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004748
Larry Hastings2f936352014-08-05 14:04:04 +10004749 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4750 "|O&:listdir", _keywords,
4751 path_converter, &path))
4752 goto exit;
4753 return_value = os_listdir_impl(module, &path);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004754
Larry Hastings2f936352014-08-05 14:04:04 +10004755exit:
4756 /* Cleanup for path */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004757 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10004758
Gregory P. Smith40a21602013-03-20 20:52:50 -07004759 return return_value;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004760}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004761
Larry Hastings2f936352014-08-05 14:04:04 +10004762static PyObject *
4763os_listdir_impl(PyModuleDef *module, path_t *path)
4764/*[clinic end generated code: output=e159bd9be6909018 input=09e300416e3cd729]*/
4765{
4766#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
4767 return _listdir_windows_no_opendir(path, NULL);
4768#else
4769 return _posix_listdir(path, NULL);
4770#endif
4771}
4772
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00004773#ifdef MS_WINDOWS
Mark Hammondef8b6542001-05-13 08:04:26 +00004774/* A helper function for abspath on win32 */
Larry Hastings2f936352014-08-05 14:04:04 +10004775/* AC 3.5: probably just convert to using path converter */
Mark Hammondef8b6542001-05-13 08:04:26 +00004776static PyObject *
4777posix__getfullpathname(PyObject *self, PyObject *args)
4778{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004779 const char *path;
Victor Stinner75875072013-11-24 19:23:25 +01004780 char outbuf[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00004781 char *temp;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004782 PyObject *po;
4783
4784 if (PyArg_ParseTuple(args, "U|:_getfullpathname", &po))
4785 {
4786 wchar_t *wpath;
Victor Stinner75875072013-11-24 19:23:25 +01004787 wchar_t woutbuf[MAX_PATH], *woutbufp = woutbuf;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004788 wchar_t *wtemp;
Victor Stinner8c62be82010-05-06 00:08:46 +00004789 DWORD result;
4790 PyObject *v;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004791
4792 wpath = PyUnicode_AsUnicode(po);
4793 if (wpath == NULL)
4794 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004795 result = GetFullPathNameW(wpath,
Victor Stinner63941882011-09-29 00:42:28 +02004796 Py_ARRAY_LENGTH(woutbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004797 woutbuf, &wtemp);
Victor Stinner63941882011-09-29 00:42:28 +02004798 if (result > Py_ARRAY_LENGTH(woutbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004799 woutbufp = PyMem_Malloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004800 if (!woutbufp)
4801 return PyErr_NoMemory();
4802 result = GetFullPathNameW(wpath, result, woutbufp, &wtemp);
4803 }
4804 if (result)
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004805 v = PyUnicode_FromWideChar(woutbufp, wcslen(woutbufp));
Victor Stinner8c62be82010-05-06 00:08:46 +00004806 else
Victor Stinnereb5657a2011-09-30 01:44:27 +02004807 v = win32_error_object("GetFullPathNameW", po);
Victor Stinner8c62be82010-05-06 00:08:46 +00004808 if (woutbufp != woutbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004809 PyMem_Free(woutbufp);
Victor Stinner8c62be82010-05-06 00:08:46 +00004810 return v;
4811 }
4812 /* Drop the argument parsing error as narrow strings
4813 are also valid. */
4814 PyErr_Clear();
Victor Stinnereb5657a2011-09-30 01:44:27 +02004815
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004816 if (!PyArg_ParseTuple (args, "y:_getfullpathname",
4817 &path))
Victor Stinner8c62be82010-05-06 00:08:46 +00004818 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004819 if (win32_warn_bytes_api())
4820 return NULL;
Victor Stinner63941882011-09-29 00:42:28 +02004821 if (!GetFullPathName(path, Py_ARRAY_LENGTH(outbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004822 outbuf, &temp)) {
4823 win32_error("GetFullPathName", path);
Victor Stinner8c62be82010-05-06 00:08:46 +00004824 return NULL;
4825 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004826 if (PyUnicode_Check(PyTuple_GetItem(args, 0))) {
4827 return PyUnicode_Decode(outbuf, strlen(outbuf),
4828 Py_FileSystemDefaultEncoding, NULL);
4829 }
4830 return PyBytes_FromString(outbuf);
Larry Hastings2f936352014-08-05 14:04:04 +10004831}
Brian Curtind40e6f72010-07-08 21:39:08 +00004832
Brian Curtind25aef52011-06-13 15:16:04 -05004833
Larry Hastings2f936352014-08-05 14:04:04 +10004834/*[clinic input]
4835os._getfinalpathname
Brian Curtinf5e76d02010-11-24 13:14:05 +00004836
Larry Hastings2f936352014-08-05 14:04:04 +10004837 path: unicode
4838 /
4839
4840A helper function for samepath on windows.
4841[clinic start generated code]*/
4842
4843PyDoc_STRVAR(os__getfinalpathname__doc__,
4844"_getfinalpathname($module, path, /)\n"
4845"--\n"
4846"\n"
4847"A helper function for samepath on windows.");
4848
4849#define OS__GETFINALPATHNAME_METHODDEF \
4850 {"_getfinalpathname", (PyCFunction)os__getfinalpathname, METH_VARARGS, os__getfinalpathname__doc__},
4851
Brian Curtind40e6f72010-07-08 21:39:08 +00004852static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004853os__getfinalpathname_impl(PyModuleDef *module, PyObject *path);
4854
4855static PyObject *
4856os__getfinalpathname(PyModuleDef *module, PyObject *args)
4857{
4858 PyObject *return_value = NULL;
4859 PyObject *path;
4860
4861 if (!PyArg_ParseTuple(args,
4862 "U:_getfinalpathname",
4863 &path))
4864 goto exit;
4865 return_value = os__getfinalpathname_impl(module, path);
4866
4867exit:
4868 return return_value;
4869}
4870
4871static PyObject *
4872os__getfinalpathname_impl(PyModuleDef *module, PyObject *path)
4873/*[clinic end generated code: output=4563c6eacf1b0881 input=71d5e89334891bf4]*/
Brian Curtind40e6f72010-07-08 21:39:08 +00004874{
4875 HANDLE hFile;
4876 int buf_size;
4877 wchar_t *target_path;
4878 int result_length;
Larry Hastings2f936352014-08-05 14:04:04 +10004879 PyObject *result;
4880 wchar_t *path_wchar;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004881
Larry Hastings2f936352014-08-05 14:04:04 +10004882 path_wchar = PyUnicode_AsUnicode(path);
4883 if (path_wchar == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02004884 return NULL;
Brian Curtind40e6f72010-07-08 21:39:08 +00004885
4886 if(!check_GetFinalPathNameByHandle()) {
4887 /* If the OS doesn't have GetFinalPathNameByHandle, return a
4888 NotImplementedError. */
4889 return PyErr_Format(PyExc_NotImplementedError,
4890 "GetFinalPathNameByHandle not available on this platform");
4891 }
4892
4893 hFile = CreateFileW(
Larry Hastings2f936352014-08-05 14:04:04 +10004894 path_wchar,
Brian Curtind40e6f72010-07-08 21:39:08 +00004895 0, /* desired access */
4896 0, /* share mode */
4897 NULL, /* security attributes */
4898 OPEN_EXISTING,
4899 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
4900 FILE_FLAG_BACKUP_SEMANTICS,
4901 NULL);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004902
Victor Stinnereb5657a2011-09-30 01:44:27 +02004903 if(hFile == INVALID_HANDLE_VALUE)
Larry Hastings2f936352014-08-05 14:04:04 +10004904 return win32_error_object("CreateFileW", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004905
4906 /* We have a good handle to the target, use it to determine the
4907 target path name. */
4908 buf_size = Py_GetFinalPathNameByHandleW(hFile, 0, 0, VOLUME_NAME_NT);
4909
4910 if(!buf_size)
Larry Hastings2f936352014-08-05 14:04:04 +10004911 return win32_error_object("GetFinalPathNameByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004912
Victor Stinnerb6404912013-07-07 16:21:41 +02004913 target_path = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtind40e6f72010-07-08 21:39:08 +00004914 if(!target_path)
4915 return PyErr_NoMemory();
4916
4917 result_length = Py_GetFinalPathNameByHandleW(hFile, target_path,
4918 buf_size, VOLUME_NAME_DOS);
4919 if(!result_length)
Larry Hastings2f936352014-08-05 14:04:04 +10004920 return win32_error_object("GetFinalPathNamyByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004921
4922 if(!CloseHandle(hFile))
Larry Hastings2f936352014-08-05 14:04:04 +10004923 return win32_error_object("CloseHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004924
4925 target_path[result_length] = 0;
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004926 result = PyUnicode_FromWideChar(target_path, result_length);
Victor Stinnerb6404912013-07-07 16:21:41 +02004927 PyMem_Free(target_path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004928 return result;
Larry Hastings2f936352014-08-05 14:04:04 +10004929}
Brian Curtin62857742010-09-06 17:07:27 +00004930
Brian Curtin95d028f2011-06-09 09:10:38 -05004931PyDoc_STRVAR(posix__isdir__doc__,
4932"Return true if the pathname refers to an existing directory.");
4933
Larry Hastings2f936352014-08-05 14:04:04 +10004934/* AC 3.5: convert using path converter */
Brian Curtin9c669cc2011-06-08 18:17:18 -05004935static PyObject *
4936posix__isdir(PyObject *self, PyObject *args)
4937{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004938 const char *path;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004939 PyObject *po;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004940 DWORD attributes;
4941
4942 if (PyArg_ParseTuple(args, "U|:_isdir", &po)) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004943 wchar_t *wpath = PyUnicode_AsUnicode(po);
4944 if (wpath == NULL)
4945 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004946
4947 attributes = GetFileAttributesW(wpath);
4948 if (attributes == INVALID_FILE_ATTRIBUTES)
4949 Py_RETURN_FALSE;
4950 goto check;
4951 }
4952 /* Drop the argument parsing error as narrow strings
4953 are also valid. */
4954 PyErr_Clear();
4955
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004956 if (!PyArg_ParseTuple(args, "y:_isdir", &path))
Brian Curtin9c669cc2011-06-08 18:17:18 -05004957 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004958 if (win32_warn_bytes_api())
4959 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004960 attributes = GetFileAttributesA(path);
4961 if (attributes == INVALID_FILE_ATTRIBUTES)
4962 Py_RETURN_FALSE;
4963
4964check:
4965 if (attributes & FILE_ATTRIBUTE_DIRECTORY)
4966 Py_RETURN_TRUE;
4967 else
4968 Py_RETURN_FALSE;
4969}
Tim Golden6b528062013-08-01 12:44:00 +01004970
Tim Golden6b528062013-08-01 12:44:00 +01004971
Larry Hastings2f936352014-08-05 14:04:04 +10004972/*[clinic input]
4973os._getvolumepathname
4974
4975 path: unicode
4976
4977A helper function for ismount on Win32.
4978[clinic start generated code]*/
4979
4980PyDoc_STRVAR(os__getvolumepathname__doc__,
4981"_getvolumepathname($module, /, path)\n"
4982"--\n"
4983"\n"
4984"A helper function for ismount on Win32.");
4985
4986#define OS__GETVOLUMEPATHNAME_METHODDEF \
4987 {"_getvolumepathname", (PyCFunction)os__getvolumepathname, METH_VARARGS|METH_KEYWORDS, os__getvolumepathname__doc__},
4988
Tim Golden6b528062013-08-01 12:44:00 +01004989static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004990os__getvolumepathname_impl(PyModuleDef *module, PyObject *path);
4991
4992static PyObject *
4993os__getvolumepathname(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Tim Golden6b528062013-08-01 12:44:00 +01004994{
Larry Hastings2f936352014-08-05 14:04:04 +10004995 PyObject *return_value = NULL;
4996 static char *_keywords[] = {"path", NULL};
4997 PyObject *path;
4998
4999 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5000 "U:_getvolumepathname", _keywords,
5001 &path))
5002 goto exit;
5003 return_value = os__getvolumepathname_impl(module, path);
5004
5005exit:
5006 return return_value;
5007}
5008
5009static PyObject *
5010os__getvolumepathname_impl(PyModuleDef *module, PyObject *path)
5011/*[clinic end generated code: output=ac0833b6d6da7657 input=7eacadc40acbda6b]*/
5012{
5013 PyObject *result;
5014 wchar_t *path_wchar, *mountpath=NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01005015 size_t buflen;
Tim Golden6b528062013-08-01 12:44:00 +01005016 BOOL ret;
5017
Larry Hastings2f936352014-08-05 14:04:04 +10005018 path_wchar = PyUnicode_AsUnicodeAndSize(path, &buflen);
5019 if (path_wchar == NULL)
Tim Golden6b528062013-08-01 12:44:00 +01005020 return NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01005021 buflen += 1;
Tim Golden6b528062013-08-01 12:44:00 +01005022
5023 /* Volume path should be shorter than entire path */
Victor Stinner6edddfa2013-11-24 19:22:57 +01005024 buflen = Py_MAX(buflen, MAX_PATH);
5025
5026 if (buflen > DWORD_MAX) {
5027 PyErr_SetString(PyExc_OverflowError, "path too long");
5028 return NULL;
5029 }
5030
5031 mountpath = (wchar_t *)PyMem_Malloc(buflen * sizeof(wchar_t));
Tim Golden6b528062013-08-01 12:44:00 +01005032 if (mountpath == NULL)
5033 return PyErr_NoMemory();
5034
5035 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005036 ret = GetVolumePathNameW(path_wchar, mountpath,
Victor Stinner6edddfa2013-11-24 19:22:57 +01005037 Py_SAFE_DOWNCAST(buflen, size_t, DWORD));
Tim Golden6b528062013-08-01 12:44:00 +01005038 Py_END_ALLOW_THREADS
5039
5040 if (!ret) {
Larry Hastings2f936352014-08-05 14:04:04 +10005041 result = win32_error_object("_getvolumepathname", path);
Tim Golden6b528062013-08-01 12:44:00 +01005042 goto exit;
5043 }
5044 result = PyUnicode_FromWideChar(mountpath, wcslen(mountpath));
5045
5046exit:
5047 PyMem_Free(mountpath);
5048 return result;
5049}
Tim Golden6b528062013-08-01 12:44:00 +01005050
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00005051#endif /* MS_WINDOWS */
Mark Hammondef8b6542001-05-13 08:04:26 +00005052
Larry Hastings2f936352014-08-05 14:04:04 +10005053
5054/*[clinic input]
5055os.mkdir
5056
5057 path : path_t
5058
5059 mode: int = 0o777
5060
5061 *
5062
5063 dir_fd : dir_fd(requires='mkdirat') = None
5064
5065# "mkdir(path, mode=0o777, *, dir_fd=None)\n\n\
5066
5067Create a directory.
5068
5069If dir_fd is not None, it should be a file descriptor open to a directory,
5070 and path should be relative; path will then be relative to that directory.
5071dir_fd may not be implemented on your platform.
5072 If it is unavailable, using it will raise a NotImplementedError.
5073
5074The mode argument is ignored on Windows.
5075[clinic start generated code]*/
5076
5077PyDoc_STRVAR(os_mkdir__doc__,
5078"mkdir($module, /, path, mode=511, *, dir_fd=None)\n"
5079"--\n"
5080"\n"
5081"Create a directory.\n"
5082"\n"
5083"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5084" and path should be relative; path will then be relative to that directory.\n"
5085"dir_fd may not be implemented on your platform.\n"
5086" If it is unavailable, using it will raise a NotImplementedError.\n"
5087"\n"
5088"The mode argument is ignored on Windows.");
5089
5090#define OS_MKDIR_METHODDEF \
5091 {"mkdir", (PyCFunction)os_mkdir, METH_VARARGS|METH_KEYWORDS, os_mkdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005092
Barry Warsaw53699e91996-12-10 23:23:01 +00005093static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005094os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005095
Larry Hastings2f936352014-08-05 14:04:04 +10005096static PyObject *
5097os_mkdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5098{
5099 PyObject *return_value = NULL;
5100 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
5101 path_t path = PATH_T_INITIALIZE("mkdir", "path", 0, 0);
5102 int mode = 511;
5103 int dir_fd = DEFAULT_DIR_FD;
5104
5105 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5106 "O&|i$O&:mkdir", _keywords,
5107 path_converter, &path, &mode, MKDIRAT_DIR_FD_CONVERTER, &dir_fd))
5108 goto exit;
5109 return_value = os_mkdir_impl(module, &path, mode, dir_fd);
5110
5111exit:
5112 /* Cleanup for path */
5113 path_cleanup(&path);
5114
5115 return return_value;
5116}
5117
5118static PyObject *
5119os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
5120/*[clinic end generated code: output=55c6ef2bc1b207e6 input=e965f68377e9b1ce]*/
5121{
5122 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005123
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00005124#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005125 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005126 if (path->wide)
5127 result = CreateDirectoryW(path->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005128 else
Larry Hastings2f936352014-08-05 14:04:04 +10005129 result = CreateDirectoryA(path->narrow, NULL);
Victor Stinner8c62be82010-05-06 00:08:46 +00005130 Py_END_ALLOW_THREADS
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005131
Larry Hastings2f936352014-08-05 14:04:04 +10005132 if (!result)
5133 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005134#else
Victor Stinner8c62be82010-05-06 00:08:46 +00005135 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07005136#if HAVE_MKDIRAT
5137 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005138 result = mkdirat(dir_fd, path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005139 else
5140#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00005141#if ( defined(__WATCOMC__) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Larry Hastings2f936352014-08-05 14:04:04 +10005142 result = mkdir(path->narrow);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005143#else
Larry Hastings2f936352014-08-05 14:04:04 +10005144 result = mkdir(path->narrow, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005145#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005146 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005147 if (result < 0)
5148 return path_error(path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00005149#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005150 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005151}
5152
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005153
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005154/* sys/resource.h is needed for at least: wait3(), wait4(), broken nice. */
5155#if defined(HAVE_SYS_RESOURCE_H)
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005156#include <sys/resource.h>
5157#endif
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005158
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005159
5160#ifdef HAVE_NICE
Larry Hastings2f936352014-08-05 14:04:04 +10005161/*[clinic input]
5162os.nice
5163
5164 increment: int
5165 /
5166
5167Add increment to the priority of process and return the new priority.
5168[clinic start generated code]*/
5169
5170PyDoc_STRVAR(os_nice__doc__,
5171"nice($module, increment, /)\n"
5172"--\n"
5173"\n"
5174"Add increment to the priority of process and return the new priority.");
5175
5176#define OS_NICE_METHODDEF \
5177 {"nice", (PyCFunction)os_nice, METH_VARARGS, os_nice__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005178
Barry Warsaw53699e91996-12-10 23:23:01 +00005179static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005180os_nice_impl(PyModuleDef *module, int increment);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005181
Larry Hastings2f936352014-08-05 14:04:04 +10005182static PyObject *
5183os_nice(PyModuleDef *module, PyObject *args)
5184{
5185 PyObject *return_value = NULL;
5186 int increment;
5187
5188 if (!PyArg_ParseTuple(args,
5189 "i:nice",
5190 &increment))
5191 goto exit;
5192 return_value = os_nice_impl(module, increment);
5193
5194exit:
5195 return return_value;
5196}
5197
5198static PyObject *
5199os_nice_impl(PyModuleDef *module, int increment)
5200/*[clinic end generated code: output=c360dc2a3bd8e3d0 input=864be2d402a21da2]*/
5201{
5202 int value;
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005203
Victor Stinner8c62be82010-05-06 00:08:46 +00005204 /* There are two flavours of 'nice': one that returns the new
5205 priority (as required by almost all standards out there) and the
5206 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
5207 the use of getpriority() to get the new priority.
Tim Peters5aa91602002-01-30 05:46:57 +00005208
Victor Stinner8c62be82010-05-06 00:08:46 +00005209 If we are of the nice family that returns the new priority, we
5210 need to clear errno before the call, and check if errno is filled
5211 before calling posix_error() on a returnvalue of -1, because the
5212 -1 may be the actual new priority! */
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005213
Victor Stinner8c62be82010-05-06 00:08:46 +00005214 errno = 0;
5215 value = nice(increment);
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005216#if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005217 if (value == 0)
5218 value = getpriority(PRIO_PROCESS, 0);
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005219#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005220 if (value == -1 && errno != 0)
5221 /* either nice() or getpriority() returned an error */
5222 return posix_error();
5223 return PyLong_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005224}
Guido van Rossumb6775db1994-08-01 11:34:53 +00005225#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00005226
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005227
5228#ifdef HAVE_GETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005229/*[clinic input]
5230os.getpriority
5231
5232 which: int
5233 who: int
5234
5235Return program scheduling priority.
5236[clinic start generated code]*/
5237
5238PyDoc_STRVAR(os_getpriority__doc__,
5239"getpriority($module, /, which, who)\n"
5240"--\n"
5241"\n"
5242"Return program scheduling priority.");
5243
5244#define OS_GETPRIORITY_METHODDEF \
5245 {"getpriority", (PyCFunction)os_getpriority, METH_VARARGS|METH_KEYWORDS, os_getpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005246
5247static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005248os_getpriority_impl(PyModuleDef *module, int which, int who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005249
Larry Hastings2f936352014-08-05 14:04:04 +10005250static PyObject *
5251os_getpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5252{
5253 PyObject *return_value = NULL;
5254 static char *_keywords[] = {"which", "who", NULL};
5255 int which;
5256 int who;
5257
5258 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5259 "ii:getpriority", _keywords,
5260 &which, &who))
5261 goto exit;
5262 return_value = os_getpriority_impl(module, which, who);
5263
5264exit:
5265 return return_value;
5266}
5267
5268static PyObject *
5269os_getpriority_impl(PyModuleDef *module, int which, int who)
5270/*[clinic end generated code: output=81639cf765f05dae input=9be615d40e2544ef]*/
5271{
5272 int retval;
5273
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005274 errno = 0;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005275 retval = getpriority(which, who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005276 if (errno != 0)
5277 return posix_error();
5278 return PyLong_FromLong((long)retval);
5279}
5280#endif /* HAVE_GETPRIORITY */
5281
5282
5283#ifdef HAVE_SETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005284/*[clinic input]
5285os.setpriority
5286
5287 which: int
5288 who: int
5289 priority: int
5290
5291Set program scheduling priority.
5292[clinic start generated code]*/
5293
5294PyDoc_STRVAR(os_setpriority__doc__,
5295"setpriority($module, /, which, who, priority)\n"
5296"--\n"
5297"\n"
5298"Set program scheduling priority.");
5299
5300#define OS_SETPRIORITY_METHODDEF \
5301 {"setpriority", (PyCFunction)os_setpriority, METH_VARARGS|METH_KEYWORDS, os_setpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005302
5303static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005304os_setpriority_impl(PyModuleDef *module, int which, int who, int priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005305
Larry Hastings2f936352014-08-05 14:04:04 +10005306static PyObject *
5307os_setpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5308{
5309 PyObject *return_value = NULL;
5310 static char *_keywords[] = {"which", "who", "priority", NULL};
5311 int which;
5312 int who;
5313 int priority;
5314
5315 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5316 "iii:setpriority", _keywords,
5317 &which, &who, &priority))
5318 goto exit;
5319 return_value = os_setpriority_impl(module, which, who, priority);
5320
5321exit:
5322 return return_value;
5323}
5324
5325static PyObject *
5326os_setpriority_impl(PyModuleDef *module, int which, int who, int priority)
5327/*[clinic end generated code: output=ddad62651fb2120c input=710ccbf65b9dc513]*/
5328{
5329 int retval;
5330
5331 retval = setpriority(which, who, priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005332 if (retval == -1)
5333 return posix_error();
5334 Py_RETURN_NONE;
5335}
5336#endif /* HAVE_SETPRIORITY */
5337
5338
Barry Warsaw53699e91996-12-10 23:23:01 +00005339static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005340internal_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 +00005341{
Larry Hastings9cf065c2012-06-22 16:30:09 -07005342 char *function_name = is_replace ? "replace" : "rename";
Larry Hastings9cf065c2012-06-22 16:30:09 -07005343 int dir_fd_specified;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005344
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005345#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005346 BOOL result;
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005347 int flags = is_replace ? MOVEFILE_REPLACE_EXISTING : 0;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005348#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005349 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005350#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07005351
Larry Hastings9cf065c2012-06-22 16:30:09 -07005352 dir_fd_specified = (src_dir_fd != DEFAULT_DIR_FD) ||
5353 (dst_dir_fd != DEFAULT_DIR_FD);
5354#ifndef HAVE_RENAMEAT
5355 if (dir_fd_specified) {
5356 argument_unavailable_error(function_name, "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10005357 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005358 }
5359#endif
5360
Larry Hastings2f936352014-08-05 14:04:04 +10005361 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07005362 PyErr_Format(PyExc_ValueError,
5363 "%s: src and dst must be the same type", function_name);
Larry Hastings2f936352014-08-05 14:04:04 +10005364 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005365 }
5366
5367#ifdef MS_WINDOWS
5368 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005369 if (src->wide)
5370 result = MoveFileExW(src->wide, dst->wide, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005371 else
Larry Hastings2f936352014-08-05 14:04:04 +10005372 result = MoveFileExA(src->narrow, dst->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005373 Py_END_ALLOW_THREADS
5374
Larry Hastings2f936352014-08-05 14:04:04 +10005375 if (!result)
5376 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005377
5378#else
5379 Py_BEGIN_ALLOW_THREADS
5380#ifdef HAVE_RENAMEAT
5381 if (dir_fd_specified)
Larry Hastings2f936352014-08-05 14:04:04 +10005382 result = renameat(src_dir_fd, src->narrow, dst_dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005383 else
5384#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005385 result = rename(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005386 Py_END_ALLOW_THREADS
5387
Larry Hastings2f936352014-08-05 14:04:04 +10005388 if (result)
5389 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005390#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005391 Py_RETURN_NONE;
5392}
Larry Hastings9cf065c2012-06-22 16:30:09 -07005393
Larry Hastings2f936352014-08-05 14:04:04 +10005394
5395/*[clinic input]
5396os.rename
5397
5398 src : path_t
5399 dst : path_t
5400 *
5401 src_dir_fd : dir_fd = None
5402 dst_dir_fd : dir_fd = None
5403
5404Rename a file or directory.
5405
5406If either src_dir_fd or dst_dir_fd is not None, it should be a file
5407 descriptor open to a directory, and the respective path string (src or dst)
5408 should be relative; the path will then be relative to that directory.
5409src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5410 If they are unavailable, using them will raise a NotImplementedError.
5411[clinic start generated code]*/
5412
5413PyDoc_STRVAR(os_rename__doc__,
5414"rename($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5415"--\n"
5416"\n"
5417"Rename a file or directory.\n"
5418"\n"
5419"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5420" descriptor open to a directory, and the respective path string (src or dst)\n"
5421" should be relative; the path will then be relative to that directory.\n"
5422"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5423" If they are unavailable, using them will raise a NotImplementedError.");
5424
5425#define OS_RENAME_METHODDEF \
5426 {"rename", (PyCFunction)os_rename, METH_VARARGS|METH_KEYWORDS, os_rename__doc__},
5427
5428static PyObject *
5429os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd);
5430
5431static PyObject *
5432os_rename(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5433{
5434 PyObject *return_value = NULL;
5435 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5436 path_t src = PATH_T_INITIALIZE("rename", "src", 0, 0);
5437 path_t dst = PATH_T_INITIALIZE("rename", "dst", 0, 0);
5438 int src_dir_fd = DEFAULT_DIR_FD;
5439 int dst_dir_fd = DEFAULT_DIR_FD;
5440
5441 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5442 "O&O&|$O&O&:rename", _keywords,
5443 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5444 goto exit;
5445 return_value = os_rename_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5446
Larry Hastings9cf065c2012-06-22 16:30:09 -07005447exit:
Larry Hastings2f936352014-08-05 14:04:04 +10005448 /* Cleanup for src */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005449 path_cleanup(&src);
Larry Hastings2f936352014-08-05 14:04:04 +10005450 /* Cleanup for dst */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005451 path_cleanup(&dst);
Larry Hastings2f936352014-08-05 14:04:04 +10005452
Larry Hastings9cf065c2012-06-22 16:30:09 -07005453 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005454}
5455
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005456static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005457os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5458/*[clinic end generated code: output=c936bdc81f460a1e input=faa61c847912c850]*/
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005459{
Larry Hastings2f936352014-08-05 14:04:04 +10005460 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 0);
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005461}
5462
Larry Hastings2f936352014-08-05 14:04:04 +10005463
5464/*[clinic input]
5465os.replace = os.rename
5466
5467Rename a file or directory, overwriting the destination.
5468
5469If either src_dir_fd or dst_dir_fd is not None, it should be a file
5470 descriptor open to a directory, and the respective path string (src or dst)
5471 should be relative; the path will then be relative to that directory.
5472src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5473 If they are unavailable, using them will raise a NotImplementedError."
5474[clinic start generated code]*/
5475
5476PyDoc_STRVAR(os_replace__doc__,
5477"replace($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5478"--\n"
5479"\n"
5480"Rename a file or directory, overwriting the destination.\n"
5481"\n"
5482"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5483" descriptor open to a directory, and the respective path string (src or dst)\n"
5484" should be relative; the path will then be relative to that directory.\n"
5485"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5486" If they are unavailable, using them will raise a NotImplementedError.\"");
5487
5488#define OS_REPLACE_METHODDEF \
5489 {"replace", (PyCFunction)os_replace, METH_VARARGS|METH_KEYWORDS, os_replace__doc__},
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005490
5491static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005492os_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 +00005493
Barry Warsaw53699e91996-12-10 23:23:01 +00005494static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005495os_replace(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005496{
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005497 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10005498 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5499 path_t src = PATH_T_INITIALIZE("replace", "src", 0, 0);
5500 path_t dst = PATH_T_INITIALIZE("replace", "dst", 0, 0);
5501 int src_dir_fd = DEFAULT_DIR_FD;
5502 int dst_dir_fd = DEFAULT_DIR_FD;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005503
Larry Hastings2f936352014-08-05 14:04:04 +10005504 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5505 "O&O&|$O&O&:replace", _keywords,
5506 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5507 goto exit;
5508 return_value = os_replace_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5509
5510exit:
5511 /* Cleanup for src */
5512 path_cleanup(&src);
5513 /* Cleanup for dst */
5514 path_cleanup(&dst);
5515
5516 return return_value;
5517}
5518
5519static PyObject *
5520os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5521/*[clinic end generated code: output=224e4710d290d171 input=25515dfb107c8421]*/
5522{
5523 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 1);
5524}
5525
5526
5527/*[clinic input]
5528os.rmdir
5529
5530 path: path_t
5531 *
5532 dir_fd: dir_fd(requires='unlinkat') = None
5533
5534Remove a directory.
5535
5536If dir_fd is not None, it should be a file descriptor open to a directory,
5537 and path should be relative; path will then be relative to that directory.
5538dir_fd may not be implemented on your platform.
5539 If it is unavailable, using it will raise a NotImplementedError.
5540[clinic start generated code]*/
5541
5542PyDoc_STRVAR(os_rmdir__doc__,
5543"rmdir($module, /, path, *, dir_fd=None)\n"
5544"--\n"
5545"\n"
5546"Remove a directory.\n"
5547"\n"
5548"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5549" and path should be relative; path will then be relative to that directory.\n"
5550"dir_fd may not be implemented on your platform.\n"
5551" If it is unavailable, using it will raise a NotImplementedError.");
5552
5553#define OS_RMDIR_METHODDEF \
5554 {"rmdir", (PyCFunction)os_rmdir, METH_VARARGS|METH_KEYWORDS, os_rmdir__doc__},
5555
5556static PyObject *
5557os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd);
5558
5559static PyObject *
5560os_rmdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5561{
5562 PyObject *return_value = NULL;
5563 static char *_keywords[] = {"path", "dir_fd", NULL};
5564 path_t path = PATH_T_INITIALIZE("rmdir", "path", 0, 0);
5565 int dir_fd = DEFAULT_DIR_FD;
5566
5567 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5568 "O&|$O&:rmdir", _keywords,
5569 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5570 goto exit;
5571 return_value = os_rmdir_impl(module, &path, dir_fd);
5572
5573exit:
5574 /* Cleanup for path */
5575 path_cleanup(&path);
5576
5577 return return_value;
5578}
5579
5580static PyObject *
5581os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd)
5582/*[clinic end generated code: output=70b9fdbe3bee0591 input=38c8b375ca34a7e2]*/
5583{
5584 int result;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005585
5586 Py_BEGIN_ALLOW_THREADS
5587#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005588 if (path->wide)
5589 result = RemoveDirectoryW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005590 else
Larry Hastings2f936352014-08-05 14:04:04 +10005591 result = RemoveDirectoryA(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005592 result = !result; /* Windows, success=1, UNIX, success=0 */
5593#else
5594#ifdef HAVE_UNLINKAT
5595 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005596 result = unlinkat(dir_fd, path->narrow, AT_REMOVEDIR);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005597 else
5598#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005599 result = rmdir(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005600#endif
5601 Py_END_ALLOW_THREADS
5602
Larry Hastings2f936352014-08-05 14:04:04 +10005603 if (result)
5604 return path_error(path);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005605
Larry Hastings2f936352014-08-05 14:04:04 +10005606 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005607}
5608
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005609
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005610#ifdef HAVE_SYSTEM
Larry Hastings2f936352014-08-05 14:04:04 +10005611#ifdef MS_WINDOWS
5612/*[clinic input]
5613os.system -> long
5614
5615 command: Py_UNICODE
5616
5617Execute the command in a subshell.
5618[clinic start generated code]*/
5619
5620PyDoc_STRVAR(os_system__doc__,
5621"system($module, /, command)\n"
5622"--\n"
5623"\n"
5624"Execute the command in a subshell.");
5625
5626#define OS_SYSTEM_METHODDEF \
5627 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5628
5629static long
5630os_system_impl(PyModuleDef *module, Py_UNICODE *command);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005631
Barry Warsaw53699e91996-12-10 23:23:01 +00005632static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005633os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005634{
Larry Hastings2f936352014-08-05 14:04:04 +10005635 PyObject *return_value = NULL;
5636 static char *_keywords[] = {"command", NULL};
5637 Py_UNICODE *command;
5638 long _return_value;
Victor Stinnercfa72782010-04-16 11:45:13 +00005639
Larry Hastings2f936352014-08-05 14:04:04 +10005640 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5641 "u:system", _keywords,
5642 &command))
5643 goto exit;
5644 _return_value = os_system_impl(module, command);
5645 if ((_return_value == -1) && PyErr_Occurred())
5646 goto exit;
5647 return_value = PyLong_FromLong(_return_value);
Victor Stinnercfa72782010-04-16 11:45:13 +00005648
Larry Hastings2f936352014-08-05 14:04:04 +10005649exit:
5650 return return_value;
5651}
5652
5653static long
5654os_system_impl(PyModuleDef *module, Py_UNICODE *command)
5655/*[clinic end generated code: output=29fe699c0b2e9d38 input=303f5ce97df606b0]*/
5656{
5657 long result;
Victor Stinner8c62be82010-05-06 00:08:46 +00005658 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005659 result = _wsystem(command);
Victor Stinner8c62be82010-05-06 00:08:46 +00005660 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005661 return result;
5662}
5663#else /* MS_WINDOWS */
5664/*[clinic input]
5665os.system -> long
5666
5667 command: FSConverter
5668
5669Execute the command in a subshell.
5670[clinic start generated code]*/
5671
5672PyDoc_STRVAR(os_system__doc__,
5673"system($module, /, command)\n"
5674"--\n"
5675"\n"
5676"Execute the command in a subshell.");
5677
5678#define OS_SYSTEM_METHODDEF \
5679 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5680
5681static long
5682os_system_impl(PyModuleDef *module, PyObject *command);
5683
5684static PyObject *
5685os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5686{
5687 PyObject *return_value = NULL;
5688 static char *_keywords[] = {"command", NULL};
5689 PyObject *command = NULL;
5690 long _return_value;
5691
5692 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5693 "O&:system", _keywords,
5694 PyUnicode_FSConverter, &command))
5695 goto exit;
5696 _return_value = os_system_impl(module, command);
5697 if ((_return_value == -1) && PyErr_Occurred())
5698 goto exit;
5699 return_value = PyLong_FromLong(_return_value);
5700
5701exit:
5702 /* Cleanup for command */
5703 Py_XDECREF(command);
5704
5705 return return_value;
5706}
5707
5708static long
5709os_system_impl(PyModuleDef *module, PyObject *command)
5710/*[clinic end generated code: output=5be9f3c40ead3bad input=86a58554ba6094af]*/
5711{
5712 long result;
5713 char *bytes = PyBytes_AsString(command);
5714 Py_BEGIN_ALLOW_THREADS
5715 result = system(bytes);
5716 Py_END_ALLOW_THREADS
5717 return result;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005718}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005719#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005720#endif /* HAVE_SYSTEM */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005721
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005722
Larry Hastings2f936352014-08-05 14:04:04 +10005723/*[clinic input]
5724os.umask
5725
5726 mask: int
5727 /
5728
5729Set the current numeric umask and return the previous umask.
5730[clinic start generated code]*/
5731
5732PyDoc_STRVAR(os_umask__doc__,
5733"umask($module, mask, /)\n"
5734"--\n"
5735"\n"
5736"Set the current numeric umask and return the previous umask.");
5737
5738#define OS_UMASK_METHODDEF \
5739 {"umask", (PyCFunction)os_umask, METH_VARARGS, os_umask__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005740
Barry Warsaw53699e91996-12-10 23:23:01 +00005741static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005742os_umask_impl(PyModuleDef *module, int mask);
5743
5744static PyObject *
5745os_umask(PyModuleDef *module, PyObject *args)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005746{
Larry Hastings2f936352014-08-05 14:04:04 +10005747 PyObject *return_value = NULL;
5748 int mask;
5749
5750 if (!PyArg_ParseTuple(args,
5751 "i:umask",
5752 &mask))
5753 goto exit;
5754 return_value = os_umask_impl(module, mask);
5755
5756exit:
5757 return return_value;
5758}
5759
5760static PyObject *
5761os_umask_impl(PyModuleDef *module, int mask)
5762/*[clinic end generated code: output=90048b39d2d4a961 input=ab6bfd9b24d8a7e8]*/
5763{
5764 int i = (int)umask(mask);
Victor Stinner8c62be82010-05-06 00:08:46 +00005765 if (i < 0)
5766 return posix_error();
5767 return PyLong_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005768}
5769
Brian Curtind40e6f72010-07-08 21:39:08 +00005770#ifdef MS_WINDOWS
5771
5772/* override the default DeleteFileW behavior so that directory
5773symlinks can be removed with this function, the same as with
5774Unix symlinks */
5775BOOL WINAPI Py_DeleteFileW(LPCWSTR lpFileName)
5776{
5777 WIN32_FILE_ATTRIBUTE_DATA info;
5778 WIN32_FIND_DATAW find_data;
5779 HANDLE find_data_handle;
5780 int is_directory = 0;
5781 int is_link = 0;
5782
5783 if (GetFileAttributesExW(lpFileName, GetFileExInfoStandard, &info)) {
5784 is_directory = info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00005785
Brian Curtind40e6f72010-07-08 21:39:08 +00005786 /* Get WIN32_FIND_DATA structure for the path to determine if
5787 it is a symlink */
5788 if(is_directory &&
5789 info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
5790 find_data_handle = FindFirstFileW(lpFileName, &find_data);
5791
5792 if(find_data_handle != INVALID_HANDLE_VALUE) {
Tim Golden0321cf22014-05-05 19:46:17 +01005793 /* IO_REPARSE_TAG_SYMLINK if it is a symlink and
5794 IO_REPARSE_TAG_MOUNT_POINT if it is a junction point. */
5795 is_link = find_data.dwReserved0 == IO_REPARSE_TAG_SYMLINK ||
5796 find_data.dwReserved0 == IO_REPARSE_TAG_MOUNT_POINT;
Brian Curtind40e6f72010-07-08 21:39:08 +00005797 FindClose(find_data_handle);
5798 }
5799 }
5800 }
5801
5802 if (is_directory && is_link)
5803 return RemoveDirectoryW(lpFileName);
5804
5805 return DeleteFileW(lpFileName);
5806}
5807#endif /* MS_WINDOWS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005808
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005809
Larry Hastings2f936352014-08-05 14:04:04 +10005810/*[clinic input]
5811os.unlink
5812
5813 path: path_t
5814 *
5815 dir_fd: dir_fd(requires='unlinkat')=None
5816
5817Remove a file (same as remove()).
5818
5819If dir_fd is not None, it should be a file descriptor open to a directory,
5820 and path should be relative; path will then be relative to that directory.
5821dir_fd may not be implemented on your platform.
5822 If it is unavailable, using it will raise a NotImplementedError.
5823
5824[clinic start generated code]*/
5825
5826PyDoc_STRVAR(os_unlink__doc__,
5827"unlink($module, /, path, *, dir_fd=None)\n"
5828"--\n"
5829"\n"
5830"Remove a file (same as remove()).\n"
5831"\n"
5832"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5833" and path should be relative; path will then be relative to that directory.\n"
5834"dir_fd may not be implemented on your platform.\n"
5835" If it is unavailable, using it will raise a NotImplementedError.");
5836
5837#define OS_UNLINK_METHODDEF \
5838 {"unlink", (PyCFunction)os_unlink, METH_VARARGS|METH_KEYWORDS, os_unlink__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005839
Barry Warsaw53699e91996-12-10 23:23:01 +00005840static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005841os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005842
Larry Hastings2f936352014-08-05 14:04:04 +10005843static PyObject *
5844os_unlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5845{
5846 PyObject *return_value = NULL;
5847 static char *_keywords[] = {"path", "dir_fd", NULL};
5848 path_t path = PATH_T_INITIALIZE("unlink", "path", 0, 0);
5849 int dir_fd = DEFAULT_DIR_FD;
5850
5851 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5852 "O&|$O&:unlink", _keywords,
5853 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5854 goto exit;
5855 return_value = os_unlink_impl(module, &path, dir_fd);
5856
5857exit:
5858 /* Cleanup for path */
5859 path_cleanup(&path);
5860
5861 return return_value;
5862}
5863
5864static PyObject *
5865os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd)
5866/*[clinic end generated code: output=59a6e66d67ff2e75 input=d7bcde2b1b2a2552]*/
5867{
5868 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005869
5870 Py_BEGIN_ALLOW_THREADS
5871#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005872 if (path->wide)
5873 result = Py_DeleteFileW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005874 else
Larry Hastings2f936352014-08-05 14:04:04 +10005875 result = DeleteFileA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005876 result = !result; /* Windows, success=1, UNIX, success=0 */
5877#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005878#ifdef HAVE_UNLINKAT
5879 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005880 result = unlinkat(dir_fd, path->narrow, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005881 else
5882#endif /* HAVE_UNLINKAT */
Larry Hastings2f936352014-08-05 14:04:04 +10005883 result = unlink(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005884#endif
5885 Py_END_ALLOW_THREADS
5886
Larry Hastings2f936352014-08-05 14:04:04 +10005887 if (result)
5888 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005889
Larry Hastings2f936352014-08-05 14:04:04 +10005890 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005891}
5892
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005893
Larry Hastings2f936352014-08-05 14:04:04 +10005894/*[clinic input]
5895os.remove = os.unlink
5896
5897Remove a file (same as unlink()).
5898
5899If dir_fd is not None, it should be a file descriptor open to a directory,
5900 and path should be relative; path will then be relative to that directory.
5901dir_fd may not be implemented on your platform.
5902 If it is unavailable, using it will raise a NotImplementedError.
5903[clinic start generated code]*/
5904
5905PyDoc_STRVAR(os_remove__doc__,
5906"remove($module, /, path, *, dir_fd=None)\n"
5907"--\n"
5908"\n"
5909"Remove a file (same as unlink()).\n"
5910"\n"
5911"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5912" and path should be relative; path will then be relative to that directory.\n"
5913"dir_fd may not be implemented on your platform.\n"
5914" If it is unavailable, using it will raise a NotImplementedError.");
5915
5916#define OS_REMOVE_METHODDEF \
5917 {"remove", (PyCFunction)os_remove, METH_VARARGS|METH_KEYWORDS, os_remove__doc__},
5918
5919static PyObject *
5920os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd);
5921
5922static PyObject *
5923os_remove(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5924{
5925 PyObject *return_value = NULL;
5926 static char *_keywords[] = {"path", "dir_fd", NULL};
5927 path_t path = PATH_T_INITIALIZE("remove", "path", 0, 0);
5928 int dir_fd = DEFAULT_DIR_FD;
5929
5930 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5931 "O&|$O&:remove", _keywords,
5932 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5933 goto exit;
5934 return_value = os_remove_impl(module, &path, dir_fd);
5935
5936exit:
5937 /* Cleanup for path */
5938 path_cleanup(&path);
5939
5940 return return_value;
5941}
5942
5943static PyObject *
5944os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd)
5945/*[clinic end generated code: output=cb170cf1e195b8ed input=e05c5ab55cd30983]*/
5946{
5947 return os_unlink_impl(module, path, dir_fd);
5948}
5949
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005950
Larry Hastings605a62d2012-06-24 04:33:36 -07005951static PyStructSequence_Field uname_result_fields[] = {
5952 {"sysname", "operating system name"},
5953 {"nodename", "name of machine on network (implementation-defined)"},
5954 {"release", "operating system release"},
5955 {"version", "operating system version"},
5956 {"machine", "hardware identifier"},
5957 {NULL}
5958};
5959
5960PyDoc_STRVAR(uname_result__doc__,
5961"uname_result: Result from os.uname().\n\n\
5962This object may be accessed either as a tuple of\n\
5963 (sysname, nodename, release, version, machine),\n\
5964or via the attributes sysname, nodename, release, version, and machine.\n\
5965\n\
5966See os.uname for more information.");
5967
5968static PyStructSequence_Desc uname_result_desc = {
5969 "uname_result", /* name */
5970 uname_result__doc__, /* doc */
5971 uname_result_fields,
5972 5
5973};
5974
5975static PyTypeObject UnameResultType;
5976
5977
5978#ifdef HAVE_UNAME
Larry Hastings2f936352014-08-05 14:04:04 +10005979/*[clinic input]
5980os.uname
5981
5982Return an object identifying the current operating system.
5983
5984The object behaves like a named tuple with the following fields:
5985 (sysname, nodename, release, version, machine)
5986
5987[clinic start generated code]*/
5988
5989PyDoc_STRVAR(os_uname__doc__,
5990"uname($module, /)\n"
5991"--\n"
5992"\n"
5993"Return an object identifying the current operating system.\n"
5994"\n"
5995"The object behaves like a named tuple with the following fields:\n"
5996" (sysname, nodename, release, version, machine)");
5997
5998#define OS_UNAME_METHODDEF \
5999 {"uname", (PyCFunction)os_uname, METH_NOARGS, os_uname__doc__},
6000
Barry Warsaw53699e91996-12-10 23:23:01 +00006001static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006002os_uname_impl(PyModuleDef *module);
6003
6004static PyObject *
6005os_uname(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
6006{
6007 return os_uname_impl(module);
6008}
6009
6010static PyObject *
6011os_uname_impl(PyModuleDef *module)
6012/*[clinic end generated code: output=459a86521ff5041c input=e68bd246db3043ed]*/
Guido van Rossumc39de5f1992-02-05 11:15:54 +00006013{
Victor Stinner8c62be82010-05-06 00:08:46 +00006014 struct utsname u;
6015 int res;
Larry Hastings605a62d2012-06-24 04:33:36 -07006016 PyObject *value;
Neal Norwitze241ce82003-02-17 18:17:05 +00006017
Victor Stinner8c62be82010-05-06 00:08:46 +00006018 Py_BEGIN_ALLOW_THREADS
6019 res = uname(&u);
6020 Py_END_ALLOW_THREADS
6021 if (res < 0)
6022 return posix_error();
Larry Hastings605a62d2012-06-24 04:33:36 -07006023
6024 value = PyStructSequence_New(&UnameResultType);
6025 if (value == NULL)
6026 return NULL;
6027
6028#define SET(i, field) \
6029 { \
Victor Stinnera534fc42013-06-03 22:07:27 +02006030 PyObject *o = PyUnicode_DecodeFSDefault(field); \
Larry Hastings605a62d2012-06-24 04:33:36 -07006031 if (!o) { \
6032 Py_DECREF(value); \
6033 return NULL; \
6034 } \
6035 PyStructSequence_SET_ITEM(value, i, o); \
6036 } \
6037
6038 SET(0, u.sysname);
6039 SET(1, u.nodename);
6040 SET(2, u.release);
6041 SET(3, u.version);
6042 SET(4, u.machine);
6043
6044#undef SET
6045
6046 return value;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00006047}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006048#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006049
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006050
Larry Hastings9cf065c2012-06-22 16:30:09 -07006051
6052typedef struct {
6053 int now;
6054 time_t atime_s;
6055 long atime_ns;
6056 time_t mtime_s;
6057 long mtime_ns;
6058} utime_t;
6059
6060/*
Victor Stinner484df002014-10-09 13:52:31 +02006061 * these macros assume that "ut" is a pointer to a utime_t
Larry Hastings9cf065c2012-06-22 16:30:09 -07006062 * they also intentionally leak the declaration of a pointer named "time"
6063 */
6064#define UTIME_TO_TIMESPEC \
6065 struct timespec ts[2]; \
6066 struct timespec *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006067 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006068 time = NULL; \
6069 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006070 ts[0].tv_sec = ut->atime_s; \
6071 ts[0].tv_nsec = ut->atime_ns; \
6072 ts[1].tv_sec = ut->mtime_s; \
6073 ts[1].tv_nsec = ut->mtime_ns; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006074 time = ts; \
6075 } \
6076
6077#define UTIME_TO_TIMEVAL \
6078 struct timeval tv[2]; \
6079 struct timeval *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006080 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006081 time = NULL; \
6082 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006083 tv[0].tv_sec = ut->atime_s; \
6084 tv[0].tv_usec = ut->atime_ns / 1000; \
6085 tv[1].tv_sec = ut->mtime_s; \
6086 tv[1].tv_usec = ut->mtime_ns / 1000; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006087 time = tv; \
6088 } \
6089
6090#define UTIME_TO_UTIMBUF \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006091 struct utimbuf u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006092 struct utimbuf *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006093 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006094 time = NULL; \
6095 else { \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006096 u.actime = ut->atime_s; \
6097 u.modtime = ut->mtime_s; \
6098 time = &u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006099 }
6100
6101#define UTIME_TO_TIME_T \
6102 time_t timet[2]; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006103 time_t *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006104 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006105 time = NULL; \
6106 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006107 timet[0] = ut->atime_s; \
6108 timet[1] = ut->mtime_s; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006109 time = timet; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006110 } \
6111
6112
6113#define UTIME_HAVE_DIR_FD (defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT))
6114
6115#if UTIME_HAVE_DIR_FD
6116
6117static int
Victor Stinner484df002014-10-09 13:52:31 +02006118utime_dir_fd(utime_t *ut, int dir_fd, char *path, int follow_symlinks)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006119{
6120#ifdef HAVE_UTIMENSAT
6121 int flags = follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW;
6122 UTIME_TO_TIMESPEC;
6123 return utimensat(dir_fd, path, time, flags);
6124#elif defined(HAVE_FUTIMESAT)
6125 UTIME_TO_TIMEVAL;
6126 /*
6127 * follow_symlinks will never be false here;
6128 * we only allow !follow_symlinks and dir_fd together
6129 * if we have utimensat()
6130 */
6131 assert(follow_symlinks);
6132 return futimesat(dir_fd, path, time);
6133#endif
6134}
6135
Larry Hastings2f936352014-08-05 14:04:04 +10006136 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_converter
6137#else
6138 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings9cf065c2012-06-22 16:30:09 -07006139#endif
6140
6141#define UTIME_HAVE_FD (defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS))
6142
6143#if UTIME_HAVE_FD
6144
6145static int
Victor Stinner484df002014-10-09 13:52:31 +02006146utime_fd(utime_t *ut, int fd)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006147{
6148#ifdef HAVE_FUTIMENS
6149 UTIME_TO_TIMESPEC;
6150 return futimens(fd, time);
6151#else
6152 UTIME_TO_TIMEVAL;
6153 return futimes(fd, time);
6154#endif
6155}
6156
Larry Hastings2f936352014-08-05 14:04:04 +10006157 #define PATH_UTIME_HAVE_FD 1
6158#else
6159 #define PATH_UTIME_HAVE_FD 0
Larry Hastings9cf065c2012-06-22 16:30:09 -07006160#endif
6161
6162
6163#define UTIME_HAVE_NOFOLLOW_SYMLINKS \
6164 (defined(HAVE_UTIMENSAT) || defined(HAVE_LUTIMES))
6165
6166#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6167
6168static int
Victor Stinner484df002014-10-09 13:52:31 +02006169utime_nofollow_symlinks(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006170{
6171#ifdef HAVE_UTIMENSAT
6172 UTIME_TO_TIMESPEC;
6173 return utimensat(DEFAULT_DIR_FD, path, time, AT_SYMLINK_NOFOLLOW);
6174#else
6175 UTIME_TO_TIMEVAL;
6176 return lutimes(path, time);
6177#endif
6178}
6179
6180#endif
6181
6182#ifndef MS_WINDOWS
6183
6184static int
Victor Stinner484df002014-10-09 13:52:31 +02006185utime_default(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006186{
6187#ifdef HAVE_UTIMENSAT
6188 UTIME_TO_TIMESPEC;
6189 return utimensat(DEFAULT_DIR_FD, path, time, 0);
6190#elif defined(HAVE_UTIMES)
6191 UTIME_TO_TIMEVAL;
6192 return utimes(path, time);
6193#elif defined(HAVE_UTIME_H)
6194 UTIME_TO_UTIMBUF;
6195 return utime(path, time);
6196#else
6197 UTIME_TO_TIME_T;
6198 return utime(path, time);
6199#endif
6200}
6201
6202#endif
6203
Larry Hastings76ad59b2012-05-03 00:30:07 -07006204static int
6205split_py_long_to_s_and_ns(PyObject *py_long, time_t *s, long *ns)
6206{
6207 int result = 0;
Benjamin Petersonfbd85a02012-05-04 11:06:09 -04006208 PyObject *divmod;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006209 divmod = PyNumber_Divmod(py_long, billion);
6210 if (!divmod)
6211 goto exit;
6212 *s = _PyLong_AsTime_t(PyTuple_GET_ITEM(divmod, 0));
6213 if ((*s == -1) && PyErr_Occurred())
6214 goto exit;
6215 *ns = PyLong_AsLong(PyTuple_GET_ITEM(divmod, 1));
Benjamin Peterson35a8f0d2012-05-04 01:10:59 -04006216 if ((*ns == -1) && PyErr_Occurred())
Larry Hastings76ad59b2012-05-03 00:30:07 -07006217 goto exit;
6218
6219 result = 1;
6220exit:
6221 Py_XDECREF(divmod);
6222 return result;
6223}
6224
Larry Hastings2f936352014-08-05 14:04:04 +10006225
6226/*[clinic input]
6227os.utime
6228
6229 path: path_t(allow_fd='PATH_UTIME_HAVE_FD')
6230 times: object = NULL
6231 *
6232 ns: object = NULL
6233 dir_fd: dir_fd(requires='futimensat') = None
6234 follow_symlinks: bool=True
6235
6236# "utime(path, times=None, *, ns=None, dir_fd=None, follow_symlinks=True)\n\
6237
6238Set the access and modified time of path.
6239
6240path may always be specified as a string.
6241On some platforms, path may also be specified as an open file descriptor.
6242 If this functionality is unavailable, using it raises an exception.
6243
6244If times is not None, it must be a tuple (atime, mtime);
6245 atime and mtime should be expressed as float seconds since the epoch.
6246If ns is not None, it must be a tuple (atime_ns, mtime_ns);
6247 atime_ns and mtime_ns should be expressed as integer nanoseconds
6248 since the epoch.
6249If both times and ns are None, utime uses the current time.
6250Specifying tuples for both times and ns is an error.
6251
6252If dir_fd is not None, it should be a file descriptor open to a directory,
6253 and path should be relative; path will then be relative to that directory.
6254If follow_symlinks is False, and the last element of the path is a symbolic
6255 link, utime will modify the symbolic link itself instead of the file the
6256 link points to.
6257It is an error to use dir_fd or follow_symlinks when specifying path
6258 as an open file descriptor.
6259dir_fd and follow_symlinks may not be available on your platform.
6260 If they are unavailable, using them will raise a NotImplementedError.
6261
6262[clinic start generated code]*/
6263
6264PyDoc_STRVAR(os_utime__doc__,
6265"utime($module, /, path, times=None, *, ns=None, dir_fd=None,\n"
6266" follow_symlinks=True)\n"
6267"--\n"
6268"\n"
6269"Set the access and modified time of path.\n"
6270"\n"
6271"path may always be specified as a string.\n"
6272"On some platforms, path may also be specified as an open file descriptor.\n"
6273" If this functionality is unavailable, using it raises an exception.\n"
6274"\n"
6275"If times is not None, it must be a tuple (atime, mtime);\n"
6276" atime and mtime should be expressed as float seconds since the epoch.\n"
6277"If ns is not None, it must be a tuple (atime_ns, mtime_ns);\n"
6278" atime_ns and mtime_ns should be expressed as integer nanoseconds\n"
6279" since the epoch.\n"
6280"If both times and ns are None, utime uses the current time.\n"
6281"Specifying tuples for both times and ns is an error.\n"
6282"\n"
6283"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
6284" and path should be relative; path will then be relative to that directory.\n"
6285"If follow_symlinks is False, and the last element of the path is a symbolic\n"
6286" link, utime will modify the symbolic link itself instead of the file the\n"
6287" link points to.\n"
6288"It is an error to use dir_fd or follow_symlinks when specifying path\n"
6289" as an open file descriptor.\n"
6290"dir_fd and follow_symlinks may not be available on your platform.\n"
6291" If they are unavailable, using them will raise a NotImplementedError.");
6292
6293#define OS_UTIME_METHODDEF \
6294 {"utime", (PyCFunction)os_utime, METH_VARARGS|METH_KEYWORDS, os_utime__doc__},
6295
Larry Hastings9cf065c2012-06-22 16:30:09 -07006296static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006297os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks);
6298
6299static PyObject *
6300os_utime(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings76ad59b2012-05-03 00:30:07 -07006301{
Larry Hastings2f936352014-08-05 14:04:04 +10006302 PyObject *return_value = NULL;
6303 static char *_keywords[] = {"path", "times", "ns", "dir_fd", "follow_symlinks", NULL};
6304 path_t path = PATH_T_INITIALIZE("utime", "path", 0, PATH_UTIME_HAVE_FD);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006305 PyObject *times = NULL;
6306 PyObject *ns = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07006307 int dir_fd = DEFAULT_DIR_FD;
6308 int follow_symlinks = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006309
Larry Hastings2f936352014-08-05 14:04:04 +10006310 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6311 "O&|O$OO&p:utime", _keywords,
6312 path_converter, &path, &times, &ns, FUTIMENSAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
6313 goto exit;
6314 return_value = os_utime_impl(module, &path, times, ns, dir_fd, follow_symlinks);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006315
Larry Hastings2f936352014-08-05 14:04:04 +10006316exit:
6317 /* Cleanup for path */
6318 path_cleanup(&path);
6319
6320 return return_value;
6321}
6322
6323static PyObject *
6324os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks)
6325/*[clinic end generated code: output=891489c35cc68c5d input=1f18c17d5941aa82]*/
6326{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006327#ifdef MS_WINDOWS
6328 HANDLE hFile;
6329 FILETIME atime, mtime;
6330#else
6331 int result;
6332#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006333
Larry Hastings9cf065c2012-06-22 16:30:09 -07006334 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10006335 utime_t utime;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006336
Christian Heimesb3c87242013-08-01 00:08:16 +02006337 memset(&utime, 0, sizeof(utime_t));
Larry Hastings76ad59b2012-05-03 00:30:07 -07006338
Larry Hastings9cf065c2012-06-22 16:30:09 -07006339 if (times && (times != Py_None) && ns) {
6340 PyErr_SetString(PyExc_ValueError,
6341 "utime: you may specify either 'times'"
6342 " or 'ns' but not both");
6343 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006344 }
6345
6346 if (times && (times != Py_None)) {
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006347 time_t a_sec, m_sec;
6348 long a_nsec, m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006349 if (!PyTuple_CheckExact(times) || (PyTuple_Size(times) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006350 PyErr_SetString(PyExc_TypeError,
6351 "utime: 'times' must be either"
6352 " a tuple of two ints or None");
6353 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006354 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006355 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006356 if (_PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 0),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006357 &a_sec, &a_nsec, _PyTime_ROUND_DOWN) == -1 ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006358 _PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 1),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006359 &m_sec, &m_nsec, _PyTime_ROUND_DOWN) == -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006360 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006361 }
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006362 utime.atime_s = a_sec;
6363 utime.atime_ns = a_nsec;
6364 utime.mtime_s = m_sec;
6365 utime.mtime_ns = m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006366 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006367 else if (ns) {
Larry Hastings76ad59b2012-05-03 00:30:07 -07006368 if (!PyTuple_CheckExact(ns) || (PyTuple_Size(ns) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006369 PyErr_SetString(PyExc_TypeError,
6370 "utime: 'ns' must be a tuple of two ints");
6371 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006372 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006373 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006374 if (!split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 0),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006375 &utime.atime_s, &utime.atime_ns) ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006376 !split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 1),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006377 &utime.mtime_s, &utime.mtime_ns)) {
6378 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006379 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006380 }
6381 else {
6382 /* times and ns are both None/unspecified. use "now". */
6383 utime.now = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006384 }
6385
Larry Hastings9cf065c2012-06-22 16:30:09 -07006386#if !UTIME_HAVE_NOFOLLOW_SYMLINKS
6387 if (follow_symlinks_specified("utime", follow_symlinks))
6388 goto exit;
6389#endif
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006390
Larry Hastings2f936352014-08-05 14:04:04 +10006391 if (path_and_dir_fd_invalid("utime", path, dir_fd) ||
6392 dir_fd_and_fd_invalid("utime", dir_fd, path->fd) ||
6393 fd_and_follow_symlinks_invalid("utime", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -07006394 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006395
Larry Hastings9cf065c2012-06-22 16:30:09 -07006396#if !defined(HAVE_UTIMENSAT)
6397 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
Georg Brandl969288e2012-06-26 09:25:44 +02006398 PyErr_SetString(PyExc_ValueError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006399 "utime: cannot use dir_fd and follow_symlinks "
6400 "together on this platform");
6401 goto exit;
6402 }
6403#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006404
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006405#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07006406 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006407 if (path->wide)
6408 hFile = CreateFileW(path->wide, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006409 NULL, OPEN_EXISTING,
6410 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006411 else
Larry Hastings2f936352014-08-05 14:04:04 +10006412 hFile = CreateFileA(path->narrow, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006413 NULL, OPEN_EXISTING,
6414 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006415 Py_END_ALLOW_THREADS
6416 if (hFile == INVALID_HANDLE_VALUE) {
Larry Hastings2f936352014-08-05 14:04:04 +10006417 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006418 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006419 }
6420
Larry Hastings9cf065c2012-06-22 16:30:09 -07006421 if (utime.now) {
Antoine Pitrou91a7af32013-11-23 15:23:26 +01006422 GetSystemTimeAsFileTime(&mtime);
6423 atime = mtime;
Victor Stinner8c62be82010-05-06 00:08:46 +00006424 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006425 else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006426 time_t_to_FILE_TIME(utime.atime_s, utime.atime_ns, &atime);
6427 time_t_to_FILE_TIME(utime.mtime_s, utime.mtime_ns, &mtime);
Victor Stinner8c62be82010-05-06 00:08:46 +00006428 }
6429 if (!SetFileTime(hFile, NULL, &atime, &mtime)) {
6430 /* Avoid putting the file name into the error here,
6431 as that may confuse the user into believing that
6432 something is wrong with the file, when it also
6433 could be the time stamp that gives a problem. */
Victor Stinnerb024e842012-10-31 22:24:06 +01006434 PyErr_SetFromWindowsErr(0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006435 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006436 }
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006437#else /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006438 Py_BEGIN_ALLOW_THREADS
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006439
Larry Hastings9cf065c2012-06-22 16:30:09 -07006440#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6441 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10006442 result = utime_nofollow_symlinks(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006443 else
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006444#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07006445
6446#if UTIME_HAVE_DIR_FD
6447 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10006448 result = utime_dir_fd(&utime, dir_fd, path->narrow, follow_symlinks);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006449 else
6450#endif
6451
6452#if UTIME_HAVE_FD
Larry Hastings2f936352014-08-05 14:04:04 +10006453 if (path->fd != -1)
6454 result = utime_fd(&utime, path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006455 else
6456#endif
6457
Larry Hastings2f936352014-08-05 14:04:04 +10006458 result = utime_default(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006459
6460 Py_END_ALLOW_THREADS
6461
6462 if (result < 0) {
6463 /* see previous comment about not putting filename in error here */
6464 return_value = posix_error();
6465 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006466 }
Larry Hastings76ad59b2012-05-03 00:30:07 -07006467
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006468#endif /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006469
6470 Py_INCREF(Py_None);
6471 return_value = Py_None;
6472
6473exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006474#ifdef MS_WINDOWS
6475 if (hFile != INVALID_HANDLE_VALUE)
6476 CloseHandle(hFile);
6477#endif
6478 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00006479}
6480
Guido van Rossum3b066191991-06-04 19:40:25 +00006481/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006482
Larry Hastings2f936352014-08-05 14:04:04 +10006483
6484/*[clinic input]
6485os._exit
6486
6487 status: int
6488
6489Exit to the system with specified status, without normal exit processing.
6490[clinic start generated code]*/
6491
6492PyDoc_STRVAR(os__exit__doc__,
6493"_exit($module, /, status)\n"
6494"--\n"
6495"\n"
6496"Exit to the system with specified status, without normal exit processing.");
6497
6498#define OS__EXIT_METHODDEF \
6499 {"_exit", (PyCFunction)os__exit, METH_VARARGS|METH_KEYWORDS, os__exit__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006500
Barry Warsaw53699e91996-12-10 23:23:01 +00006501static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006502os__exit_impl(PyModuleDef *module, int status);
6503
6504static PyObject *
6505os__exit(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85e3b011991-06-03 12:42:10 +00006506{
Larry Hastings2f936352014-08-05 14:04:04 +10006507 PyObject *return_value = NULL;
6508 static char *_keywords[] = {"status", NULL};
6509 int status;
6510
6511 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6512 "i:_exit", _keywords,
6513 &status))
6514 goto exit;
6515 return_value = os__exit_impl(module, status);
6516
6517exit:
6518 return return_value;
6519}
6520
6521static PyObject *
6522os__exit_impl(PyModuleDef *module, int status)
6523/*[clinic end generated code: output=4f9858c4cc2dcb89 input=5e6d57556b0c4a62]*/
6524{
6525 _exit(status);
Victor Stinner8c62be82010-05-06 00:08:46 +00006526 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006527}
6528
Martin v. Löwis114619e2002-10-07 06:44:21 +00006529#if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
6530static void
Martin v. Löwis725507b2006-03-07 12:08:51 +00006531free_string_array(char **array, Py_ssize_t count)
Martin v. Löwis114619e2002-10-07 06:44:21 +00006532{
Victor Stinner8c62be82010-05-06 00:08:46 +00006533 Py_ssize_t i;
6534 for (i = 0; i < count; i++)
6535 PyMem_Free(array[i]);
6536 PyMem_DEL(array);
Martin v. Löwis114619e2002-10-07 06:44:21 +00006537}
Martin v. Löwis011e8422009-05-05 04:43:17 +00006538
Antoine Pitrou69f71142009-05-24 21:25:49 +00006539static
Martin v. Löwis011e8422009-05-05 04:43:17 +00006540int fsconvert_strdup(PyObject *o, char**out)
6541{
Victor Stinner8c62be82010-05-06 00:08:46 +00006542 PyObject *bytes;
6543 Py_ssize_t size;
6544 if (!PyUnicode_FSConverter(o, &bytes))
6545 return 0;
6546 size = PyBytes_GET_SIZE(bytes);
6547 *out = PyMem_Malloc(size+1);
Victor Stinner50abf222013-11-07 23:56:10 +01006548 if (!*out) {
6549 PyErr_NoMemory();
Victor Stinner8c62be82010-05-06 00:08:46 +00006550 return 0;
Victor Stinner50abf222013-11-07 23:56:10 +01006551 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006552 memcpy(*out, PyBytes_AsString(bytes), size+1);
6553 Py_DECREF(bytes);
6554 return 1;
Martin v. Löwis011e8422009-05-05 04:43:17 +00006555}
Martin v. Löwis114619e2002-10-07 06:44:21 +00006556#endif
6557
Ross Lagerwall7807c352011-03-17 20:20:30 +02006558#if defined(HAVE_EXECV) || defined (HAVE_FEXECVE)
Victor Stinner13bb71c2010-04-23 21:41:56 +00006559static char**
6560parse_envlist(PyObject* env, Py_ssize_t *envc_ptr)
6561{
Victor Stinner8c62be82010-05-06 00:08:46 +00006562 char **envlist;
6563 Py_ssize_t i, pos, envc;
6564 PyObject *keys=NULL, *vals=NULL;
6565 PyObject *key, *val, *key2, *val2;
6566 char *p, *k, *v;
6567 size_t len;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006568
Victor Stinner8c62be82010-05-06 00:08:46 +00006569 i = PyMapping_Size(env);
6570 if (i < 0)
6571 return NULL;
6572 envlist = PyMem_NEW(char *, i + 1);
6573 if (envlist == NULL) {
6574 PyErr_NoMemory();
6575 return NULL;
6576 }
6577 envc = 0;
6578 keys = PyMapping_Keys(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006579 if (!keys)
6580 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00006581 vals = PyMapping_Values(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006582 if (!vals)
Victor Stinner8c62be82010-05-06 00:08:46 +00006583 goto error;
6584 if (!PyList_Check(keys) || !PyList_Check(vals)) {
6585 PyErr_Format(PyExc_TypeError,
6586 "env.keys() or env.values() is not a list");
6587 goto error;
6588 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006589
Victor Stinner8c62be82010-05-06 00:08:46 +00006590 for (pos = 0; pos < i; pos++) {
6591 key = PyList_GetItem(keys, pos);
6592 val = PyList_GetItem(vals, pos);
6593 if (!key || !val)
6594 goto error;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006595
Victor Stinner8c62be82010-05-06 00:08:46 +00006596 if (PyUnicode_FSConverter(key, &key2) == 0)
6597 goto error;
6598 if (PyUnicode_FSConverter(val, &val2) == 0) {
6599 Py_DECREF(key2);
6600 goto error;
6601 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006602
Victor Stinner8c62be82010-05-06 00:08:46 +00006603 k = PyBytes_AsString(key2);
6604 v = PyBytes_AsString(val2);
6605 len = PyBytes_GET_SIZE(key2) + PyBytes_GET_SIZE(val2) + 2;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006606
Victor Stinner8c62be82010-05-06 00:08:46 +00006607 p = PyMem_NEW(char, len);
6608 if (p == NULL) {
6609 PyErr_NoMemory();
6610 Py_DECREF(key2);
6611 Py_DECREF(val2);
6612 goto error;
6613 }
6614 PyOS_snprintf(p, len, "%s=%s", k, v);
6615 envlist[envc++] = p;
6616 Py_DECREF(key2);
6617 Py_DECREF(val2);
Victor Stinner8c62be82010-05-06 00:08:46 +00006618 }
6619 Py_DECREF(vals);
6620 Py_DECREF(keys);
Victor Stinner13bb71c2010-04-23 21:41:56 +00006621
Victor Stinner8c62be82010-05-06 00:08:46 +00006622 envlist[envc] = 0;
6623 *envc_ptr = envc;
6624 return envlist;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006625
6626error:
Victor Stinner8c62be82010-05-06 00:08:46 +00006627 Py_XDECREF(keys);
6628 Py_XDECREF(vals);
6629 while (--envc >= 0)
6630 PyMem_DEL(envlist[envc]);
6631 PyMem_DEL(envlist);
6632 return NULL;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006633}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006634
Ross Lagerwall7807c352011-03-17 20:20:30 +02006635static char**
6636parse_arglist(PyObject* argv, Py_ssize_t *argc)
6637{
6638 int i;
6639 char **argvlist = PyMem_NEW(char *, *argc+1);
6640 if (argvlist == NULL) {
6641 PyErr_NoMemory();
6642 return NULL;
6643 }
6644 for (i = 0; i < *argc; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006645 PyObject* item = PySequence_ITEM(argv, i);
6646 if (item == NULL)
6647 goto fail;
6648 if (!fsconvert_strdup(item, &argvlist[i])) {
6649 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006650 goto fail;
6651 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006652 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006653 }
6654 argvlist[*argc] = NULL;
6655 return argvlist;
6656fail:
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006657 *argc = i;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006658 free_string_array(argvlist, *argc);
6659 return NULL;
6660}
6661#endif
6662
Larry Hastings2f936352014-08-05 14:04:04 +10006663
Ross Lagerwall7807c352011-03-17 20:20:30 +02006664#ifdef HAVE_EXECV
Larry Hastings2f936352014-08-05 14:04:04 +10006665/*[clinic input]
6666os.execv
6667
6668 path: FSConverter
6669 Path of executable file.
6670 argv: object
6671 Tuple or list of strings.
6672 /
6673
6674Execute an executable path with arguments, replacing current process.
6675[clinic start generated code]*/
6676
6677PyDoc_STRVAR(os_execv__doc__,
6678"execv($module, path, argv, /)\n"
6679"--\n"
6680"\n"
6681"Execute an executable path with arguments, replacing current process.\n"
6682"\n"
6683" path\n"
6684" Path of executable file.\n"
6685" argv\n"
6686" Tuple or list of strings.");
6687
6688#define OS_EXECV_METHODDEF \
6689 {"execv", (PyCFunction)os_execv, METH_VARARGS, os_execv__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02006690
6691static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006692os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv);
6693
6694static PyObject *
6695os_execv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006696{
Larry Hastings2f936352014-08-05 14:04:04 +10006697 PyObject *return_value = NULL;
6698 PyObject *path = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006699 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006700
6701 if (!PyArg_ParseTuple(args,
6702 "O&O:execv",
6703 PyUnicode_FSConverter, &path, &argv))
6704 goto exit;
6705 return_value = os_execv_impl(module, path, argv);
6706
6707exit:
6708 /* Cleanup for path */
6709 Py_XDECREF(path);
6710
6711 return return_value;
6712}
6713
6714static PyObject *
6715os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv)
6716/*[clinic end generated code: output=b0f5f2caa6097edc input=96041559925e5229]*/
6717{
6718 char *path_char;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006719 char **argvlist;
6720 Py_ssize_t argc;
6721
6722 /* execv has two arguments: (path, argv), where
6723 argv is a list or tuple of strings. */
6724
Larry Hastings2f936352014-08-05 14:04:04 +10006725 path_char = PyBytes_AsString(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006726 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
6727 PyErr_SetString(PyExc_TypeError,
6728 "execv() arg 2 must be a tuple or list");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006729 return NULL;
6730 }
6731 argc = PySequence_Size(argv);
6732 if (argc < 1) {
6733 PyErr_SetString(PyExc_ValueError, "execv() arg 2 must not be empty");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006734 return NULL;
6735 }
6736
6737 argvlist = parse_arglist(argv, &argc);
6738 if (argvlist == NULL) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02006739 return NULL;
6740 }
6741
Larry Hastings2f936352014-08-05 14:04:04 +10006742 execv(path_char, argvlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006743
6744 /* If we get here it's definitely an error */
6745
6746 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006747 return posix_error();
6748}
6749
Larry Hastings2f936352014-08-05 14:04:04 +10006750
6751/*[clinic input]
6752os.execve
6753
6754 path: path_t(allow_fd='PATH_HAVE_FEXECVE')
6755 Path of executable file.
6756 argv: object
6757 Tuple or list of strings.
6758 env: object
6759 Dictionary of strings mapping to strings.
6760
6761Execute an executable path with arguments, replacing current process.
6762[clinic start generated code]*/
6763
6764PyDoc_STRVAR(os_execve__doc__,
6765"execve($module, /, path, argv, env)\n"
6766"--\n"
6767"\n"
6768"Execute an executable path with arguments, replacing current process.\n"
6769"\n"
6770" path\n"
6771" Path of executable file.\n"
6772" argv\n"
6773" Tuple or list of strings.\n"
6774" env\n"
6775" Dictionary of strings mapping to strings.");
6776
6777#define OS_EXECVE_METHODDEF \
6778 {"execve", (PyCFunction)os_execve, METH_VARARGS|METH_KEYWORDS, os_execve__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006779
Barry Warsaw53699e91996-12-10 23:23:01 +00006780static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006781os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env);
6782
6783static PyObject *
6784os_execve(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006785{
Larry Hastings2f936352014-08-05 14:04:04 +10006786 PyObject *return_value = NULL;
6787 static char *_keywords[] = {"path", "argv", "env", NULL};
6788 path_t path = PATH_T_INITIALIZE("execve", "path", 0, PATH_HAVE_FEXECVE);
6789 PyObject *argv;
6790 PyObject *env;
6791
6792 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6793 "O&OO:execve", _keywords,
6794 path_converter, &path, &argv, &env))
6795 goto exit;
6796 return_value = os_execve_impl(module, &path, argv, env);
6797
6798exit:
6799 /* Cleanup for path */
6800 path_cleanup(&path);
6801
6802 return return_value;
6803}
6804
6805static PyObject *
6806os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env)
6807/*[clinic end generated code: output=fb283760f5d15ab7 input=626804fa092606d9]*/
6808{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006809 char **argvlist = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006810 char **envlist;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006811 Py_ssize_t argc, envc;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006812
Victor Stinner8c62be82010-05-06 00:08:46 +00006813 /* execve has three arguments: (path, argv, env), where
6814 argv is a list or tuple of strings and env is a dictionary
6815 like posix.environ. */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006816
Ross Lagerwall7807c352011-03-17 20:20:30 +02006817 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006818 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006819 "execve: argv must be a tuple or list");
6820 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006821 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02006822 argc = PySequence_Size(argv);
Victor Stinner8c62be82010-05-06 00:08:46 +00006823 if (!PyMapping_Check(env)) {
6824 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006825 "execve: environment must be a mapping object");
6826 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006827 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006828
Ross Lagerwall7807c352011-03-17 20:20:30 +02006829 argvlist = parse_arglist(argv, &argc);
Victor Stinner8c62be82010-05-06 00:08:46 +00006830 if (argvlist == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006831 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006832 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006833
Victor Stinner8c62be82010-05-06 00:08:46 +00006834 envlist = parse_envlist(env, &envc);
6835 if (envlist == NULL)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006836 goto fail;
6837
Larry Hastings9cf065c2012-06-22 16:30:09 -07006838#ifdef HAVE_FEXECVE
Larry Hastings2f936352014-08-05 14:04:04 +10006839 if (path->fd > -1)
6840 fexecve(path->fd, argvlist, envlist);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006841 else
6842#endif
Larry Hastings2f936352014-08-05 14:04:04 +10006843 execve(path->narrow, argvlist, envlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006844
6845 /* If we get here it's definitely an error */
6846
Larry Hastings2f936352014-08-05 14:04:04 +10006847 path_error(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006848
6849 while (--envc >= 0)
6850 PyMem_DEL(envlist[envc]);
6851 PyMem_DEL(envlist);
6852 fail:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006853 if (argvlist)
6854 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006855 return NULL;
6856}
Larry Hastings9cf065c2012-06-22 16:30:09 -07006857#endif /* HAVE_EXECV */
6858
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006859
Guido van Rossuma1065681999-01-25 23:20:23 +00006860#ifdef HAVE_SPAWNV
Larry Hastings2f936352014-08-05 14:04:04 +10006861/*[clinic input]
6862os.spawnv
6863
6864 mode: int
6865 Mode of process creation.
6866 path: FSConverter
6867 Path of executable file.
6868 argv: object
6869 Tuple or list of strings.
6870 /
6871
6872Execute the program specified by path in a new process.
6873[clinic start generated code]*/
6874
6875PyDoc_STRVAR(os_spawnv__doc__,
6876"spawnv($module, mode, path, argv, /)\n"
6877"--\n"
6878"\n"
6879"Execute the program specified by path in a new process.\n"
6880"\n"
6881" mode\n"
6882" Mode of process creation.\n"
6883" path\n"
6884" Path of executable file.\n"
6885" argv\n"
6886" Tuple or list of strings.");
6887
6888#define OS_SPAWNV_METHODDEF \
6889 {"spawnv", (PyCFunction)os_spawnv, METH_VARARGS, os_spawnv__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00006890
6891static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006892os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv);
6893
6894static PyObject *
6895os_spawnv(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00006896{
Larry Hastings2f936352014-08-05 14:04:04 +10006897 PyObject *return_value = NULL;
6898 int mode;
6899 PyObject *path = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006900 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006901
6902 if (!PyArg_ParseTuple(args,
6903 "iO&O:spawnv",
6904 &mode, PyUnicode_FSConverter, &path, &argv))
6905 goto exit;
6906 return_value = os_spawnv_impl(module, mode, path, argv);
6907
6908exit:
6909 /* Cleanup for path */
6910 Py_XDECREF(path);
6911
6912 return return_value;
6913}
6914
6915static PyObject *
6916os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv)
6917/*[clinic end generated code: output=dfee6be062e780e3 input=042c91dfc1e6debc]*/
6918{
6919 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00006920 char **argvlist;
Larry Hastings2f936352014-08-05 14:04:04 +10006921 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00006922 Py_ssize_t argc;
6923 Py_intptr_t spawnval;
6924 PyObject *(*getitem)(PyObject *, Py_ssize_t);
Guido van Rossuma1065681999-01-25 23:20:23 +00006925
Victor Stinner8c62be82010-05-06 00:08:46 +00006926 /* spawnv has three arguments: (mode, path, argv), where
6927 argv is a list or tuple of strings. */
Guido van Rossuma1065681999-01-25 23:20:23 +00006928
Larry Hastings2f936352014-08-05 14:04:04 +10006929 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00006930 if (PyList_Check(argv)) {
6931 argc = PyList_Size(argv);
6932 getitem = PyList_GetItem;
6933 }
6934 else if (PyTuple_Check(argv)) {
6935 argc = PyTuple_Size(argv);
6936 getitem = PyTuple_GetItem;
6937 }
6938 else {
6939 PyErr_SetString(PyExc_TypeError,
6940 "spawnv() arg 2 must be a tuple or list");
Victor Stinner8c62be82010-05-06 00:08:46 +00006941 return NULL;
6942 }
Guido van Rossuma1065681999-01-25 23:20:23 +00006943
Victor Stinner8c62be82010-05-06 00:08:46 +00006944 argvlist = PyMem_NEW(char *, argc+1);
6945 if (argvlist == NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006946 return PyErr_NoMemory();
6947 }
6948 for (i = 0; i < argc; i++) {
6949 if (!fsconvert_strdup((*getitem)(argv, i),
6950 &argvlist[i])) {
6951 free_string_array(argvlist, i);
6952 PyErr_SetString(
6953 PyExc_TypeError,
6954 "spawnv() arg 2 must contain only strings");
Victor Stinner8c62be82010-05-06 00:08:46 +00006955 return NULL;
6956 }
6957 }
6958 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00006959
Victor Stinner8c62be82010-05-06 00:08:46 +00006960 if (mode == _OLD_P_OVERLAY)
6961 mode = _P_OVERLAY;
Tim Peters5aa91602002-01-30 05:46:57 +00006962
Victor Stinner8c62be82010-05-06 00:08:46 +00006963 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006964 spawnval = _spawnv(mode, path_char, argvlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00006965 Py_END_ALLOW_THREADS
Tim Peters5aa91602002-01-30 05:46:57 +00006966
Victor Stinner8c62be82010-05-06 00:08:46 +00006967 free_string_array(argvlist, argc);
Guido van Rossuma1065681999-01-25 23:20:23 +00006968
Victor Stinner8c62be82010-05-06 00:08:46 +00006969 if (spawnval == -1)
6970 return posix_error();
6971 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006972 return Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00006973}
6974
6975
Larry Hastings2f936352014-08-05 14:04:04 +10006976/*[clinic input]
6977os.spawnve
6978
6979 mode: int
6980 Mode of process creation.
6981 path: FSConverter
6982 Path of executable file.
6983 argv: object
6984 Tuple or list of strings.
6985 env: object
6986 Dictionary of strings mapping to strings.
6987 /
6988
6989Execute the program specified by path in a new process.
6990[clinic start generated code]*/
6991
6992PyDoc_STRVAR(os_spawnve__doc__,
6993"spawnve($module, mode, path, argv, env, /)\n"
6994"--\n"
6995"\n"
6996"Execute the program specified by path in a new process.\n"
6997"\n"
6998" mode\n"
6999" Mode of process creation.\n"
7000" path\n"
7001" Path of executable file.\n"
7002" argv\n"
7003" Tuple or list of strings.\n"
7004" env\n"
7005" Dictionary of strings mapping to strings.");
7006
7007#define OS_SPAWNVE_METHODDEF \
7008 {"spawnve", (PyCFunction)os_spawnve, METH_VARARGS, os_spawnve__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00007009
7010static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007011os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env);
7012
7013static PyObject *
7014os_spawnve(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00007015{
Larry Hastings2f936352014-08-05 14:04:04 +10007016 PyObject *return_value = NULL;
7017 int mode;
7018 PyObject *path = NULL;
7019 PyObject *argv;
7020 PyObject *env;
7021
7022 if (!PyArg_ParseTuple(args,
7023 "iO&OO:spawnve",
7024 &mode, PyUnicode_FSConverter, &path, &argv, &env))
7025 goto exit;
7026 return_value = os_spawnve_impl(module, mode, path, argv, env);
7027
7028exit:
7029 /* Cleanup for path */
7030 Py_XDECREF(path);
7031
7032 return return_value;
7033}
7034
7035static PyObject *
7036os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env)
7037/*[clinic end generated code: output=6f7df38473f63c7c input=02362fd937963f8f]*/
7038{
7039 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00007040 char **argvlist;
7041 char **envlist;
7042 PyObject *res = NULL;
Antoine Pitrou22e41552010-08-15 18:07:50 +00007043 Py_ssize_t argc, i, envc;
Victor Stinner8c62be82010-05-06 00:08:46 +00007044 Py_intptr_t spawnval;
7045 PyObject *(*getitem)(PyObject *, Py_ssize_t);
7046 Py_ssize_t lastarg = 0;
Guido van Rossuma1065681999-01-25 23:20:23 +00007047
Victor Stinner8c62be82010-05-06 00:08:46 +00007048 /* spawnve has four arguments: (mode, path, argv, env), where
7049 argv is a list or tuple of strings and env is a dictionary
7050 like posix.environ. */
Guido van Rossuma1065681999-01-25 23:20:23 +00007051
Larry Hastings2f936352014-08-05 14:04:04 +10007052 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00007053 if (PyList_Check(argv)) {
7054 argc = PyList_Size(argv);
7055 getitem = PyList_GetItem;
7056 }
7057 else if (PyTuple_Check(argv)) {
7058 argc = PyTuple_Size(argv);
7059 getitem = PyTuple_GetItem;
7060 }
7061 else {
7062 PyErr_SetString(PyExc_TypeError,
7063 "spawnve() arg 2 must be a tuple or list");
7064 goto fail_0;
7065 }
7066 if (!PyMapping_Check(env)) {
7067 PyErr_SetString(PyExc_TypeError,
7068 "spawnve() arg 3 must be a mapping object");
7069 goto fail_0;
7070 }
Guido van Rossuma1065681999-01-25 23:20:23 +00007071
Victor Stinner8c62be82010-05-06 00:08:46 +00007072 argvlist = PyMem_NEW(char *, argc+1);
7073 if (argvlist == NULL) {
7074 PyErr_NoMemory();
7075 goto fail_0;
7076 }
7077 for (i = 0; i < argc; i++) {
7078 if (!fsconvert_strdup((*getitem)(argv, i),
7079 &argvlist[i]))
7080 {
7081 lastarg = i;
7082 goto fail_1;
7083 }
7084 }
7085 lastarg = argc;
7086 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00007087
Victor Stinner8c62be82010-05-06 00:08:46 +00007088 envlist = parse_envlist(env, &envc);
7089 if (envlist == NULL)
7090 goto fail_1;
Guido van Rossuma1065681999-01-25 23:20:23 +00007091
Victor Stinner8c62be82010-05-06 00:08:46 +00007092 if (mode == _OLD_P_OVERLAY)
7093 mode = _P_OVERLAY;
Tim Peters25059d32001-12-07 20:35:43 +00007094
Victor Stinner8c62be82010-05-06 00:08:46 +00007095 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007096 spawnval = _spawnve(mode, path_char, argvlist, envlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00007097 Py_END_ALLOW_THREADS
Tim Peters25059d32001-12-07 20:35:43 +00007098
Victor Stinner8c62be82010-05-06 00:08:46 +00007099 if (spawnval == -1)
7100 (void) posix_error();
7101 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01007102 res = Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00007103
Victor Stinner8c62be82010-05-06 00:08:46 +00007104 while (--envc >= 0)
7105 PyMem_DEL(envlist[envc]);
7106 PyMem_DEL(envlist);
Guido van Rossum0847c5c2002-12-13 18:36:22 +00007107 fail_1:
Victor Stinner8c62be82010-05-06 00:08:46 +00007108 free_string_array(argvlist, lastarg);
Martin v. Löwis114619e2002-10-07 06:44:21 +00007109 fail_0:
Victor Stinner8c62be82010-05-06 00:08:46 +00007110 return res;
Guido van Rossuma1065681999-01-25 23:20:23 +00007111}
Andrew MacIntyre69e18c92004-04-04 07:11:43 +00007112
Guido van Rossuma1065681999-01-25 23:20:23 +00007113#endif /* HAVE_SPAWNV */
7114
7115
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007116#ifdef HAVE_FORK1
Larry Hastings2f936352014-08-05 14:04:04 +10007117/*[clinic input]
7118os.fork1
7119
7120Fork a child process with a single multiplexed (i.e., not bound) thread.
7121
7122Return 0 to child process and PID of child to parent process.
7123[clinic start generated code]*/
7124
7125PyDoc_STRVAR(os_fork1__doc__,
7126"fork1($module, /)\n"
7127"--\n"
7128"\n"
7129"Fork a child process with a single multiplexed (i.e., not bound) thread.\n"
7130"\n"
7131"Return 0 to child process and PID of child to parent process.");
7132
7133#define OS_FORK1_METHODDEF \
7134 {"fork1", (PyCFunction)os_fork1, METH_NOARGS, os_fork1__doc__},
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007135
7136static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007137os_fork1_impl(PyModuleDef *module);
7138
7139static PyObject *
7140os_fork1(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7141{
7142 return os_fork1_impl(module);
7143}
7144
7145static PyObject *
7146os_fork1_impl(PyModuleDef *module)
7147/*[clinic end generated code: output=fa04088d6bc02efa input=12db02167893926e]*/
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007148{
Victor Stinner8c62be82010-05-06 00:08:46 +00007149 pid_t pid;
7150 int result = 0;
7151 _PyImport_AcquireLock();
7152 pid = fork1();
7153 if (pid == 0) {
7154 /* child: this clobbers and resets the import lock. */
7155 PyOS_AfterFork();
7156 } else {
7157 /* parent: release the import lock. */
7158 result = _PyImport_ReleaseLock();
7159 }
7160 if (pid == -1)
7161 return posix_error();
7162 if (result < 0) {
7163 /* Don't clobber the OSError if the fork failed. */
7164 PyErr_SetString(PyExc_RuntimeError,
7165 "not holding the import lock");
7166 return NULL;
7167 }
7168 return PyLong_FromPid(pid);
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007169}
Larry Hastings2f936352014-08-05 14:04:04 +10007170#endif /* HAVE_FORK1 */
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007171
7172
Guido van Rossumad0ee831995-03-01 10:34:45 +00007173#ifdef HAVE_FORK
Larry Hastings2f936352014-08-05 14:04:04 +10007174/*[clinic input]
7175os.fork
7176
7177Fork a child process.
7178
7179Return 0 to child process and PID of child to parent process.
7180[clinic start generated code]*/
7181
7182PyDoc_STRVAR(os_fork__doc__,
7183"fork($module, /)\n"
7184"--\n"
7185"\n"
7186"Fork a child process.\n"
7187"\n"
7188"Return 0 to child process and PID of child to parent process.");
7189
7190#define OS_FORK_METHODDEF \
7191 {"fork", (PyCFunction)os_fork, METH_NOARGS, os_fork__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007192
Barry Warsaw53699e91996-12-10 23:23:01 +00007193static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007194os_fork_impl(PyModuleDef *module);
7195
7196static PyObject *
7197os_fork(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7198{
7199 return os_fork_impl(module);
7200}
7201
7202static PyObject *
7203os_fork_impl(PyModuleDef *module)
7204/*[clinic end generated code: output=b3c8e6bdc11eedc6 input=13c956413110eeaa]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00007205{
Victor Stinner8c62be82010-05-06 00:08:46 +00007206 pid_t pid;
7207 int result = 0;
7208 _PyImport_AcquireLock();
7209 pid = fork();
7210 if (pid == 0) {
7211 /* child: this clobbers and resets the import lock. */
7212 PyOS_AfterFork();
7213 } else {
7214 /* parent: release the import lock. */
7215 result = _PyImport_ReleaseLock();
7216 }
7217 if (pid == -1)
7218 return posix_error();
7219 if (result < 0) {
7220 /* Don't clobber the OSError if the fork failed. */
7221 PyErr_SetString(PyExc_RuntimeError,
7222 "not holding the import lock");
7223 return NULL;
7224 }
7225 return PyLong_FromPid(pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00007226}
Larry Hastings2f936352014-08-05 14:04:04 +10007227#endif /* HAVE_FORK */
7228
Guido van Rossum85e3b011991-06-03 12:42:10 +00007229
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007230#ifdef HAVE_SCHED_H
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007231#ifdef HAVE_SCHED_GET_PRIORITY_MAX
Larry Hastings2f936352014-08-05 14:04:04 +10007232/*[clinic input]
7233os.sched_get_priority_max
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007234
Larry Hastings2f936352014-08-05 14:04:04 +10007235 policy: int
7236
7237Get the maximum scheduling priority for policy.
7238[clinic start generated code]*/
7239
7240PyDoc_STRVAR(os_sched_get_priority_max__doc__,
7241"sched_get_priority_max($module, /, policy)\n"
7242"--\n"
7243"\n"
7244"Get the maximum scheduling priority for policy.");
7245
7246#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF \
7247 {"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 -05007248
7249static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007250os_sched_get_priority_max_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007251
Larry Hastings2f936352014-08-05 14:04:04 +10007252static PyObject *
7253os_sched_get_priority_max(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7254{
7255 PyObject *return_value = NULL;
7256 static char *_keywords[] = {"policy", NULL};
7257 int policy;
7258
7259 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7260 "i:sched_get_priority_max", _keywords,
7261 &policy))
7262 goto exit;
7263 return_value = os_sched_get_priority_max_impl(module, policy);
7264
7265exit:
7266 return return_value;
7267}
7268
7269static PyObject *
7270os_sched_get_priority_max_impl(PyModuleDef *module, int policy)
7271/*[clinic end generated code: output=a580a52f25238c1f input=2097b7998eca6874]*/
7272{
7273 int max;
7274
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007275 max = sched_get_priority_max(policy);
7276 if (max < 0)
7277 return posix_error();
7278 return PyLong_FromLong(max);
7279}
7280
Larry Hastings2f936352014-08-05 14:04:04 +10007281
7282/*[clinic input]
7283os.sched_get_priority_min
7284
7285 policy: int
7286
7287Get the minimum scheduling priority for policy.
7288[clinic start generated code]*/
7289
7290PyDoc_STRVAR(os_sched_get_priority_min__doc__,
7291"sched_get_priority_min($module, /, policy)\n"
7292"--\n"
7293"\n"
7294"Get the minimum scheduling priority for policy.");
7295
7296#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF \
7297 {"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 -05007298
7299static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007300os_sched_get_priority_min_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007301
Larry Hastings2f936352014-08-05 14:04:04 +10007302static PyObject *
7303os_sched_get_priority_min(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7304{
7305 PyObject *return_value = NULL;
7306 static char *_keywords[] = {"policy", NULL};
7307 int policy;
7308
7309 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7310 "i:sched_get_priority_min", _keywords,
7311 &policy))
7312 goto exit;
7313 return_value = os_sched_get_priority_min_impl(module, policy);
7314
7315exit:
7316 return return_value;
7317}
7318
7319static PyObject *
7320os_sched_get_priority_min_impl(PyModuleDef *module, int policy)
7321/*[clinic end generated code: output=bad8ba10e7d0e977 input=21bc8fa0d70983bf]*/
7322{
7323 int min = sched_get_priority_min(policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007324 if (min < 0)
7325 return posix_error();
7326 return PyLong_FromLong(min);
7327}
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007328#endif /* HAVE_SCHED_GET_PRIORITY_MAX */
7329
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007330
Larry Hastings2f936352014-08-05 14:04:04 +10007331#ifdef HAVE_SCHED_SETSCHEDULER
7332/*[clinic input]
7333os.sched_getscheduler
7334 pid: pid_t
7335 /
7336
7337Get the scheduling policy for the process identifiedy by pid.
7338
7339Passing 0 for pid returns the scheduling policy for the calling process.
7340[clinic start generated code]*/
7341
7342PyDoc_STRVAR(os_sched_getscheduler__doc__,
7343"sched_getscheduler($module, pid, /)\n"
7344"--\n"
7345"\n"
7346"Get the scheduling policy for the process identifiedy by pid.\n"
7347"\n"
7348"Passing 0 for pid returns the scheduling policy for the calling process.");
7349
7350#define OS_SCHED_GETSCHEDULER_METHODDEF \
7351 {"sched_getscheduler", (PyCFunction)os_sched_getscheduler, METH_VARARGS, os_sched_getscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007352
7353static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007354os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid);
7355
7356static PyObject *
7357os_sched_getscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007358{
Larry Hastings2f936352014-08-05 14:04:04 +10007359 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007360 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007361
7362 if (!PyArg_ParseTuple(args,
7363 "" _Py_PARSE_PID ":sched_getscheduler",
7364 &pid))
7365 goto exit;
7366 return_value = os_sched_getscheduler_impl(module, pid);
7367
7368exit:
7369 return return_value;
7370}
7371
7372static PyObject *
7373os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid)
7374/*[clinic end generated code: output=e0d6244207b1d828 input=5f14cfd1f189e1a0]*/
7375{
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007376 int policy;
7377
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007378 policy = sched_getscheduler(pid);
7379 if (policy < 0)
7380 return posix_error();
7381 return PyLong_FromLong(policy);
7382}
Larry Hastings2f936352014-08-05 14:04:04 +10007383#endif /* HAVE_SCHED_SETSCHEDULER */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007384
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007385
7386#if defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM)
Larry Hastings2f936352014-08-05 14:04:04 +10007387/*[clinic input]
7388class os.sched_param "PyObject *" "&SchedParamType"
7389
7390@classmethod
7391os.sched_param.__new__
7392
7393 sched_priority: object
7394 A scheduling parameter.
7395
7396Current has only one field: sched_priority");
7397[clinic start generated code]*/
7398
7399PyDoc_STRVAR(os_sched_param__doc__,
7400"sched_param(sched_priority)\n"
7401"--\n"
7402"\n"
7403"Current has only one field: sched_priority\");\n"
7404"\n"
7405" sched_priority\n"
7406" A scheduling parameter.");
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007407
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007408static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007409os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007410
Larry Hastings2f936352014-08-05 14:04:04 +10007411static PyObject *
7412os_sched_param(PyTypeObject *type, PyObject *args, PyObject *kwargs)
7413{
7414 PyObject *return_value = NULL;
7415 static char *_keywords[] = {"sched_priority", NULL};
7416 PyObject *sched_priority;
7417
7418 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7419 "O:sched_param", _keywords,
7420 &sched_priority))
7421 goto exit;
7422 return_value = os_sched_param_impl(type, sched_priority);
7423
7424exit:
7425 return return_value;
7426}
7427
7428static PyObject *
7429os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority)
7430/*[clinic end generated code: output=d3791e345f7fe573 input=73a4c22f7071fc62]*/
7431{
7432 PyObject *res;
7433
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007434 res = PyStructSequence_New(type);
7435 if (!res)
7436 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10007437 Py_INCREF(sched_priority);
7438 PyStructSequence_SET_ITEM(res, 0, sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007439 return res;
7440}
7441
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007442
7443static PyStructSequence_Field sched_param_fields[] = {
7444 {"sched_priority", "the scheduling priority"},
7445 {0}
7446};
7447
7448static PyStructSequence_Desc sched_param_desc = {
7449 "sched_param", /* name */
Larry Hastings2f936352014-08-05 14:04:04 +10007450 os_sched_param__doc__, /* doc */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007451 sched_param_fields,
7452 1
7453};
7454
7455static int
7456convert_sched_param(PyObject *param, struct sched_param *res)
7457{
7458 long priority;
7459
7460 if (Py_TYPE(param) != &SchedParamType) {
7461 PyErr_SetString(PyExc_TypeError, "must have a sched_param object");
7462 return 0;
7463 }
7464 priority = PyLong_AsLong(PyStructSequence_GET_ITEM(param, 0));
7465 if (priority == -1 && PyErr_Occurred())
7466 return 0;
7467 if (priority > INT_MAX || priority < INT_MIN) {
7468 PyErr_SetString(PyExc_OverflowError, "sched_priority out of range");
7469 return 0;
7470 }
7471 res->sched_priority = Py_SAFE_DOWNCAST(priority, long, int);
7472 return 1;
7473}
Larry Hastings2f936352014-08-05 14:04:04 +10007474#endif /* defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM) */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007475
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007476
7477#ifdef HAVE_SCHED_SETSCHEDULER
Larry Hastings2f936352014-08-05 14:04:04 +10007478/*[clinic input]
7479os.sched_setscheduler
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007480
Larry Hastings2f936352014-08-05 14:04:04 +10007481 pid: pid_t
7482 policy: int
7483 param: sched_param
7484 /
7485
7486Set the scheduling policy for the process identified by pid.
7487
7488If pid is 0, the calling process is changed.
7489param is an instance of sched_param.
7490[clinic start generated code]*/
7491
7492PyDoc_STRVAR(os_sched_setscheduler__doc__,
7493"sched_setscheduler($module, pid, policy, param, /)\n"
7494"--\n"
7495"\n"
7496"Set the scheduling policy for the process identified by pid.\n"
7497"\n"
7498"If pid is 0, the calling process is changed.\n"
7499"param is an instance of sched_param.");
7500
7501#define OS_SCHED_SETSCHEDULER_METHODDEF \
7502 {"sched_setscheduler", (PyCFunction)os_sched_setscheduler, METH_VARARGS, os_sched_setscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007503
7504static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007505os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param);
7506
7507static PyObject *
7508os_sched_setscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007509{
Larry Hastings2f936352014-08-05 14:04:04 +10007510 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007511 pid_t pid;
7512 int policy;
7513 struct sched_param param;
7514
Larry Hastings2f936352014-08-05 14:04:04 +10007515 if (!PyArg_ParseTuple(args,
7516 "" _Py_PARSE_PID "iO&:sched_setscheduler",
7517 &pid, &policy, convert_sched_param, &param))
7518 goto exit;
7519 return_value = os_sched_setscheduler_impl(module, pid, policy, &param);
Jesus Cea9c822272011-09-10 01:40:52 +02007520
Larry Hastings2f936352014-08-05 14:04:04 +10007521exit:
7522 return return_value;
7523}
7524
7525static PyObject *
7526os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param)
7527/*[clinic end generated code: output=36abdb73f81c224f input=c581f9469a5327dd]*/
7528{
Jesus Cea9c822272011-09-10 01:40:52 +02007529 /*
Jesus Cea54b01492011-09-10 01:53:19 +02007530 ** sched_setscheduler() returns 0 in Linux, but the previous
7531 ** scheduling policy under Solaris/Illumos, and others.
7532 ** On error, -1 is returned in all Operating Systems.
Jesus Cea9c822272011-09-10 01:40:52 +02007533 */
Larry Hastings2f936352014-08-05 14:04:04 +10007534 if (sched_setscheduler(pid, policy, param) == -1)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007535 return posix_error();
7536 Py_RETURN_NONE;
7537}
Larry Hastings2f936352014-08-05 14:04:04 +10007538#endif /* HAVE_SCHED_SETSCHEDULER*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007539
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007540
7541#ifdef HAVE_SCHED_SETPARAM
Larry Hastings2f936352014-08-05 14:04:04 +10007542/*[clinic input]
7543os.sched_getparam
7544 pid: pid_t
7545 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007546
Larry Hastings2f936352014-08-05 14:04:04 +10007547Returns scheduling parameters for the process identified by pid.
7548
7549If pid is 0, returns parameters for the calling process.
7550Return value is an instance of sched_param.
7551[clinic start generated code]*/
7552
7553PyDoc_STRVAR(os_sched_getparam__doc__,
7554"sched_getparam($module, pid, /)\n"
7555"--\n"
7556"\n"
7557"Returns scheduling parameters for the process identified by pid.\n"
7558"\n"
7559"If pid is 0, returns parameters for the calling process.\n"
7560"Return value is an instance of sched_param.");
7561
7562#define OS_SCHED_GETPARAM_METHODDEF \
7563 {"sched_getparam", (PyCFunction)os_sched_getparam, METH_VARARGS, os_sched_getparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007564
7565static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007566os_sched_getparam_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007567
Larry Hastings2f936352014-08-05 14:04:04 +10007568static PyObject *
7569os_sched_getparam(PyModuleDef *module, PyObject *args)
7570{
7571 PyObject *return_value = NULL;
7572 pid_t pid;
7573
7574 if (!PyArg_ParseTuple(args,
7575 "" _Py_PARSE_PID ":sched_getparam",
7576 &pid))
7577 goto exit;
7578 return_value = os_sched_getparam_impl(module, pid);
7579
7580exit:
7581 return return_value;
7582}
7583
7584static PyObject *
7585os_sched_getparam_impl(PyModuleDef *module, pid_t pid)
7586/*[clinic end generated code: output=b33acc8db004a8c9 input=18a1ef9c2efae296]*/
7587{
7588 struct sched_param param;
7589 PyObject *result;
7590 PyObject *priority;
7591
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007592 if (sched_getparam(pid, &param))
7593 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007594 result = PyStructSequence_New(&SchedParamType);
7595 if (!result)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007596 return NULL;
7597 priority = PyLong_FromLong(param.sched_priority);
7598 if (!priority) {
Larry Hastings2f936352014-08-05 14:04:04 +10007599 Py_DECREF(result);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007600 return NULL;
7601 }
Larry Hastings2f936352014-08-05 14:04:04 +10007602 PyStructSequence_SET_ITEM(result, 0, priority);
7603 return result;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007604}
7605
Larry Hastings2f936352014-08-05 14:04:04 +10007606
7607/*[clinic input]
7608os.sched_setparam
7609 pid: pid_t
7610 param: sched_param
7611 /
7612
7613Set scheduling parameters for the process identified by pid.
7614
7615If pid is 0, sets parameters for the calling process.
7616param should be an instance of sched_param.
7617[clinic start generated code]*/
7618
7619PyDoc_STRVAR(os_sched_setparam__doc__,
7620"sched_setparam($module, pid, param, /)\n"
7621"--\n"
7622"\n"
7623"Set scheduling parameters for the process identified by pid.\n"
7624"\n"
7625"If pid is 0, sets parameters for the calling process.\n"
7626"param should be an instance of sched_param.");
7627
7628#define OS_SCHED_SETPARAM_METHODDEF \
7629 {"sched_setparam", (PyCFunction)os_sched_setparam, METH_VARARGS, os_sched_setparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007630
7631static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007632os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param);
7633
7634static PyObject *
7635os_sched_setparam(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007636{
Larry Hastings2f936352014-08-05 14:04:04 +10007637 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007638 pid_t pid;
7639 struct sched_param param;
7640
Larry Hastings2f936352014-08-05 14:04:04 +10007641 if (!PyArg_ParseTuple(args,
7642 "" _Py_PARSE_PID "O&:sched_setparam",
7643 &pid, convert_sched_param, &param))
7644 goto exit;
7645 return_value = os_sched_setparam_impl(module, pid, &param);
7646
7647exit:
7648 return return_value;
7649}
7650
7651static PyObject *
7652os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param)
7653/*[clinic end generated code: output=488bdf5bcbe0d4e8 input=6b8d6dfcecdc21bd]*/
7654{
7655 if (sched_setparam(pid, param))
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007656 return posix_error();
7657 Py_RETURN_NONE;
7658}
Larry Hastings2f936352014-08-05 14:04:04 +10007659#endif /* HAVE_SCHED_SETPARAM */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007660
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007661
7662#ifdef HAVE_SCHED_RR_GET_INTERVAL
Larry Hastings2f936352014-08-05 14:04:04 +10007663/*[clinic input]
7664os.sched_rr_get_interval -> double
7665 pid: pid_t
7666 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007667
Larry Hastings2f936352014-08-05 14:04:04 +10007668Return the round-robin quantum for the process identified by pid, in seconds.
7669
7670Value returned is a float.
7671[clinic start generated code]*/
7672
7673PyDoc_STRVAR(os_sched_rr_get_interval__doc__,
7674"sched_rr_get_interval($module, pid, /)\n"
7675"--\n"
7676"\n"
7677"Return the round-robin quantum for the process identified by pid, in seconds.\n"
7678"\n"
7679"Value returned is a float.");
7680
7681#define OS_SCHED_RR_GET_INTERVAL_METHODDEF \
7682 {"sched_rr_get_interval", (PyCFunction)os_sched_rr_get_interval, METH_VARARGS, os_sched_rr_get_interval__doc__},
7683
7684static double
7685os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007686
7687static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007688os_sched_rr_get_interval(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007689{
Larry Hastings2f936352014-08-05 14:04:04 +10007690 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007691 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007692 double _return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007693
Larry Hastings2f936352014-08-05 14:04:04 +10007694 if (!PyArg_ParseTuple(args,
7695 "" _Py_PARSE_PID ":sched_rr_get_interval",
7696 &pid))
7697 goto exit;
7698 _return_value = os_sched_rr_get_interval_impl(module, pid);
7699 if ((_return_value == -1.0) && PyErr_Occurred())
7700 goto exit;
7701 return_value = PyFloat_FromDouble(_return_value);
7702
7703exit:
7704 return return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007705}
7706
Larry Hastings2f936352014-08-05 14:04:04 +10007707static double
7708os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid)
7709/*[clinic end generated code: output=5b3b8d1f27fb2c0a input=2a973da15cca6fae]*/
7710{
7711 struct timespec interval;
7712 if (sched_rr_get_interval(pid, &interval)) {
7713 posix_error();
7714 return -1.0;
7715 }
7716 return (double)interval.tv_sec + 1e-9*interval.tv_nsec;
7717}
7718#endif /* HAVE_SCHED_RR_GET_INTERVAL */
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007719
Larry Hastings2f936352014-08-05 14:04:04 +10007720
7721/*[clinic input]
7722os.sched_yield
7723
7724Voluntarily relinquish the CPU.
7725[clinic start generated code]*/
7726
7727PyDoc_STRVAR(os_sched_yield__doc__,
7728"sched_yield($module, /)\n"
7729"--\n"
7730"\n"
7731"Voluntarily relinquish the CPU.");
7732
7733#define OS_SCHED_YIELD_METHODDEF \
7734 {"sched_yield", (PyCFunction)os_sched_yield, METH_NOARGS, os_sched_yield__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007735
7736static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007737os_sched_yield_impl(PyModuleDef *module);
7738
7739static PyObject *
7740os_sched_yield(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7741{
7742 return os_sched_yield_impl(module);
7743}
7744
7745static PyObject *
7746os_sched_yield_impl(PyModuleDef *module)
7747/*[clinic end generated code: output=9d2e5f29f1370324 input=e54d6f98189391d4]*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007748{
7749 if (sched_yield())
7750 return posix_error();
7751 Py_RETURN_NONE;
7752}
7753
Benjamin Peterson2740af82011-08-02 17:41:34 -05007754#ifdef HAVE_SCHED_SETAFFINITY
Antoine Pitrou84869872012-08-04 16:16:35 +02007755/* The minimum number of CPUs allocated in a cpu_set_t */
7756static const int NCPUS_START = sizeof(unsigned long) * CHAR_BIT;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007757
Larry Hastings2f936352014-08-05 14:04:04 +10007758/*[clinic input]
7759os.sched_setaffinity
7760 pid: pid_t
7761 mask : object
7762 /
7763
7764Set the CPU affinity of the process identified by pid to mask.
7765
7766mask should be an iterable of integers identifying CPUs.
7767[clinic start generated code]*/
7768
7769PyDoc_STRVAR(os_sched_setaffinity__doc__,
7770"sched_setaffinity($module, pid, mask, /)\n"
7771"--\n"
7772"\n"
7773"Set the CPU affinity of the process identified by pid to mask.\n"
7774"\n"
7775"mask should be an iterable of integers identifying CPUs.");
7776
7777#define OS_SCHED_SETAFFINITY_METHODDEF \
7778 {"sched_setaffinity", (PyCFunction)os_sched_setaffinity, METH_VARARGS, os_sched_setaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007779
7780static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007781os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask);
7782
7783static PyObject *
7784os_sched_setaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007785{
Larry Hastings2f936352014-08-05 14:04:04 +10007786 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007787 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007788 PyObject *mask;
7789
7790 if (!PyArg_ParseTuple(args,
7791 "" _Py_PARSE_PID "O:sched_setaffinity",
7792 &pid, &mask))
7793 goto exit;
7794 return_value = os_sched_setaffinity_impl(module, pid, mask);
7795
7796exit:
7797 return return_value;
7798}
7799
7800static PyObject *
7801os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask)
7802/*[clinic end generated code: output=5199929738130196 input=a0791a597c7085ba]*/
7803{
Antoine Pitrou84869872012-08-04 16:16:35 +02007804 int ncpus;
7805 size_t setsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007806 cpu_set_t *cpu_set = NULL;
7807 PyObject *iterator = NULL, *item;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007808
Larry Hastings2f936352014-08-05 14:04:04 +10007809 iterator = PyObject_GetIter(mask);
Antoine Pitrou84869872012-08-04 16:16:35 +02007810 if (iterator == NULL)
7811 return NULL;
7812
7813 ncpus = NCPUS_START;
7814 setsize = CPU_ALLOC_SIZE(ncpus);
Larry Hastings2f936352014-08-05 14:04:04 +10007815 cpu_set = CPU_ALLOC(ncpus);
7816 if (cpu_set == NULL) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007817 PyErr_NoMemory();
7818 goto error;
7819 }
Larry Hastings2f936352014-08-05 14:04:04 +10007820 CPU_ZERO_S(setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007821
7822 while ((item = PyIter_Next(iterator))) {
7823 long cpu;
7824 if (!PyLong_Check(item)) {
7825 PyErr_Format(PyExc_TypeError,
7826 "expected an iterator of ints, "
7827 "but iterator yielded %R",
7828 Py_TYPE(item));
7829 Py_DECREF(item);
7830 goto error;
7831 }
7832 cpu = PyLong_AsLong(item);
7833 Py_DECREF(item);
7834 if (cpu < 0) {
7835 if (!PyErr_Occurred())
7836 PyErr_SetString(PyExc_ValueError, "negative CPU number");
7837 goto error;
7838 }
7839 if (cpu > INT_MAX - 1) {
7840 PyErr_SetString(PyExc_OverflowError, "CPU number too large");
7841 goto error;
7842 }
7843 if (cpu >= ncpus) {
7844 /* Grow CPU mask to fit the CPU number */
7845 int newncpus = ncpus;
7846 cpu_set_t *newmask;
7847 size_t newsetsize;
7848 while (newncpus <= cpu) {
7849 if (newncpus > INT_MAX / 2)
7850 newncpus = cpu + 1;
7851 else
7852 newncpus = newncpus * 2;
7853 }
7854 newmask = CPU_ALLOC(newncpus);
7855 if (newmask == NULL) {
7856 PyErr_NoMemory();
7857 goto error;
7858 }
7859 newsetsize = CPU_ALLOC_SIZE(newncpus);
7860 CPU_ZERO_S(newsetsize, newmask);
Larry Hastings2f936352014-08-05 14:04:04 +10007861 memcpy(newmask, cpu_set, setsize);
7862 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007863 setsize = newsetsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007864 cpu_set = newmask;
Antoine Pitrou84869872012-08-04 16:16:35 +02007865 ncpus = newncpus;
7866 }
Larry Hastings2f936352014-08-05 14:04:04 +10007867 CPU_SET_S(cpu, setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007868 }
7869 Py_CLEAR(iterator);
7870
Larry Hastings2f936352014-08-05 14:04:04 +10007871 if (sched_setaffinity(pid, setsize, cpu_set)) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007872 posix_error();
7873 goto error;
7874 }
Larry Hastings2f936352014-08-05 14:04:04 +10007875 CPU_FREE(cpu_set);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007876 Py_RETURN_NONE;
Antoine Pitrou84869872012-08-04 16:16:35 +02007877
7878error:
Larry Hastings2f936352014-08-05 14:04:04 +10007879 if (cpu_set)
7880 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007881 Py_XDECREF(iterator);
7882 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007883}
7884
Larry Hastings2f936352014-08-05 14:04:04 +10007885
7886/*[clinic input]
7887os.sched_getaffinity
7888 pid: pid_t
7889 /
7890
7891Return the affinity of the process identified by pid.
7892
7893The affinity is returned as a set of CPU identifiers.
7894[clinic start generated code]*/
7895
7896PyDoc_STRVAR(os_sched_getaffinity__doc__,
7897"sched_getaffinity($module, pid, /)\n"
7898"--\n"
7899"\n"
7900"Return the affinity of the process identified by pid.\n"
7901"\n"
7902"The affinity is returned as a set of CPU identifiers.");
7903
7904#define OS_SCHED_GETAFFINITY_METHODDEF \
7905 {"sched_getaffinity", (PyCFunction)os_sched_getaffinity, METH_VARARGS, os_sched_getaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007906
7907static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007908os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid);
7909
7910static PyObject *
7911os_sched_getaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007912{
Larry Hastings2f936352014-08-05 14:04:04 +10007913 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007914 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007915
7916 if (!PyArg_ParseTuple(args,
7917 "" _Py_PARSE_PID ":sched_getaffinity",
7918 &pid))
7919 goto exit;
7920 return_value = os_sched_getaffinity_impl(module, pid);
7921
7922exit:
7923 return return_value;
7924}
7925
7926static PyObject *
7927os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid)
7928/*[clinic end generated code: output=7b273b0fca9830f0 input=eaf161936874b8a1]*/
7929{
Antoine Pitrou84869872012-08-04 16:16:35 +02007930 int cpu, ncpus, count;
7931 size_t setsize;
7932 cpu_set_t *mask = NULL;
7933 PyObject *res = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007934
Antoine Pitrou84869872012-08-04 16:16:35 +02007935 ncpus = NCPUS_START;
7936 while (1) {
7937 setsize = CPU_ALLOC_SIZE(ncpus);
7938 mask = CPU_ALLOC(ncpus);
7939 if (mask == NULL)
7940 return PyErr_NoMemory();
7941 if (sched_getaffinity(pid, setsize, mask) == 0)
7942 break;
7943 CPU_FREE(mask);
7944 if (errno != EINVAL)
7945 return posix_error();
7946 if (ncpus > INT_MAX / 2) {
7947 PyErr_SetString(PyExc_OverflowError, "could not allocate "
7948 "a large enough CPU set");
7949 return NULL;
7950 }
7951 ncpus = ncpus * 2;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007952 }
Antoine Pitrou84869872012-08-04 16:16:35 +02007953
7954 res = PySet_New(NULL);
7955 if (res == NULL)
7956 goto error;
7957 for (cpu = 0, count = CPU_COUNT_S(setsize, mask); count; cpu++) {
7958 if (CPU_ISSET_S(cpu, setsize, mask)) {
7959 PyObject *cpu_num = PyLong_FromLong(cpu);
7960 --count;
7961 if (cpu_num == NULL)
7962 goto error;
7963 if (PySet_Add(res, cpu_num)) {
7964 Py_DECREF(cpu_num);
7965 goto error;
7966 }
7967 Py_DECREF(cpu_num);
7968 }
7969 }
7970 CPU_FREE(mask);
7971 return res;
7972
7973error:
7974 if (mask)
7975 CPU_FREE(mask);
7976 Py_XDECREF(res);
7977 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007978}
7979
Benjamin Peterson2740af82011-08-02 17:41:34 -05007980#endif /* HAVE_SCHED_SETAFFINITY */
7981
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007982#endif /* HAVE_SCHED_H */
7983
Larry Hastings2f936352014-08-05 14:04:04 +10007984#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7985#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7986#endif /* OS_SCHED_GET_PRIORITY_MAX_METHODDEF */
7987
7988#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7989#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7990#endif /* OS_SCHED_GET_PRIORITY_MIN_METHODDEF */
7991
7992#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
7993#define OS_SCHED_GETSCHEDULER_METHODDEF
7994#endif /* OS_SCHED_GETSCHEDULER_METHODDEF */
7995
7996#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
7997#define OS_SCHED_SETSCHEDULER_METHODDEF
7998#endif /* OS_SCHED_SETSCHEDULER_METHODDEF */
7999
8000#ifndef OS_SCHED_GETPARAM_METHODDEF
8001#define OS_SCHED_GETPARAM_METHODDEF
8002#endif /* OS_SCHED_GETPARAM_METHODDEF */
8003
8004#ifndef OS_SCHED_SETPARAM_METHODDEF
8005#define OS_SCHED_SETPARAM_METHODDEF
8006#endif /* OS_SCHED_SETPARAM_METHODDEF */
8007
8008#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
8009#define OS_SCHED_RR_GET_INTERVAL_METHODDEF
8010#endif /* OS_SCHED_RR_GET_INTERVAL_METHODDEF */
8011
8012#ifndef OS_SCHED_YIELD_METHODDEF
8013#define OS_SCHED_YIELD_METHODDEF
8014#endif /* OS_SCHED_YIELD_METHODDEF */
8015
8016#ifndef OS_SCHED_SETAFFINITY_METHODDEF
8017#define OS_SCHED_SETAFFINITY_METHODDEF
8018#endif /* OS_SCHED_SETAFFINITY_METHODDEF */
8019
8020#ifndef OS_SCHED_GETAFFINITY_METHODDEF
8021#define OS_SCHED_GETAFFINITY_METHODDEF
8022#endif /* OS_SCHED_GETAFFINITY_METHODDEF */
8023
8024
Neal Norwitzb59798b2003-03-21 01:43:31 +00008025/* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
Neal Norwitz2deaddb2003-03-21 03:08:31 +00008026/* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
8027#if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
Neal Norwitzb59798b2003-03-21 01:43:31 +00008028#define DEV_PTY_FILE "/dev/ptc"
8029#define HAVE_DEV_PTMX
8030#else
8031#define DEV_PTY_FILE "/dev/ptmx"
8032#endif
8033
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008034#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
Fred Drake8cef4cf2000-06-28 16:40:38 +00008035#ifdef HAVE_PTY_H
8036#include <pty.h>
8037#else
8038#ifdef HAVE_LIBUTIL_H
8039#include <libutil.h>
Ronald Oussoren755740f2010-02-07 19:56:39 +00008040#else
8041#ifdef HAVE_UTIL_H
8042#include <util.h>
8043#endif /* HAVE_UTIL_H */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008044#endif /* HAVE_LIBUTIL_H */
8045#endif /* HAVE_PTY_H */
Martin v. Löwis14e73b12003-01-01 09:51:12 +00008046#ifdef HAVE_STROPTS_H
8047#include <stropts.h>
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008048#endif
8049#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008050
Larry Hastings2f936352014-08-05 14:04:04 +10008051
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008052#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
Larry Hastings2f936352014-08-05 14:04:04 +10008053/*[clinic input]
8054os.openpty
8055
8056Open a pseudo-terminal.
8057
8058Return a tuple of (master_fd, slave_fd) containing open file descriptors
8059for both the master and slave ends.
8060[clinic start generated code]*/
8061
8062PyDoc_STRVAR(os_openpty__doc__,
8063"openpty($module, /)\n"
8064"--\n"
8065"\n"
8066"Open a pseudo-terminal.\n"
8067"\n"
8068"Return a tuple of (master_fd, slave_fd) containing open file descriptors\n"
8069"for both the master and slave ends.");
8070
8071#define OS_OPENPTY_METHODDEF \
8072 {"openpty", (PyCFunction)os_openpty, METH_NOARGS, os_openpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008073
8074static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008075os_openpty_impl(PyModuleDef *module);
8076
8077static PyObject *
8078os_openpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8079{
8080 return os_openpty_impl(module);
8081}
8082
8083static PyObject *
8084os_openpty_impl(PyModuleDef *module)
8085/*[clinic end generated code: output=b12d3c1735468464 input=f3d99fd99e762907]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008086{
Victor Stinnerdaf45552013-08-28 00:53:59 +02008087 int master_fd = -1, slave_fd = -1;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008088#ifndef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008089 char * slave_name;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008090#endif
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008091#if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008092 PyOS_sighandler_t sig_saved;
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008093#ifdef sun
Victor Stinner8c62be82010-05-06 00:08:46 +00008094 extern char *ptsname(int fildes);
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008095#endif
8096#endif
Thomas Wouters70c21a12000-07-14 14:28:33 +00008097
Thomas Wouters70c21a12000-07-14 14:28:33 +00008098#ifdef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008099 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008100 goto posix_error;
8101
8102 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8103 goto error;
8104 if (_Py_set_inheritable(slave_fd, 0, NULL) < 0)
8105 goto error;
8106
Neal Norwitzb59798b2003-03-21 01:43:31 +00008107#elif defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008108 slave_name = _getpty(&master_fd, O_RDWR, 0666, 0);
8109 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008110 goto posix_error;
8111 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8112 goto error;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008113
Victor Stinnerdaf45552013-08-28 00:53:59 +02008114 slave_fd = _Py_open(slave_name, O_RDWR);
Victor Stinner8c62be82010-05-06 00:08:46 +00008115 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008116 goto posix_error;
8117
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008118#else
Victor Stinner000de532013-11-25 23:19:58 +01008119 master_fd = open(DEV_PTY_FILE, O_RDWR | O_NOCTTY); /* open master */
Victor Stinner8c62be82010-05-06 00:08:46 +00008120 if (master_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008121 goto posix_error;
8122
Victor Stinner8c62be82010-05-06 00:08:46 +00008123 sig_saved = PyOS_setsig(SIGCHLD, SIG_DFL);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008124
Victor Stinner8c62be82010-05-06 00:08:46 +00008125 /* change permission of slave */
8126 if (grantpt(master_fd) < 0) {
8127 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008128 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008129 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008130
Victor Stinner8c62be82010-05-06 00:08:46 +00008131 /* unlock slave */
8132 if (unlockpt(master_fd) < 0) {
8133 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008134 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008135 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008136
Victor Stinner8c62be82010-05-06 00:08:46 +00008137 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008138
Victor Stinner8c62be82010-05-06 00:08:46 +00008139 slave_name = ptsname(master_fd); /* get name of slave */
8140 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008141 goto posix_error;
8142
8143 slave_fd = _Py_open(slave_name, O_RDWR | O_NOCTTY); /* open slave */
Victor Stinner8c62be82010-05-06 00:08:46 +00008144 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008145 goto posix_error;
Victor Stinner000de532013-11-25 23:19:58 +01008146
8147 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8148 goto posix_error;
8149
Neal Norwitzb59798b2003-03-21 01:43:31 +00008150#if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
Victor Stinner8c62be82010-05-06 00:08:46 +00008151 ioctl(slave_fd, I_PUSH, "ptem"); /* push ptem */
8152 ioctl(slave_fd, I_PUSH, "ldterm"); /* push ldterm */
Neal Norwitz6700e472002-12-31 16:16:07 +00008153#ifndef __hpux
Victor Stinner8c62be82010-05-06 00:08:46 +00008154 ioctl(slave_fd, I_PUSH, "ttcompat"); /* push ttcompat */
Neal Norwitz6700e472002-12-31 16:16:07 +00008155#endif /* __hpux */
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008156#endif /* HAVE_CYGWIN */
Thomas Wouters1e0c2f42000-07-24 16:06:23 +00008157#endif /* HAVE_OPENPTY */
Thomas Wouters70c21a12000-07-14 14:28:33 +00008158
Victor Stinner8c62be82010-05-06 00:08:46 +00008159 return Py_BuildValue("(ii)", master_fd, slave_fd);
Thomas Wouters70c21a12000-07-14 14:28:33 +00008160
Victor Stinnerdaf45552013-08-28 00:53:59 +02008161posix_error:
8162 posix_error();
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008163#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008164error:
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008165#endif
Victor Stinnerdaf45552013-08-28 00:53:59 +02008166 if (master_fd != -1)
8167 close(master_fd);
8168 if (slave_fd != -1)
8169 close(slave_fd);
8170 return NULL;
Fred Drake8cef4cf2000-06-28 16:40:38 +00008171}
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008172#endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008173
Larry Hastings2f936352014-08-05 14:04:04 +10008174
Fred Drake8cef4cf2000-06-28 16:40:38 +00008175#ifdef HAVE_FORKPTY
Larry Hastings2f936352014-08-05 14:04:04 +10008176/*[clinic input]
8177os.forkpty
8178
8179Fork a new process with a new pseudo-terminal as controlling tty.
8180
8181Returns a tuple of (pid, master_fd).
8182Like fork(), return pid of 0 to the child process,
8183and pid of child to the parent process.
8184To both, return fd of newly opened pseudo-terminal.
8185[clinic start generated code]*/
8186
8187PyDoc_STRVAR(os_forkpty__doc__,
8188"forkpty($module, /)\n"
8189"--\n"
8190"\n"
8191"Fork a new process with a new pseudo-terminal as controlling tty.\n"
8192"\n"
8193"Returns a tuple of (pid, master_fd).\n"
8194"Like fork(), return pid of 0 to the child process,\n"
8195"and pid of child to the parent process.\n"
8196"To both, return fd of newly opened pseudo-terminal.");
8197
8198#define OS_FORKPTY_METHODDEF \
8199 {"forkpty", (PyCFunction)os_forkpty, METH_NOARGS, os_forkpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008200
8201static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008202os_forkpty_impl(PyModuleDef *module);
8203
8204static PyObject *
8205os_forkpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8206{
8207 return os_forkpty_impl(module);
8208}
8209
8210static PyObject *
8211os_forkpty_impl(PyModuleDef *module)
8212/*[clinic end generated code: output=d4f82958d2ed5cad input=f1f7f4bae3966010]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008213{
Victor Stinner8c62be82010-05-06 00:08:46 +00008214 int master_fd = -1, result = 0;
8215 pid_t pid;
Tim Peters5aa91602002-01-30 05:46:57 +00008216
Victor Stinner8c62be82010-05-06 00:08:46 +00008217 _PyImport_AcquireLock();
8218 pid = forkpty(&master_fd, NULL, NULL, NULL);
8219 if (pid == 0) {
8220 /* child: this clobbers and resets the import lock. */
8221 PyOS_AfterFork();
8222 } else {
8223 /* parent: release the import lock. */
8224 result = _PyImport_ReleaseLock();
8225 }
8226 if (pid == -1)
8227 return posix_error();
8228 if (result < 0) {
8229 /* Don't clobber the OSError if the fork failed. */
8230 PyErr_SetString(PyExc_RuntimeError,
8231 "not holding the import lock");
8232 return NULL;
8233 }
8234 return Py_BuildValue("(Ni)", PyLong_FromPid(pid), master_fd);
Fred Drake8cef4cf2000-06-28 16:40:38 +00008235}
Larry Hastings2f936352014-08-05 14:04:04 +10008236#endif /* HAVE_FORKPTY */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008237
Ross Lagerwall7807c352011-03-17 20:20:30 +02008238
Guido van Rossumad0ee831995-03-01 10:34:45 +00008239#ifdef HAVE_GETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10008240/*[clinic input]
8241os.getegid
8242
8243Return the current process's effective group id.
8244[clinic start generated code]*/
8245
8246PyDoc_STRVAR(os_getegid__doc__,
8247"getegid($module, /)\n"
8248"--\n"
8249"\n"
8250"Return the current process\'s effective group id.");
8251
8252#define OS_GETEGID_METHODDEF \
8253 {"getegid", (PyCFunction)os_getegid, METH_NOARGS, os_getegid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008254
Barry Warsaw53699e91996-12-10 23:23:01 +00008255static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008256os_getegid_impl(PyModuleDef *module);
8257
8258static PyObject *
8259os_getegid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8260{
8261 return os_getegid_impl(module);
8262}
8263
8264static PyObject *
8265os_getegid_impl(PyModuleDef *module)
8266/*[clinic end generated code: output=fd12c346fa41cccb input=1596f79ad1107d5d]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008267{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008268 return _PyLong_FromGid(getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008269}
Larry Hastings2f936352014-08-05 14:04:04 +10008270#endif /* HAVE_GETEGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008271
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008272
Guido van Rossumad0ee831995-03-01 10:34:45 +00008273#ifdef HAVE_GETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10008274/*[clinic input]
8275os.geteuid
8276
8277Return the current process's effective user id.
8278[clinic start generated code]*/
8279
8280PyDoc_STRVAR(os_geteuid__doc__,
8281"geteuid($module, /)\n"
8282"--\n"
8283"\n"
8284"Return the current process\'s effective user id.");
8285
8286#define OS_GETEUID_METHODDEF \
8287 {"geteuid", (PyCFunction)os_geteuid, METH_NOARGS, os_geteuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008288
Barry Warsaw53699e91996-12-10 23:23:01 +00008289static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008290os_geteuid_impl(PyModuleDef *module);
8291
8292static PyObject *
8293os_geteuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8294{
8295 return os_geteuid_impl(module);
8296}
8297
8298static PyObject *
8299os_geteuid_impl(PyModuleDef *module)
8300/*[clinic end generated code: output=03d98e07f4bc03d4 input=4644c662d3bd9f19]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008301{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008302 return _PyLong_FromUid(geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008303}
Larry Hastings2f936352014-08-05 14:04:04 +10008304#endif /* HAVE_GETEUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008305
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008306
Guido van Rossumad0ee831995-03-01 10:34:45 +00008307#ifdef HAVE_GETGID
Larry Hastings2f936352014-08-05 14:04:04 +10008308/*[clinic input]
8309os.getgid
8310
8311Return the current process's group id.
8312[clinic start generated code]*/
8313
8314PyDoc_STRVAR(os_getgid__doc__,
8315"getgid($module, /)\n"
8316"--\n"
8317"\n"
8318"Return the current process\'s group id.");
8319
8320#define OS_GETGID_METHODDEF \
8321 {"getgid", (PyCFunction)os_getgid, METH_NOARGS, os_getgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008322
Barry Warsaw53699e91996-12-10 23:23:01 +00008323static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008324os_getgid_impl(PyModuleDef *module);
8325
8326static PyObject *
8327os_getgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8328{
8329 return os_getgid_impl(module);
8330}
8331
8332static PyObject *
8333os_getgid_impl(PyModuleDef *module)
8334/*[clinic end generated code: output=07b0356121b8098d input=58796344cd87c0f6]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008335{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008336 return _PyLong_FromGid(getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008337}
Larry Hastings2f936352014-08-05 14:04:04 +10008338#endif /* HAVE_GETGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008339
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008340
Larry Hastings2f936352014-08-05 14:04:04 +10008341/*[clinic input]
8342os.getpid
8343
8344Return the current process id.
8345[clinic start generated code]*/
8346
8347PyDoc_STRVAR(os_getpid__doc__,
8348"getpid($module, /)\n"
8349"--\n"
8350"\n"
8351"Return the current process id.");
8352
8353#define OS_GETPID_METHODDEF \
8354 {"getpid", (PyCFunction)os_getpid, METH_NOARGS, os_getpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008355
Barry Warsaw53699e91996-12-10 23:23:01 +00008356static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008357os_getpid_impl(PyModuleDef *module);
8358
8359static PyObject *
8360os_getpid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8361{
8362 return os_getpid_impl(module);
8363}
8364
8365static PyObject *
8366os_getpid_impl(PyModuleDef *module)
8367/*[clinic end generated code: output=d63a01a3cebc573d input=5a9a00f0ab68aa00]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008368{
Victor Stinner8c62be82010-05-06 00:08:46 +00008369 return PyLong_FromPid(getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00008370}
8371
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008372#ifdef HAVE_GETGROUPLIST
Larry Hastings2f936352014-08-05 14:04:04 +10008373
8374/* AC 3.5: funny apple logic below */
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008375PyDoc_STRVAR(posix_getgrouplist__doc__,
8376"getgrouplist(user, group) -> list of groups to which a user belongs\n\n\
8377Returns a list of groups to which a user belongs.\n\n\
8378 user: username to lookup\n\
8379 group: base group id of the user");
8380
8381static PyObject *
8382posix_getgrouplist(PyObject *self, PyObject *args)
8383{
8384#ifdef NGROUPS_MAX
8385#define MAX_GROUPS NGROUPS_MAX
8386#else
8387 /* defined to be 16 on Solaris7, so this should be a small number */
8388#define MAX_GROUPS 64
8389#endif
8390
8391 const char *user;
8392 int i, ngroups;
8393 PyObject *list;
8394#ifdef __APPLE__
8395 int *groups, basegid;
8396#else
8397 gid_t *groups, basegid;
8398#endif
8399 ngroups = MAX_GROUPS;
8400
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008401#ifdef __APPLE__
8402 if (!PyArg_ParseTuple(args, "si:getgrouplist", &user, &basegid))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008403 return NULL;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008404#else
8405 if (!PyArg_ParseTuple(args, "sO&:getgrouplist", &user,
8406 _Py_Gid_Converter, &basegid))
8407 return NULL;
8408#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008409
8410#ifdef __APPLE__
8411 groups = PyMem_Malloc(ngroups * sizeof(int));
8412#else
8413 groups = PyMem_Malloc(ngroups * sizeof(gid_t));
8414#endif
8415 if (groups == NULL)
8416 return PyErr_NoMemory();
8417
8418 if (getgrouplist(user, basegid, groups, &ngroups) == -1) {
8419 PyMem_Del(groups);
8420 return posix_error();
8421 }
8422
8423 list = PyList_New(ngroups);
8424 if (list == NULL) {
8425 PyMem_Del(groups);
8426 return NULL;
8427 }
8428
8429 for (i = 0; i < ngroups; i++) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008430#ifdef __APPLE__
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008431 PyObject *o = PyLong_FromUnsignedLong((unsigned long)groups[i]);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008432#else
8433 PyObject *o = _PyLong_FromGid(groups[i]);
8434#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008435 if (o == NULL) {
8436 Py_DECREF(list);
8437 PyMem_Del(groups);
8438 return NULL;
8439 }
8440 PyList_SET_ITEM(list, i, o);
8441 }
8442
8443 PyMem_Del(groups);
8444
8445 return list;
8446}
Larry Hastings2f936352014-08-05 14:04:04 +10008447#endif /* HAVE_GETGROUPLIST */
8448
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008449
Fred Drakec9680921999-12-13 16:37:25 +00008450#ifdef HAVE_GETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10008451/*[clinic input]
8452os.getgroups
8453
8454Return list of supplemental group IDs for the process.
8455[clinic start generated code]*/
8456
8457PyDoc_STRVAR(os_getgroups__doc__,
8458"getgroups($module, /)\n"
8459"--\n"
8460"\n"
8461"Return list of supplemental group IDs for the process.");
8462
8463#define OS_GETGROUPS_METHODDEF \
8464 {"getgroups", (PyCFunction)os_getgroups, METH_NOARGS, os_getgroups__doc__},
Fred Drakec9680921999-12-13 16:37:25 +00008465
8466static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008467os_getgroups_impl(PyModuleDef *module);
8468
8469static PyObject *
8470os_getgroups(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8471{
8472 return os_getgroups_impl(module);
8473}
8474
8475static PyObject *
8476os_getgroups_impl(PyModuleDef *module)
8477/*[clinic end generated code: output=d9a3559b2e6f4ab8 input=d3f109412e6a155c]*/
Fred Drakec9680921999-12-13 16:37:25 +00008478{
8479 PyObject *result = NULL;
8480
Fred Drakec9680921999-12-13 16:37:25 +00008481#ifdef NGROUPS_MAX
8482#define MAX_GROUPS NGROUPS_MAX
8483#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008484 /* defined to be 16 on Solaris7, so this should be a small number */
Fred Drakec9680921999-12-13 16:37:25 +00008485#define MAX_GROUPS 64
8486#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008487 gid_t grouplist[MAX_GROUPS];
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008488
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008489 /* On MacOSX getgroups(2) can return more than MAX_GROUPS results
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008490 * This is a helper variable to store the intermediate result when
8491 * that happens.
8492 *
8493 * To keep the code readable the OSX behaviour is unconditional,
8494 * according to the POSIX spec this should be safe on all unix-y
8495 * systems.
8496 */
8497 gid_t* alt_grouplist = grouplist;
Victor Stinner8c62be82010-05-06 00:08:46 +00008498 int n;
Fred Drakec9680921999-12-13 16:37:25 +00008499
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008500#ifdef __APPLE__
8501 /* Issue #17557: As of OS X 10.8, getgroups(2) no longer raises EINVAL if
8502 * there are more groups than can fit in grouplist. Therefore, on OS X
8503 * always first call getgroups with length 0 to get the actual number
8504 * of groups.
8505 */
8506 n = getgroups(0, NULL);
8507 if (n < 0) {
8508 return posix_error();
8509 } else if (n <= MAX_GROUPS) {
8510 /* groups will fit in existing array */
8511 alt_grouplist = grouplist;
8512 } else {
8513 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8514 if (alt_grouplist == NULL) {
8515 errno = EINVAL;
8516 return posix_error();
8517 }
8518 }
8519
8520 n = getgroups(n, alt_grouplist);
8521 if (n == -1) {
8522 if (alt_grouplist != grouplist) {
8523 PyMem_Free(alt_grouplist);
8524 }
8525 return posix_error();
8526 }
8527#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008528 n = getgroups(MAX_GROUPS, grouplist);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008529 if (n < 0) {
8530 if (errno == EINVAL) {
8531 n = getgroups(0, NULL);
8532 if (n == -1) {
8533 return posix_error();
8534 }
8535 if (n == 0) {
8536 /* Avoid malloc(0) */
8537 alt_grouplist = grouplist;
8538 } else {
8539 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8540 if (alt_grouplist == NULL) {
8541 errno = EINVAL;
8542 return posix_error();
8543 }
8544 n = getgroups(n, alt_grouplist);
8545 if (n == -1) {
8546 PyMem_Free(alt_grouplist);
8547 return posix_error();
8548 }
8549 }
8550 } else {
8551 return posix_error();
8552 }
8553 }
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008554#endif
8555
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008556 result = PyList_New(n);
8557 if (result != NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008558 int i;
8559 for (i = 0; i < n; ++i) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008560 PyObject *o = _PyLong_FromGid(alt_grouplist[i]);
Victor Stinner8c62be82010-05-06 00:08:46 +00008561 if (o == NULL) {
Stefan Krah0e803b32010-11-26 16:16:47 +00008562 Py_DECREF(result);
8563 result = NULL;
8564 break;
Fred Drakec9680921999-12-13 16:37:25 +00008565 }
Victor Stinner8c62be82010-05-06 00:08:46 +00008566 PyList_SET_ITEM(result, i, o);
Fred Drakec9680921999-12-13 16:37:25 +00008567 }
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008568 }
8569
8570 if (alt_grouplist != grouplist) {
8571 PyMem_Free(alt_grouplist);
Victor Stinner8c62be82010-05-06 00:08:46 +00008572 }
Neal Norwitze241ce82003-02-17 18:17:05 +00008573
Fred Drakec9680921999-12-13 16:37:25 +00008574 return result;
8575}
Larry Hastings2f936352014-08-05 14:04:04 +10008576#endif /* HAVE_GETGROUPS */
Fred Drakec9680921999-12-13 16:37:25 +00008577
Antoine Pitroub7572f02009-12-02 20:46:48 +00008578#ifdef HAVE_INITGROUPS
8579PyDoc_STRVAR(posix_initgroups__doc__,
8580"initgroups(username, gid) -> None\n\n\
8581Call the system initgroups() to initialize the group access list with all of\n\
8582the groups of which the specified username is a member, plus the specified\n\
8583group id.");
8584
Larry Hastings2f936352014-08-05 14:04:04 +10008585/* AC 3.5: funny apple logic */
Antoine Pitroub7572f02009-12-02 20:46:48 +00008586static PyObject *
8587posix_initgroups(PyObject *self, PyObject *args)
8588{
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008589 PyObject *oname;
Victor Stinner8c62be82010-05-06 00:08:46 +00008590 char *username;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008591 int res;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008592#ifdef __APPLE__
8593 int gid;
8594#else
8595 gid_t gid;
8596#endif
Antoine Pitroub7572f02009-12-02 20:46:48 +00008597
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008598#ifdef __APPLE__
8599 if (!PyArg_ParseTuple(args, "O&i:initgroups",
8600 PyUnicode_FSConverter, &oname,
8601 &gid))
8602#else
8603 if (!PyArg_ParseTuple(args, "O&O&:initgroups",
8604 PyUnicode_FSConverter, &oname,
8605 _Py_Gid_Converter, &gid))
8606#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008607 return NULL;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008608 username = PyBytes_AS_STRING(oname);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008609
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008610 res = initgroups(username, gid);
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008611 Py_DECREF(oname);
8612 if (res == -1)
Victor Stinner8c62be82010-05-06 00:08:46 +00008613 return PyErr_SetFromErrno(PyExc_OSError);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008614
Victor Stinner8c62be82010-05-06 00:08:46 +00008615 Py_INCREF(Py_None);
8616 return Py_None;
Antoine Pitroub7572f02009-12-02 20:46:48 +00008617}
Larry Hastings2f936352014-08-05 14:04:04 +10008618#endif /* HAVE_INITGROUPS */
8619
Antoine Pitroub7572f02009-12-02 20:46:48 +00008620
Martin v. Löwis606edc12002-06-13 21:09:11 +00008621#ifdef HAVE_GETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10008622/*[clinic input]
8623os.getpgid
8624
8625 pid: pid_t
8626
8627Call the system call getpgid(), and return the result.
8628[clinic start generated code]*/
8629
8630PyDoc_STRVAR(os_getpgid__doc__,
8631"getpgid($module, /, pid)\n"
8632"--\n"
8633"\n"
8634"Call the system call getpgid(), and return the result.");
8635
8636#define OS_GETPGID_METHODDEF \
8637 {"getpgid", (PyCFunction)os_getpgid, METH_VARARGS|METH_KEYWORDS, os_getpgid__doc__},
Martin v. Löwis606edc12002-06-13 21:09:11 +00008638
8639static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008640os_getpgid_impl(PyModuleDef *module, pid_t pid);
8641
8642static PyObject *
8643os_getpgid(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis606edc12002-06-13 21:09:11 +00008644{
Larry Hastings2f936352014-08-05 14:04:04 +10008645 PyObject *return_value = NULL;
8646 static char *_keywords[] = {"pid", NULL};
8647 pid_t pid;
8648
8649 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
8650 "" _Py_PARSE_PID ":getpgid", _keywords,
8651 &pid))
8652 goto exit;
8653 return_value = os_getpgid_impl(module, pid);
8654
8655exit:
8656 return return_value;
8657}
8658
8659static PyObject *
8660os_getpgid_impl(PyModuleDef *module, pid_t pid)
8661/*[clinic end generated code: output=3db4ed686179160d input=39d710ae3baaf1c7]*/
8662{
8663 pid_t pgid = getpgid(pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00008664 if (pgid < 0)
8665 return posix_error();
8666 return PyLong_FromPid(pgid);
Martin v. Löwis606edc12002-06-13 21:09:11 +00008667}
8668#endif /* HAVE_GETPGID */
8669
8670
Guido van Rossumb6775db1994-08-01 11:34:53 +00008671#ifdef HAVE_GETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008672/*[clinic input]
8673os.getpgrp
8674
8675Return the current process group id.
8676[clinic start generated code]*/
8677
8678PyDoc_STRVAR(os_getpgrp__doc__,
8679"getpgrp($module, /)\n"
8680"--\n"
8681"\n"
8682"Return the current process group id.");
8683
8684#define OS_GETPGRP_METHODDEF \
8685 {"getpgrp", (PyCFunction)os_getpgrp, METH_NOARGS, os_getpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008686
Barry Warsaw53699e91996-12-10 23:23:01 +00008687static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008688os_getpgrp_impl(PyModuleDef *module);
8689
8690static PyObject *
8691os_getpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8692{
8693 return os_getpgrp_impl(module);
8694}
8695
8696static PyObject *
8697os_getpgrp_impl(PyModuleDef *module)
8698/*[clinic end generated code: output=3b0d3663ea054277 input=6846fb2bb9a3705e]*/
Guido van Rossum04814471991-06-04 20:23:49 +00008699{
Guido van Rossumb6775db1994-08-01 11:34:53 +00008700#ifdef GETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008701 return PyLong_FromPid(getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008702#else /* GETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008703 return PyLong_FromPid(getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008704#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00008705}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008706#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00008707
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008708
Guido van Rossumb6775db1994-08-01 11:34:53 +00008709#ifdef HAVE_SETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008710/*[clinic input]
8711os.setpgrp
8712
8713Make the current process the leader of its process group.
8714[clinic start generated code]*/
8715
8716PyDoc_STRVAR(os_setpgrp__doc__,
8717"setpgrp($module, /)\n"
8718"--\n"
8719"\n"
8720"Make the current process the leader of its process group.");
8721
8722#define OS_SETPGRP_METHODDEF \
8723 {"setpgrp", (PyCFunction)os_setpgrp, METH_NOARGS, os_setpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008724
Barry Warsaw53699e91996-12-10 23:23:01 +00008725static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008726os_setpgrp_impl(PyModuleDef *module);
8727
8728static PyObject *
8729os_setpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8730{
8731 return os_setpgrp_impl(module);
8732}
8733
8734static PyObject *
8735os_setpgrp_impl(PyModuleDef *module)
8736/*[clinic end generated code: output=8fbb0ee29ef6fb2d input=1f0619fcb5731e7e]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00008737{
Guido van Rossum64933891994-10-20 21:56:42 +00008738#ifdef SETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008739 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008740#else /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008741 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008742#endif /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008743 return posix_error();
8744 Py_INCREF(Py_None);
8745 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00008746}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008747#endif /* HAVE_SETPGRP */
8748
Guido van Rossumad0ee831995-03-01 10:34:45 +00008749#ifdef HAVE_GETPPID
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008750
8751#ifdef MS_WINDOWS
8752#include <tlhelp32.h>
8753
8754static PyObject*
8755win32_getppid()
8756{
8757 HANDLE snapshot;
8758 pid_t mypid;
8759 PyObject* result = NULL;
8760 BOOL have_record;
8761 PROCESSENTRY32 pe;
8762
8763 mypid = getpid(); /* This function never fails */
8764
8765 snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
8766 if (snapshot == INVALID_HANDLE_VALUE)
8767 return PyErr_SetFromWindowsErr(GetLastError());
8768
8769 pe.dwSize = sizeof(pe);
8770 have_record = Process32First(snapshot, &pe);
8771 while (have_record) {
8772 if (mypid == (pid_t)pe.th32ProcessID) {
8773 /* We could cache the ulong value in a static variable. */
8774 result = PyLong_FromPid((pid_t)pe.th32ParentProcessID);
8775 break;
8776 }
8777
8778 have_record = Process32Next(snapshot, &pe);
8779 }
8780
8781 /* If our loop exits and our pid was not found (result will be NULL)
8782 * then GetLastError will return ERROR_NO_MORE_FILES. This is an
8783 * error anyway, so let's raise it. */
8784 if (!result)
8785 result = PyErr_SetFromWindowsErr(GetLastError());
8786
8787 CloseHandle(snapshot);
8788
8789 return result;
8790}
8791#endif /*MS_WINDOWS*/
8792
Larry Hastings2f936352014-08-05 14:04:04 +10008793
8794/*[clinic input]
8795os.getppid
8796
8797Return the parent's process id.
8798
8799If the parent process has already exited, Windows machines will still
8800return its id; others systems will return the id of the 'init' process (1).
8801[clinic start generated code]*/
8802
8803PyDoc_STRVAR(os_getppid__doc__,
8804"getppid($module, /)\n"
8805"--\n"
8806"\n"
8807"Return the parent\'s process id.\n"
8808"\n"
8809"If the parent process has already exited, Windows machines will still\n"
8810"return its id; others systems will return the id of the \'init\' process (1).");
8811
8812#define OS_GETPPID_METHODDEF \
8813 {"getppid", (PyCFunction)os_getppid, METH_NOARGS, os_getppid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008814
Barry Warsaw53699e91996-12-10 23:23:01 +00008815static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008816os_getppid_impl(PyModuleDef *module);
8817
8818static PyObject *
8819os_getppid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8820{
8821 return os_getppid_impl(module);
8822}
8823
8824static PyObject *
8825os_getppid_impl(PyModuleDef *module)
8826/*[clinic end generated code: output=9ff3b387781edf3a input=e637cb87539c030e]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008827{
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008828#ifdef MS_WINDOWS
8829 return win32_getppid();
8830#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008831 return PyLong_FromPid(getppid());
Guido van Rossumad0ee831995-03-01 10:34:45 +00008832#endif
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008833}
8834#endif /* HAVE_GETPPID */
Guido van Rossum85e3b011991-06-03 12:42:10 +00008835
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008836
Fred Drake12c6e2d1999-12-14 21:25:03 +00008837#ifdef HAVE_GETLOGIN
Larry Hastings2f936352014-08-05 14:04:04 +10008838/*[clinic input]
8839os.getlogin
8840
8841Return the actual login name.
8842[clinic start generated code]*/
8843
8844PyDoc_STRVAR(os_getlogin__doc__,
8845"getlogin($module, /)\n"
8846"--\n"
8847"\n"
8848"Return the actual login name.");
8849
8850#define OS_GETLOGIN_METHODDEF \
8851 {"getlogin", (PyCFunction)os_getlogin, METH_NOARGS, os_getlogin__doc__},
Fred Drake12c6e2d1999-12-14 21:25:03 +00008852
8853static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008854os_getlogin_impl(PyModuleDef *module);
8855
8856static PyObject *
8857os_getlogin(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8858{
8859 return os_getlogin_impl(module);
8860}
8861
8862static PyObject *
8863os_getlogin_impl(PyModuleDef *module)
8864/*[clinic end generated code: output=ab6211dab104cbb2 input=2a21ab1e917163df]*/
Fred Drake12c6e2d1999-12-14 21:25:03 +00008865{
Victor Stinner8c62be82010-05-06 00:08:46 +00008866 PyObject *result = NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008867#ifdef MS_WINDOWS
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008868 wchar_t user_name[UNLEN + 1];
Victor Stinner63941882011-09-29 00:42:28 +02008869 DWORD num_chars = Py_ARRAY_LENGTH(user_name);
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008870
8871 if (GetUserNameW(user_name, &num_chars)) {
8872 /* num_chars is the number of unicode chars plus null terminator */
8873 result = PyUnicode_FromWideChar(user_name, num_chars - 1);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008874 }
8875 else
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008876 result = PyErr_SetFromWindowsErr(GetLastError());
8877#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008878 char *name;
8879 int old_errno = errno;
Fred Drake12c6e2d1999-12-14 21:25:03 +00008880
Victor Stinner8c62be82010-05-06 00:08:46 +00008881 errno = 0;
8882 name = getlogin();
8883 if (name == NULL) {
8884 if (errno)
Victor Stinnere039ffe2010-08-15 09:33:08 +00008885 posix_error();
Fred Drake12c6e2d1999-12-14 21:25:03 +00008886 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008887 PyErr_SetString(PyExc_OSError, "unable to determine login name");
Victor Stinner8c62be82010-05-06 00:08:46 +00008888 }
8889 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008890 result = PyUnicode_DecodeFSDefault(name);
Victor Stinner8c62be82010-05-06 00:08:46 +00008891 errno = old_errno;
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008892#endif
Fred Drake12c6e2d1999-12-14 21:25:03 +00008893 return result;
8894}
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008895#endif /* HAVE_GETLOGIN */
Fred Drake12c6e2d1999-12-14 21:25:03 +00008896
Larry Hastings2f936352014-08-05 14:04:04 +10008897
Guido van Rossumad0ee831995-03-01 10:34:45 +00008898#ifdef HAVE_GETUID
Larry Hastings2f936352014-08-05 14:04:04 +10008899/*[clinic input]
8900os.getuid
8901
8902Return the current process's user id.
8903[clinic start generated code]*/
8904
8905PyDoc_STRVAR(os_getuid__doc__,
8906"getuid($module, /)\n"
8907"--\n"
8908"\n"
8909"Return the current process\'s user id.");
8910
8911#define OS_GETUID_METHODDEF \
8912 {"getuid", (PyCFunction)os_getuid, METH_NOARGS, os_getuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008913
Barry Warsaw53699e91996-12-10 23:23:01 +00008914static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008915os_getuid_impl(PyModuleDef *module);
8916
8917static PyObject *
8918os_getuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8919{
8920 return os_getuid_impl(module);
8921}
8922
8923static PyObject *
8924os_getuid_impl(PyModuleDef *module)
8925/*[clinic end generated code: output=77e0dcf2e37d1e89 input=b53c8b35f110a516]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008926{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008927 return _PyLong_FromUid(getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008928}
Larry Hastings2f936352014-08-05 14:04:04 +10008929#endif /* HAVE_GETUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008930
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008931
Brian Curtineb24d742010-04-12 17:16:38 +00008932#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008933#define HAVE_KILL
8934#endif /* MS_WINDOWS */
8935
8936#ifdef HAVE_KILL
8937/*[clinic input]
8938os.kill
8939
8940 pid: pid_t
8941 signal: Py_ssize_t
8942 /
8943
8944Kill a process with a signal.
8945[clinic start generated code]*/
8946
8947PyDoc_STRVAR(os_kill__doc__,
8948"kill($module, pid, signal, /)\n"
8949"--\n"
8950"\n"
8951"Kill a process with a signal.");
8952
8953#define OS_KILL_METHODDEF \
8954 {"kill", (PyCFunction)os_kill, METH_VARARGS, os_kill__doc__},
Brian Curtineb24d742010-04-12 17:16:38 +00008955
8956static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008957os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal);
8958
8959static PyObject *
8960os_kill(PyModuleDef *module, PyObject *args)
8961{
8962 PyObject *return_value = NULL;
8963 pid_t pid;
8964 Py_ssize_t signal;
8965
8966 if (!PyArg_ParseTuple(args,
8967 "" _Py_PARSE_PID "n:kill",
8968 &pid, &signal))
8969 goto exit;
8970 return_value = os_kill_impl(module, pid, signal);
8971
8972exit:
8973 return return_value;
8974}
8975
8976static PyObject *
8977os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal)
8978/*[clinic end generated code: output=2f5c77920ed575e6 input=61a36b86ca275ab9]*/
8979#ifndef MS_WINDOWS
8980{
8981 if (kill(pid, (int)signal) == -1)
8982 return posix_error();
8983 Py_RETURN_NONE;
8984}
8985#else /* !MS_WINDOWS */
Brian Curtineb24d742010-04-12 17:16:38 +00008986{
Amaury Forgeot d'Arc0a589c92010-05-15 20:35:12 +00008987 PyObject *result;
Larry Hastings2f936352014-08-05 14:04:04 +10008988 DWORD sig = (DWORD)signal;
8989 DWORD err;
Victor Stinner8c62be82010-05-06 00:08:46 +00008990 HANDLE handle;
Brian Curtineb24d742010-04-12 17:16:38 +00008991
Victor Stinner8c62be82010-05-06 00:08:46 +00008992 /* Console processes which share a common console can be sent CTRL+C or
8993 CTRL+BREAK events, provided they handle said events. */
8994 if (sig == CTRL_C_EVENT || sig == CTRL_BREAK_EVENT) {
Richard Oudkerkac0ad882013-06-05 23:29:30 +01008995 if (GenerateConsoleCtrlEvent(sig, (DWORD)pid) == 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008996 err = GetLastError();
8997 PyErr_SetFromWindowsErr(err);
8998 }
8999 else
9000 Py_RETURN_NONE;
9001 }
Brian Curtineb24d742010-04-12 17:16:38 +00009002
Victor Stinner8c62be82010-05-06 00:08:46 +00009003 /* If the signal is outside of what GenerateConsoleCtrlEvent can use,
9004 attempt to open and terminate the process. */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01009005 handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, (DWORD)pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00009006 if (handle == NULL) {
9007 err = GetLastError();
9008 return PyErr_SetFromWindowsErr(err);
9009 }
Brian Curtineb24d742010-04-12 17:16:38 +00009010
Victor Stinner8c62be82010-05-06 00:08:46 +00009011 if (TerminateProcess(handle, sig) == 0) {
9012 err = GetLastError();
9013 result = PyErr_SetFromWindowsErr(err);
9014 } else {
9015 Py_INCREF(Py_None);
9016 result = Py_None;
9017 }
Brian Curtineb24d742010-04-12 17:16:38 +00009018
Victor Stinner8c62be82010-05-06 00:08:46 +00009019 CloseHandle(handle);
9020 return result;
Brian Curtineb24d742010-04-12 17:16:38 +00009021}
Larry Hastings2f936352014-08-05 14:04:04 +10009022#endif /* !MS_WINDOWS */
9023#endif /* HAVE_KILL */
9024
9025
9026#ifdef HAVE_KILLPG
9027/*[clinic input]
9028os.killpg
9029
9030 pgid: pid_t
9031 signal: int
9032 /
9033
9034Kill a process group with a signal.
9035[clinic start generated code]*/
9036
9037PyDoc_STRVAR(os_killpg__doc__,
9038"killpg($module, pgid, signal, /)\n"
9039"--\n"
9040"\n"
9041"Kill a process group with a signal.");
9042
9043#define OS_KILLPG_METHODDEF \
9044 {"killpg", (PyCFunction)os_killpg, METH_VARARGS, os_killpg__doc__},
9045
9046static PyObject *
9047os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal);
9048
9049static PyObject *
9050os_killpg(PyModuleDef *module, PyObject *args)
9051{
9052 PyObject *return_value = NULL;
9053 pid_t pgid;
9054 int signal;
9055
9056 if (!PyArg_ParseTuple(args,
9057 "" _Py_PARSE_PID "i:killpg",
9058 &pgid, &signal))
9059 goto exit;
9060 return_value = os_killpg_impl(module, pgid, signal);
9061
9062exit:
9063 return return_value;
9064}
9065
9066static PyObject *
9067os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal)
9068/*[clinic end generated code: output=0e05215d1c007e01 input=38b5449eb8faec19]*/
9069{
9070 /* XXX some man pages make the `pgid` parameter an int, others
9071 a pid_t. Since getpgrp() returns a pid_t, we assume killpg should
9072 take the same type. Moreover, pid_t is always at least as wide as
9073 int (else compilation of this module fails), which is safe. */
9074 if (killpg(pgid, signal) == -1)
9075 return posix_error();
9076 Py_RETURN_NONE;
9077}
9078#endif /* HAVE_KILLPG */
9079
Brian Curtineb24d742010-04-12 17:16:38 +00009080
Guido van Rossumc0125471996-06-28 18:55:32 +00009081#ifdef HAVE_PLOCK
Guido van Rossumc0125471996-06-28 18:55:32 +00009082#ifdef HAVE_SYS_LOCK_H
9083#include <sys/lock.h>
9084#endif
9085
Larry Hastings2f936352014-08-05 14:04:04 +10009086/*[clinic input]
9087os.plock
9088 op: int
9089 /
9090
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009091Lock program segments into memory.");
Larry Hastings2f936352014-08-05 14:04:04 +10009092[clinic start generated code]*/
9093
9094PyDoc_STRVAR(os_plock__doc__,
9095"plock($module, op, /)\n"
9096"--\n"
9097"\n"
9098"Lock program segments into memory.\");");
9099
9100#define OS_PLOCK_METHODDEF \
9101 {"plock", (PyCFunction)os_plock, METH_VARARGS, os_plock__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009102
Barry Warsaw53699e91996-12-10 23:23:01 +00009103static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009104os_plock_impl(PyModuleDef *module, int op);
9105
9106static PyObject *
9107os_plock(PyModuleDef *module, PyObject *args)
Guido van Rossumc0125471996-06-28 18:55:32 +00009108{
Larry Hastings2f936352014-08-05 14:04:04 +10009109 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009110 int op;
Larry Hastings2f936352014-08-05 14:04:04 +10009111
9112 if (!PyArg_ParseTuple(args,
9113 "i:plock",
9114 &op))
9115 goto exit;
9116 return_value = os_plock_impl(module, op);
9117
9118exit:
9119 return return_value;
9120}
9121
9122static PyObject *
9123os_plock_impl(PyModuleDef *module, int op)
9124/*[clinic end generated code: output=2744fe4b6e5f4dbc input=e6e5e348e1525f60]*/
9125{
Victor Stinner8c62be82010-05-06 00:08:46 +00009126 if (plock(op) == -1)
9127 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009128 Py_RETURN_NONE;
Guido van Rossumc0125471996-06-28 18:55:32 +00009129}
Larry Hastings2f936352014-08-05 14:04:04 +10009130#endif /* HAVE_PLOCK */
9131
Guido van Rossumc0125471996-06-28 18:55:32 +00009132
Guido van Rossumb6775db1994-08-01 11:34:53 +00009133#ifdef HAVE_SETUID
Larry Hastings2f936352014-08-05 14:04:04 +10009134/*[clinic input]
9135os.setuid
9136
9137 uid: uid_t
9138 /
9139
9140Set the current process's user id.
9141[clinic start generated code]*/
9142
9143PyDoc_STRVAR(os_setuid__doc__,
9144"setuid($module, uid, /)\n"
9145"--\n"
9146"\n"
9147"Set the current process\'s user id.");
9148
9149#define OS_SETUID_METHODDEF \
9150 {"setuid", (PyCFunction)os_setuid, METH_VARARGS, os_setuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009151
Barry Warsaw53699e91996-12-10 23:23:01 +00009152static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009153os_setuid_impl(PyModuleDef *module, uid_t uid);
9154
9155static PyObject *
9156os_setuid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009157{
Larry Hastings2f936352014-08-05 14:04:04 +10009158 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009159 uid_t uid;
Larry Hastings2f936352014-08-05 14:04:04 +10009160
9161 if (!PyArg_ParseTuple(args,
9162 "O&:setuid",
9163 _Py_Uid_Converter, &uid))
9164 goto exit;
9165 return_value = os_setuid_impl(module, uid);
9166
9167exit:
9168 return return_value;
9169}
9170
9171static PyObject *
9172os_setuid_impl(PyModuleDef *module, uid_t uid)
9173/*[clinic end generated code: output=aea344bc22ccf400 input=c921a3285aa22256]*/
9174{
Victor Stinner8c62be82010-05-06 00:08:46 +00009175 if (setuid(uid) < 0)
9176 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009177 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009178}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009179#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009180
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009181
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009182#ifdef HAVE_SETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10009183/*[clinic input]
9184os.seteuid
9185
9186 euid: uid_t
9187 /
9188
9189Set the current process's effective user id.
9190[clinic start generated code]*/
9191
9192PyDoc_STRVAR(os_seteuid__doc__,
9193"seteuid($module, euid, /)\n"
9194"--\n"
9195"\n"
9196"Set the current process\'s effective user id.");
9197
9198#define OS_SETEUID_METHODDEF \
9199 {"seteuid", (PyCFunction)os_seteuid, METH_VARARGS, os_seteuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009200
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009201static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009202os_seteuid_impl(PyModuleDef *module, uid_t euid);
9203
9204static PyObject *
9205os_seteuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009206{
Larry Hastings2f936352014-08-05 14:04:04 +10009207 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009208 uid_t euid;
Larry Hastings2f936352014-08-05 14:04:04 +10009209
9210 if (!PyArg_ParseTuple(args,
9211 "O&:seteuid",
9212 _Py_Uid_Converter, &euid))
9213 goto exit;
9214 return_value = os_seteuid_impl(module, euid);
9215
9216exit:
9217 return return_value;
9218}
9219
9220static PyObject *
9221os_seteuid_impl(PyModuleDef *module, uid_t euid)
9222/*[clinic end generated code: output=6e824cce4f3b8a5d input=ba93d927e4781aa9]*/
9223{
9224 if (seteuid(euid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009225 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009226 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009227}
9228#endif /* HAVE_SETEUID */
9229
Larry Hastings2f936352014-08-05 14:04:04 +10009230
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009231#ifdef HAVE_SETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10009232/*[clinic input]
9233os.setegid
9234
9235 egid: gid_t
9236 /
9237
9238Set the current process's effective group id.
9239[clinic start generated code]*/
9240
9241PyDoc_STRVAR(os_setegid__doc__,
9242"setegid($module, egid, /)\n"
9243"--\n"
9244"\n"
9245"Set the current process\'s effective group id.");
9246
9247#define OS_SETEGID_METHODDEF \
9248 {"setegid", (PyCFunction)os_setegid, METH_VARARGS, os_setegid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009249
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009250static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009251os_setegid_impl(PyModuleDef *module, gid_t egid);
9252
9253static PyObject *
9254os_setegid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009255{
Larry Hastings2f936352014-08-05 14:04:04 +10009256 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009257 gid_t egid;
Larry Hastings2f936352014-08-05 14:04:04 +10009258
9259 if (!PyArg_ParseTuple(args,
9260 "O&:setegid",
9261 _Py_Gid_Converter, &egid))
9262 goto exit;
9263 return_value = os_setegid_impl(module, egid);
9264
9265exit:
9266 return return_value;
9267}
9268
9269static PyObject *
9270os_setegid_impl(PyModuleDef *module, gid_t egid)
9271/*[clinic end generated code: output=80a32263a4d56a9c input=4080526d0ccd6ce3]*/
9272{
9273 if (setegid(egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009274 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009275 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009276}
9277#endif /* HAVE_SETEGID */
9278
Larry Hastings2f936352014-08-05 14:04:04 +10009279
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009280#ifdef HAVE_SETREUID
Larry Hastings2f936352014-08-05 14:04:04 +10009281/*[clinic input]
9282os.setreuid
9283
9284 ruid: uid_t
9285 euid: uid_t
9286 /
9287
9288Set the current process's real and effective user ids.
9289[clinic start generated code]*/
9290
9291PyDoc_STRVAR(os_setreuid__doc__,
9292"setreuid($module, ruid, euid, /)\n"
9293"--\n"
9294"\n"
9295"Set the current process\'s real and effective user ids.");
9296
9297#define OS_SETREUID_METHODDEF \
9298 {"setreuid", (PyCFunction)os_setreuid, METH_VARARGS, os_setreuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009299
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009300static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009301os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid);
9302
9303static PyObject *
9304os_setreuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009305{
Larry Hastings2f936352014-08-05 14:04:04 +10009306 PyObject *return_value = NULL;
9307 uid_t ruid;
9308 uid_t euid;
9309
9310 if (!PyArg_ParseTuple(args,
9311 "O&O&:setreuid",
9312 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid))
9313 goto exit;
9314 return_value = os_setreuid_impl(module, ruid, euid);
9315
9316exit:
9317 return return_value;
9318}
9319
9320static PyObject *
9321os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid)
9322/*[clinic end generated code: output=d7f226f943dad739 input=0ca8978de663880c]*/
9323{
Victor Stinner8c62be82010-05-06 00:08:46 +00009324 if (setreuid(ruid, euid) < 0) {
9325 return posix_error();
9326 } else {
9327 Py_INCREF(Py_None);
9328 return Py_None;
9329 }
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009330}
9331#endif /* HAVE_SETREUID */
9332
Larry Hastings2f936352014-08-05 14:04:04 +10009333
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009334#ifdef HAVE_SETREGID
Larry Hastings2f936352014-08-05 14:04:04 +10009335/*[clinic input]
9336os.setregid
9337
9338 rgid: gid_t
9339 egid: gid_t
9340 /
9341
9342Set the current process's real and effective group ids.
9343[clinic start generated code]*/
9344
9345PyDoc_STRVAR(os_setregid__doc__,
9346"setregid($module, rgid, egid, /)\n"
9347"--\n"
9348"\n"
9349"Set the current process\'s real and effective group ids.");
9350
9351#define OS_SETREGID_METHODDEF \
9352 {"setregid", (PyCFunction)os_setregid, METH_VARARGS, os_setregid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009353
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009354static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009355os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid);
9356
9357static PyObject *
9358os_setregid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009359{
Larry Hastings2f936352014-08-05 14:04:04 +10009360 PyObject *return_value = NULL;
9361 gid_t rgid;
9362 gid_t egid;
9363
9364 if (!PyArg_ParseTuple(args,
9365 "O&O&:setregid",
9366 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid))
9367 goto exit;
9368 return_value = os_setregid_impl(module, rgid, egid);
9369
9370exit:
9371 return return_value;
9372}
9373
9374static PyObject *
9375os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid)
9376/*[clinic end generated code: output=a82d9ab70f8e6562 input=c59499f72846db78]*/
9377{
9378 if (setregid(rgid, egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009379 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009380 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b22000-07-13 01:26:58 +00009381}
9382#endif /* HAVE_SETREGID */
9383
Larry Hastings2f936352014-08-05 14:04:04 +10009384
Guido van Rossumb6775db1994-08-01 11:34:53 +00009385#ifdef HAVE_SETGID
Larry Hastings2f936352014-08-05 14:04:04 +10009386/*[clinic input]
9387os.setgid
9388 gid: gid_t
9389 /
9390
9391Set the current process's group id.
9392[clinic start generated code]*/
9393
9394PyDoc_STRVAR(os_setgid__doc__,
9395"setgid($module, gid, /)\n"
9396"--\n"
9397"\n"
9398"Set the current process\'s group id.");
9399
9400#define OS_SETGID_METHODDEF \
9401 {"setgid", (PyCFunction)os_setgid, METH_VARARGS, os_setgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009402
Barry Warsaw53699e91996-12-10 23:23:01 +00009403static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009404os_setgid_impl(PyModuleDef *module, gid_t gid);
9405
9406static PyObject *
9407os_setgid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009408{
Larry Hastings2f936352014-08-05 14:04:04 +10009409 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009410 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10009411
9412 if (!PyArg_ParseTuple(args,
9413 "O&:setgid",
9414 _Py_Gid_Converter, &gid))
9415 goto exit;
9416 return_value = os_setgid_impl(module, gid);
9417
9418exit:
9419 return return_value;
9420}
9421
9422static PyObject *
9423os_setgid_impl(PyModuleDef *module, gid_t gid)
9424/*[clinic end generated code: output=08287886db435f23 input=27d30c4059045dc6]*/
9425{
Victor Stinner8c62be82010-05-06 00:08:46 +00009426 if (setgid(gid) < 0)
9427 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009428 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009429}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009430#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009431
Larry Hastings2f936352014-08-05 14:04:04 +10009432
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009433#ifdef HAVE_SETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10009434/*[clinic input]
9435os.setgroups
9436
9437 groups: object
9438 /
9439
9440Set the groups of the current process to list.
9441[clinic start generated code]*/
9442
9443PyDoc_STRVAR(os_setgroups__doc__,
9444"setgroups($module, groups, /)\n"
9445"--\n"
9446"\n"
9447"Set the groups of the current process to list.");
9448
9449#define OS_SETGROUPS_METHODDEF \
9450 {"setgroups", (PyCFunction)os_setgroups, METH_O, os_setgroups__doc__},
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009451
9452static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009453os_setgroups(PyModuleDef *module, PyObject *groups)
9454/*[clinic end generated code: output=0b8de65d5b3cda94 input=fa742ca3daf85a7e]*/
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009455{
Victor Stinner8c62be82010-05-06 00:08:46 +00009456 int i, len;
9457 gid_t grouplist[MAX_GROUPS];
Tim Peters5aa91602002-01-30 05:46:57 +00009458
Victor Stinner8c62be82010-05-06 00:08:46 +00009459 if (!PySequence_Check(groups)) {
9460 PyErr_SetString(PyExc_TypeError, "setgroups argument must be a sequence");
9461 return NULL;
9462 }
9463 len = PySequence_Size(groups);
9464 if (len > MAX_GROUPS) {
9465 PyErr_SetString(PyExc_ValueError, "too many groups");
9466 return NULL;
9467 }
9468 for(i = 0; i < len; i++) {
9469 PyObject *elem;
9470 elem = PySequence_GetItem(groups, i);
9471 if (!elem)
9472 return NULL;
9473 if (!PyLong_Check(elem)) {
9474 PyErr_SetString(PyExc_TypeError,
9475 "groups must be integers");
9476 Py_DECREF(elem);
9477 return NULL;
9478 } else {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009479 if (!_Py_Gid_Converter(elem, &grouplist[i])) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009480 Py_DECREF(elem);
9481 return NULL;
9482 }
9483 }
9484 Py_DECREF(elem);
9485 }
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009486
Victor Stinner8c62be82010-05-06 00:08:46 +00009487 if (setgroups(len, grouplist) < 0)
9488 return posix_error();
9489 Py_INCREF(Py_None);
9490 return Py_None;
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009491}
9492#endif /* HAVE_SETGROUPS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009493
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009494#if defined(HAVE_WAIT3) || defined(HAVE_WAIT4)
9495static PyObject *
Victor Stinner4195b5c2012-02-08 23:03:19 +01009496wait_helper(pid_t pid, int status, struct rusage *ru)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009497{
Victor Stinner8c62be82010-05-06 00:08:46 +00009498 PyObject *result;
9499 static PyObject *struct_rusage;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02009500 _Py_IDENTIFIER(struct_rusage);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009501
Victor Stinner8c62be82010-05-06 00:08:46 +00009502 if (pid == -1)
9503 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009504
Victor Stinner8c62be82010-05-06 00:08:46 +00009505 if (struct_rusage == NULL) {
9506 PyObject *m = PyImport_ImportModuleNoBlock("resource");
9507 if (m == NULL)
9508 return NULL;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02009509 struct_rusage = _PyObject_GetAttrId(m, &PyId_struct_rusage);
Victor Stinner8c62be82010-05-06 00:08:46 +00009510 Py_DECREF(m);
9511 if (struct_rusage == NULL)
9512 return NULL;
9513 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009514
Victor Stinner8c62be82010-05-06 00:08:46 +00009515 /* XXX(nnorwitz): Copied (w/mods) from resource.c, there should be only one. */
9516 result = PyStructSequence_New((PyTypeObject*) struct_rusage);
9517 if (!result)
9518 return NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009519
9520#ifndef doubletime
9521#define doubletime(TV) ((double)(TV).tv_sec + (TV).tv_usec * 0.000001)
9522#endif
9523
Victor Stinner8c62be82010-05-06 00:08:46 +00009524 PyStructSequence_SET_ITEM(result, 0,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009525 PyFloat_FromDouble(doubletime(ru->ru_utime)));
Victor Stinner8c62be82010-05-06 00:08:46 +00009526 PyStructSequence_SET_ITEM(result, 1,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009527 PyFloat_FromDouble(doubletime(ru->ru_stime)));
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009528#define SET_INT(result, index, value)\
Victor Stinner8c62be82010-05-06 00:08:46 +00009529 PyStructSequence_SET_ITEM(result, index, PyLong_FromLong(value))
9530 SET_INT(result, 2, ru->ru_maxrss);
9531 SET_INT(result, 3, ru->ru_ixrss);
9532 SET_INT(result, 4, ru->ru_idrss);
9533 SET_INT(result, 5, ru->ru_isrss);
9534 SET_INT(result, 6, ru->ru_minflt);
9535 SET_INT(result, 7, ru->ru_majflt);
9536 SET_INT(result, 8, ru->ru_nswap);
9537 SET_INT(result, 9, ru->ru_inblock);
9538 SET_INT(result, 10, ru->ru_oublock);
9539 SET_INT(result, 11, ru->ru_msgsnd);
9540 SET_INT(result, 12, ru->ru_msgrcv);
9541 SET_INT(result, 13, ru->ru_nsignals);
9542 SET_INT(result, 14, ru->ru_nvcsw);
9543 SET_INT(result, 15, ru->ru_nivcsw);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009544#undef SET_INT
9545
Victor Stinner8c62be82010-05-06 00:08:46 +00009546 if (PyErr_Occurred()) {
9547 Py_DECREF(result);
9548 return NULL;
9549 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009550
Victor Stinner8c62be82010-05-06 00:08:46 +00009551 return Py_BuildValue("NiN", PyLong_FromPid(pid), status, result);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009552}
9553#endif /* HAVE_WAIT3 || HAVE_WAIT4 */
9554
Larry Hastings2f936352014-08-05 14:04:04 +10009555
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009556#ifdef HAVE_WAIT3
Larry Hastings2f936352014-08-05 14:04:04 +10009557/*[clinic input]
9558os.wait3
9559
9560 options: int
9561Wait for completion of a child process.
9562
9563Returns a tuple of information about the child process:
9564 (pid, status, rusage)
9565[clinic start generated code]*/
9566
9567PyDoc_STRVAR(os_wait3__doc__,
9568"wait3($module, /, options)\n"
9569"--\n"
9570"\n"
9571"Wait for completion of a child process.\n"
9572"\n"
9573"Returns a tuple of information about the child process:\n"
9574" (pid, status, rusage)");
9575
9576#define OS_WAIT3_METHODDEF \
9577 {"wait3", (PyCFunction)os_wait3, METH_VARARGS|METH_KEYWORDS, os_wait3__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009578
9579static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009580os_wait3_impl(PyModuleDef *module, int options);
9581
9582static PyObject *
9583os_wait3(PyModuleDef *module, PyObject *args, PyObject *kwargs)
9584{
9585 PyObject *return_value = NULL;
9586 static char *_keywords[] = {"options", NULL};
9587 int options;
9588
9589 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9590 "i:wait3", _keywords,
9591 &options))
9592 goto exit;
9593 return_value = os_wait3_impl(module, options);
9594
9595exit:
9596 return return_value;
9597}
9598
9599static PyObject *
9600os_wait3_impl(PyModuleDef *module, int options)
9601/*[clinic end generated code: output=1f2a63b6a93cbb57 input=8ac4c56956b61710]*/
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009602{
Victor Stinner8c62be82010-05-06 00:08:46 +00009603 pid_t pid;
Victor Stinner8c62be82010-05-06 00:08:46 +00009604 struct rusage ru;
9605 WAIT_TYPE status;
9606 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009607
Victor Stinner8c62be82010-05-06 00:08:46 +00009608 Py_BEGIN_ALLOW_THREADS
9609 pid = wait3(&status, options, &ru);
9610 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009611
Victor Stinner4195b5c2012-02-08 23:03:19 +01009612 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009613}
9614#endif /* HAVE_WAIT3 */
9615
Larry Hastings2f936352014-08-05 14:04:04 +10009616
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009617#ifdef HAVE_WAIT4
Larry Hastings2f936352014-08-05 14:04:04 +10009618/*[clinic input]
9619
9620os.wait4
9621
9622 pid: pid_t
9623 options: int
9624
9625Wait for completion of a specific child process.
9626
9627Returns a tuple of information about the child process:
9628 (pid, status, rusage)
9629[clinic start generated code]*/
9630
9631PyDoc_STRVAR(os_wait4__doc__,
9632"wait4($module, /, pid, options)\n"
9633"--\n"
9634"\n"
9635"Wait for completion of a specific child process.\n"
9636"\n"
9637"Returns a tuple of information about the child process:\n"
9638" (pid, status, rusage)");
9639
9640#define OS_WAIT4_METHODDEF \
9641 {"wait4", (PyCFunction)os_wait4, METH_VARARGS|METH_KEYWORDS, os_wait4__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009642
9643static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009644os_wait4_impl(PyModuleDef *module, pid_t pid, int options);
9645
9646static PyObject *
9647os_wait4(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009648{
Larry Hastings2f936352014-08-05 14:04:04 +10009649 PyObject *return_value = NULL;
9650 static char *_keywords[] = {"pid", "options", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00009651 pid_t pid;
9652 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009653
9654 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9655 "" _Py_PARSE_PID "i:wait4", _keywords,
9656 &pid, &options))
9657 goto exit;
9658 return_value = os_wait4_impl(module, pid, options);
9659
9660exit:
9661 return return_value;
9662}
9663
9664static PyObject *
9665os_wait4_impl(PyModuleDef *module, pid_t pid, int options)
9666/*[clinic end generated code: output=20dfb05289d37dc6 input=d11deed0750600ba]*/
9667{
Victor Stinner8c62be82010-05-06 00:08:46 +00009668 struct rusage ru;
9669 WAIT_TYPE status;
9670 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009671
Victor Stinner8c62be82010-05-06 00:08:46 +00009672 Py_BEGIN_ALLOW_THREADS
9673 pid = wait4(pid, &status, options, &ru);
9674 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009675
Victor Stinner4195b5c2012-02-08 23:03:19 +01009676 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009677}
9678#endif /* HAVE_WAIT4 */
9679
Larry Hastings2f936352014-08-05 14:04:04 +10009680
Ross Lagerwall7807c352011-03-17 20:20:30 +02009681#if defined(HAVE_WAITID) && !defined(__APPLE__)
Larry Hastings2f936352014-08-05 14:04:04 +10009682/*[clinic input]
9683os.waitid
9684
9685 idtype: idtype_t
9686 Must be one of be P_PID, P_PGID or P_ALL.
9687 id: id_t
9688 The id to wait on.
9689 options: int
9690 Constructed from the ORing of one or more of WEXITED, WSTOPPED
9691 or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.
9692 /
9693
9694Returns the result of waiting for a process or processes.
9695
9696Returns either waitid_result or None if WNOHANG is specified and there are
9697no children in a waitable state.
9698[clinic start generated code]*/
9699
9700PyDoc_STRVAR(os_waitid__doc__,
9701"waitid($module, idtype, id, options, /)\n"
9702"--\n"
9703"\n"
9704"Returns the result of waiting for a process or processes.\n"
9705"\n"
9706" idtype\n"
9707" Must be one of be P_PID, P_PGID or P_ALL.\n"
9708" id\n"
9709" The id to wait on.\n"
9710" options\n"
9711" Constructed from the ORing of one or more of WEXITED, WSTOPPED\n"
9712" or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.\n"
9713"\n"
9714"Returns either waitid_result or None if WNOHANG is specified and there are\n"
9715"no children in a waitable state.");
9716
9717#define OS_WAITID_METHODDEF \
9718 {"waitid", (PyCFunction)os_waitid, METH_VARARGS, os_waitid__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02009719
9720static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009721os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options);
9722
9723static PyObject *
9724os_waitid(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02009725{
Larry Hastings2f936352014-08-05 14:04:04 +10009726 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009727 idtype_t idtype;
9728 id_t id;
Larry Hastings2f936352014-08-05 14:04:04 +10009729 int options;
9730
9731 if (!PyArg_ParseTuple(args,
9732 "i" _Py_PARSE_PID "i:waitid",
9733 &idtype, &id, &options))
9734 goto exit;
9735 return_value = os_waitid_impl(module, idtype, id, options);
9736
9737exit:
9738 return return_value;
9739}
9740
9741static PyObject *
9742os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options)
9743/*[clinic end generated code: output=fb44bf97f01021b2 input=d8e7f76e052b7920]*/
9744{
9745 PyObject *result;
9746 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009747 siginfo_t si;
9748 si.si_pid = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10009749
Ross Lagerwall7807c352011-03-17 20:20:30 +02009750 Py_BEGIN_ALLOW_THREADS
9751 res = waitid(idtype, id, &si, options);
9752 Py_END_ALLOW_THREADS
9753 if (res == -1)
9754 return posix_error();
9755
9756 if (si.si_pid == 0)
9757 Py_RETURN_NONE;
9758
9759 result = PyStructSequence_New(&WaitidResultType);
9760 if (!result)
9761 return NULL;
9762
9763 PyStructSequence_SET_ITEM(result, 0, PyLong_FromPid(si.si_pid));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009764 PyStructSequence_SET_ITEM(result, 1, _PyLong_FromUid(si.si_uid));
Ross Lagerwall7807c352011-03-17 20:20:30 +02009765 PyStructSequence_SET_ITEM(result, 2, PyLong_FromLong((long)(si.si_signo)));
9766 PyStructSequence_SET_ITEM(result, 3, PyLong_FromLong((long)(si.si_status)));
9767 PyStructSequence_SET_ITEM(result, 4, PyLong_FromLong((long)(si.si_code)));
9768 if (PyErr_Occurred()) {
9769 Py_DECREF(result);
9770 return NULL;
9771 }
9772
9773 return result;
9774}
Larry Hastings2f936352014-08-05 14:04:04 +10009775#endif /* defined(HAVE_WAITID) && !defined(__APPLE__) */
Ross Lagerwall7807c352011-03-17 20:20:30 +02009776
Larry Hastings2f936352014-08-05 14:04:04 +10009777
9778#if defined(HAVE_WAITPID)
9779/*[clinic input]
9780os.waitpid
9781 pid: pid_t
9782 options: int
9783 /
9784
9785Wait for completion of a given child process.
9786
9787Returns a tuple of information regarding the child process:
9788 (pid, status)
9789
9790The options argument is ignored on Windows.
9791[clinic start generated code]*/
9792
9793PyDoc_STRVAR(os_waitpid__doc__,
9794"waitpid($module, pid, options, /)\n"
9795"--\n"
9796"\n"
9797"Wait for completion of a given child process.\n"
9798"\n"
9799"Returns a tuple of information regarding the child process:\n"
9800" (pid, status)\n"
9801"\n"
9802"The options argument is ignored on Windows.");
9803
9804#define OS_WAITPID_METHODDEF \
9805 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009806
Barry Warsaw53699e91996-12-10 23:23:01 +00009807static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009808os_waitpid_impl(PyModuleDef *module, pid_t pid, int options);
9809
9810static PyObject *
9811os_waitpid(PyModuleDef *module, PyObject *args)
Guido van Rossum85e3b011991-06-03 12:42:10 +00009812{
Larry Hastings2f936352014-08-05 14:04:04 +10009813 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009814 pid_t pid;
9815 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009816
9817 if (!PyArg_ParseTuple(args,
9818 "" _Py_PARSE_PID "i:waitpid",
9819 &pid, &options))
9820 goto exit;
9821 return_value = os_waitpid_impl(module, pid, options);
9822
9823exit:
9824 return return_value;
9825}
9826
9827static PyObject *
9828os_waitpid_impl(PyModuleDef *module, pid_t pid, int options)
9829/*[clinic end generated code: output=095a6b00af70b7ac input=0bf1666b8758fda3]*/
9830{
Victor Stinner8c62be82010-05-06 00:08:46 +00009831 WAIT_TYPE status;
9832 WAIT_STATUS_INT(status) = 0;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00009833
Victor Stinner8c62be82010-05-06 00:08:46 +00009834 Py_BEGIN_ALLOW_THREADS
9835 pid = waitpid(pid, &status, options);
9836 Py_END_ALLOW_THREADS
9837 if (pid == -1)
9838 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009839
Victor Stinner8c62be82010-05-06 00:08:46 +00009840 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum21803b81992-08-09 12:55:27 +00009841}
Tim Petersab034fa2002-02-01 11:27:43 +00009842#elif defined(HAVE_CWAIT)
Tim Petersab034fa2002-02-01 11:27:43 +00009843/* MS C has a variant of waitpid() that's usable for most purposes. */
Larry Hastings2f936352014-08-05 14:04:04 +10009844/*[clinic input]
9845os.waitpid
9846 pid: Py_intptr_t
9847 options: int
9848 /
9849
9850Wait for completion of a given process.
9851
9852Returns a tuple of information regarding the process:
9853 (pid, status << 8)
9854
9855The options argument is ignored on Windows.
9856[clinic start generated code]*/
9857
9858PyDoc_STRVAR(os_waitpid__doc__,
9859"waitpid($module, pid, options, /)\n"
9860"--\n"
9861"\n"
9862"Wait for completion of a given process.\n"
9863"\n"
9864"Returns a tuple of information regarding the process:\n"
9865" (pid, status << 8)\n"
9866"\n"
9867"The options argument is ignored on Windows.");
9868
9869#define OS_WAITPID_METHODDEF \
9870 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Tim Petersab034fa2002-02-01 11:27:43 +00009871
9872static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009873os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options);
Tim Petersab034fa2002-02-01 11:27:43 +00009874
Larry Hastings2f936352014-08-05 14:04:04 +10009875static PyObject *
9876os_waitpid(PyModuleDef *module, PyObject *args)
9877{
9878 PyObject *return_value = NULL;
9879 Py_intptr_t pid;
9880 int options;
9881
9882 if (!PyArg_ParseTuple(args,
9883 "" _Py_PARSE_INTPTR "i:waitpid",
9884 &pid, &options))
9885 goto exit;
9886 return_value = os_waitpid_impl(module, pid, options);
9887
9888exit:
9889 return return_value;
9890}
9891
9892static PyObject *
9893os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options)
9894/*[clinic end generated code: output=c20b95b15ad44a3a input=444c8f51cca5b862]*/
9895{
9896 int status;
9897
Victor Stinner8c62be82010-05-06 00:08:46 +00009898 Py_BEGIN_ALLOW_THREADS
9899 pid = _cwait(&status, pid, options);
9900 Py_END_ALLOW_THREADS
9901 if (pid == -1)
9902 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009903
Victor Stinner8c62be82010-05-06 00:08:46 +00009904 /* shift the status left a byte so this is more like the POSIX waitpid */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01009905 return Py_BuildValue(_Py_PARSE_INTPTR "i", pid, status << 8);
Tim Petersab034fa2002-02-01 11:27:43 +00009906}
Larry Hastings2f936352014-08-05 14:04:04 +10009907#endif
9908
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009909
Guido van Rossumad0ee831995-03-01 10:34:45 +00009910#ifdef HAVE_WAIT
Larry Hastings2f936352014-08-05 14:04:04 +10009911/*[clinic input]
9912os.wait
9913
9914Wait for completion of a child process.
9915
9916Returns a tuple of information about the child process:
9917 (pid, status)
9918[clinic start generated code]*/
9919
9920PyDoc_STRVAR(os_wait__doc__,
9921"wait($module, /)\n"
9922"--\n"
9923"\n"
9924"Wait for completion of a child process.\n"
9925"\n"
9926"Returns a tuple of information about the child process:\n"
9927" (pid, status)");
9928
9929#define OS_WAIT_METHODDEF \
9930 {"wait", (PyCFunction)os_wait, METH_NOARGS, os_wait__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009931
Barry Warsaw53699e91996-12-10 23:23:01 +00009932static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009933os_wait_impl(PyModuleDef *module);
9934
9935static PyObject *
9936os_wait(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
9937{
9938 return os_wait_impl(module);
9939}
9940
9941static PyObject *
9942os_wait_impl(PyModuleDef *module)
9943/*[clinic end generated code: output=2a83a9d164e7e6a8 input=03b0182d4a4700ce]*/
Guido van Rossum21803b81992-08-09 12:55:27 +00009944{
Victor Stinner8c62be82010-05-06 00:08:46 +00009945 pid_t pid;
9946 WAIT_TYPE status;
9947 WAIT_STATUS_INT(status) = 0;
Neal Norwitze241ce82003-02-17 18:17:05 +00009948
Victor Stinner8c62be82010-05-06 00:08:46 +00009949 Py_BEGIN_ALLOW_THREADS
9950 pid = wait(&status);
9951 Py_END_ALLOW_THREADS
9952 if (pid == -1)
9953 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009954
Victor Stinner8c62be82010-05-06 00:08:46 +00009955 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum85e3b011991-06-03 12:42:10 +00009956}
Larry Hastings2f936352014-08-05 14:04:04 +10009957#endif /* HAVE_WAIT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00009958
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009959
Larry Hastings9cf065c2012-06-22 16:30:09 -07009960#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
9961PyDoc_STRVAR(readlink__doc__,
9962"readlink(path, *, dir_fd=None) -> path\n\n\
9963Return a string representing the path to which the symbolic link points.\n\
9964\n\
9965If dir_fd is not None, it should be a file descriptor open to a directory,\n\
9966 and path should be relative; path will then be relative to that directory.\n\
9967dir_fd may not be implemented on your platform.\n\
9968 If it is unavailable, using it will raise a NotImplementedError.");
Mark Hammondc2e85bd2002-10-03 05:10:39 +00009969#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009970
Guido van Rossumb6775db1994-08-01 11:34:53 +00009971#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009972
Larry Hastings2f936352014-08-05 14:04:04 +10009973/* AC 3.5: merge win32 and not together */
Barry Warsaw53699e91996-12-10 23:23:01 +00009974static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07009975posix_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009976{
Larry Hastings9cf065c2012-06-22 16:30:09 -07009977 path_t path;
9978 int dir_fd = DEFAULT_DIR_FD;
9979 char buffer[MAXPATHLEN];
9980 ssize_t length;
9981 PyObject *return_value = NULL;
9982 static char *keywords[] = {"path", "dir_fd", NULL};
Thomas Wouters89f507f2006-12-13 04:49:30 +00009983
Larry Hastings9cf065c2012-06-22 16:30:09 -07009984 memset(&path, 0, sizeof(path));
Victor Stinner292c8352012-10-30 02:17:38 +01009985 path.function_name = "readlink";
Larry Hastings9cf065c2012-06-22 16:30:09 -07009986 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O&|$O&:readlink", keywords,
9987 path_converter, &path,
Larry Hastings2f936352014-08-05 14:04:04 +10009988 READLINKAT_DIR_FD_CONVERTER, &dir_fd))
Victor Stinner8c62be82010-05-06 00:08:46 +00009989 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00009990
Victor Stinner8c62be82010-05-06 00:08:46 +00009991 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07009992#ifdef HAVE_READLINKAT
9993 if (dir_fd != DEFAULT_DIR_FD)
9994 length = readlinkat(dir_fd, path.narrow, buffer, sizeof(buffer));
Victor Stinnera45598a2010-05-14 16:35:39 +00009995 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07009996#endif
9997 length = readlink(path.narrow, buffer, sizeof(buffer));
9998 Py_END_ALLOW_THREADS
9999
10000 if (length < 0) {
Victor Stinner292c8352012-10-30 02:17:38 +010010001 return_value = path_error(&path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010002 goto exit;
10003 }
10004
10005 if (PyUnicode_Check(path.object))
10006 return_value = PyUnicode_DecodeFSDefaultAndSize(buffer, length);
10007 else
10008 return_value = PyBytes_FromStringAndSize(buffer, length);
10009exit:
10010 path_cleanup(&path);
10011 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000010012}
Larry Hastings9cf065c2012-06-22 16:30:09 -070010013
Guido van Rossumb6775db1994-08-01 11:34:53 +000010014#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000010015
Larry Hastings2f936352014-08-05 14:04:04 +100010016#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
10017
10018static PyObject *
10019win_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
10020{
10021 wchar_t *path;
10022 DWORD n_bytes_returned;
10023 DWORD io_result;
10024 PyObject *po, *result;
10025 int dir_fd;
10026 HANDLE reparse_point_handle;
10027
10028 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
10029 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
10030 wchar_t *print_name;
10031
10032 static char *keywords[] = {"path", "dir_fd", NULL};
10033
10034 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "U|$O&:readlink", keywords,
10035 &po,
10036 dir_fd_unavailable, &dir_fd
10037 ))
10038 return NULL;
10039
10040 path = PyUnicode_AsUnicode(po);
10041 if (path == NULL)
10042 return NULL;
10043
10044 /* First get a handle to the reparse point */
10045 Py_BEGIN_ALLOW_THREADS
10046 reparse_point_handle = CreateFileW(
10047 path,
10048 0,
10049 0,
10050 0,
10051 OPEN_EXISTING,
10052 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS,
10053 0);
10054 Py_END_ALLOW_THREADS
10055
10056 if (reparse_point_handle==INVALID_HANDLE_VALUE)
10057 return win32_error_object("readlink", po);
10058
10059 Py_BEGIN_ALLOW_THREADS
10060 /* New call DeviceIoControl to read the reparse point */
10061 io_result = DeviceIoControl(
10062 reparse_point_handle,
10063 FSCTL_GET_REPARSE_POINT,
10064 0, 0, /* in buffer */
10065 target_buffer, sizeof(target_buffer),
10066 &n_bytes_returned,
10067 0 /* we're not using OVERLAPPED_IO */
10068 );
10069 CloseHandle(reparse_point_handle);
10070 Py_END_ALLOW_THREADS
10071
10072 if (io_result==0)
10073 return win32_error_object("readlink", po);
10074
10075 if (rdb->ReparseTag != IO_REPARSE_TAG_SYMLINK)
10076 {
10077 PyErr_SetString(PyExc_ValueError,
10078 "not a symbolic link");
10079 return NULL;
10080 }
10081 print_name = rdb->SymbolicLinkReparseBuffer.PathBuffer +
10082 rdb->SymbolicLinkReparseBuffer.PrintNameOffset;
10083
10084 result = PyUnicode_FromWideChar(print_name,
10085 rdb->SymbolicLinkReparseBuffer.PrintNameLength/2);
10086 return result;
10087}
10088
10089#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
10090
10091
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010092
Larry Hastings9cf065c2012-06-22 16:30:09 -070010093#ifdef HAVE_SYMLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070010094
10095#if defined(MS_WINDOWS)
10096
10097/* Grab CreateSymbolicLinkW dynamically from kernel32 */
10098static DWORD (CALLBACK *Py_CreateSymbolicLinkW)(LPWSTR, LPWSTR, DWORD) = NULL;
10099static DWORD (CALLBACK *Py_CreateSymbolicLinkA)(LPSTR, LPSTR, DWORD) = NULL;
Victor Stinner31b3b922013-06-05 01:49:17 +020010100
Larry Hastings9cf065c2012-06-22 16:30:09 -070010101static int
Victor Stinner31b3b922013-06-05 01:49:17 +020010102check_CreateSymbolicLink(void)
Larry Hastings9cf065c2012-06-22 16:30:09 -070010103{
10104 HINSTANCE hKernel32;
10105 /* only recheck */
10106 if (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA)
10107 return 1;
10108 hKernel32 = GetModuleHandleW(L"KERNEL32");
10109 *(FARPROC*)&Py_CreateSymbolicLinkW = GetProcAddress(hKernel32,
10110 "CreateSymbolicLinkW");
10111 *(FARPROC*)&Py_CreateSymbolicLinkA = GetProcAddress(hKernel32,
10112 "CreateSymbolicLinkA");
10113 return (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA);
10114}
10115
Victor Stinner31b3b922013-06-05 01:49:17 +020010116/* Remove the last portion of the path */
10117static void
10118_dirnameW(WCHAR *path)
10119{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010120 WCHAR *ptr;
10121
10122 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010123 for(ptr = path + wcslen(path); ptr != path; ptr--) {
Victor Stinner072318b2013-06-05 02:07:46 +020010124 if (*ptr == L'\\' || *ptr == L'/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010125 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010126 }
10127 *ptr = 0;
10128}
10129
Victor Stinner31b3b922013-06-05 01:49:17 +020010130/* Remove the last portion of the path */
10131static void
10132_dirnameA(char *path)
10133{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010134 char *ptr;
10135
10136 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010137 for(ptr = path + strlen(path); ptr != path; ptr--) {
10138 if (*ptr == '\\' || *ptr == '/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010139 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010140 }
10141 *ptr = 0;
10142}
10143
Victor Stinner31b3b922013-06-05 01:49:17 +020010144/* Is this path absolute? */
10145static int
10146_is_absW(const WCHAR *path)
10147{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010148 return path[0] == L'\\' || path[0] == L'/' || path[1] == L':';
10149
10150}
10151
Victor Stinner31b3b922013-06-05 01:49:17 +020010152/* Is this path absolute? */
10153static int
10154_is_absA(const char *path)
10155{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010156 return path[0] == '\\' || path[0] == '/' || path[1] == ':';
10157
10158}
10159
Victor Stinner31b3b922013-06-05 01:49:17 +020010160/* join root and rest with a backslash */
10161static void
10162_joinW(WCHAR *dest_path, const WCHAR *root, const WCHAR *rest)
10163{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010164 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010165
Victor Stinner31b3b922013-06-05 01:49:17 +020010166 if (_is_absW(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010167 wcscpy(dest_path, rest);
10168 return;
10169 }
10170
10171 root_len = wcslen(root);
10172
10173 wcscpy(dest_path, root);
10174 if(root_len) {
Victor Stinner31b3b922013-06-05 01:49:17 +020010175 dest_path[root_len] = L'\\';
10176 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010177 }
10178 wcscpy(dest_path+root_len, rest);
10179}
10180
Victor Stinner31b3b922013-06-05 01:49:17 +020010181/* join root and rest with a backslash */
10182static void
10183_joinA(char *dest_path, const char *root, const char *rest)
10184{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010185 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010186
Victor Stinner31b3b922013-06-05 01:49:17 +020010187 if (_is_absA(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010188 strcpy(dest_path, rest);
10189 return;
10190 }
10191
10192 root_len = strlen(root);
10193
10194 strcpy(dest_path, root);
10195 if(root_len) {
10196 dest_path[root_len] = '\\';
Victor Stinner31b3b922013-06-05 01:49:17 +020010197 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010198 }
10199 strcpy(dest_path+root_len, rest);
10200}
10201
Victor Stinner31b3b922013-06-05 01:49:17 +020010202/* Return True if the path at src relative to dest is a directory */
10203static int
10204_check_dirW(WCHAR *src, WCHAR *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010205{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010206 WIN32_FILE_ATTRIBUTE_DATA src_info;
10207 WCHAR dest_parent[MAX_PATH];
10208 WCHAR src_resolved[MAX_PATH] = L"";
10209
10210 /* dest_parent = os.path.dirname(dest) */
10211 wcscpy(dest_parent, dest);
10212 _dirnameW(dest_parent);
10213 /* src_resolved = os.path.join(dest_parent, src) */
10214 _joinW(src_resolved, dest_parent, src);
10215 return (
10216 GetFileAttributesExW(src_resolved, GetFileExInfoStandard, &src_info)
10217 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10218 );
10219}
10220
Victor Stinner31b3b922013-06-05 01:49:17 +020010221/* Return True if the path at src relative to dest is a directory */
10222static int
10223_check_dirA(char *src, char *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010224{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010225 WIN32_FILE_ATTRIBUTE_DATA src_info;
10226 char dest_parent[MAX_PATH];
10227 char src_resolved[MAX_PATH] = "";
10228
10229 /* dest_parent = os.path.dirname(dest) */
10230 strcpy(dest_parent, dest);
Victor Stinner5a436762013-06-05 00:37:12 +020010231 _dirnameA(dest_parent);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010232 /* src_resolved = os.path.join(dest_parent, src) */
Victor Stinner5a436762013-06-05 00:37:12 +020010233 _joinA(src_resolved, dest_parent, src);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010234 return (
10235 GetFileAttributesExA(src_resolved, GetFileExInfoStandard, &src_info)
10236 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10237 );
10238}
Larry Hastings9cf065c2012-06-22 16:30:09 -070010239#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010240
Larry Hastings2f936352014-08-05 14:04:04 +100010241
10242/*[clinic input]
10243os.symlink
10244 src: path_t
10245 dst: path_t
10246 target_is_directory: bool = False
10247 *
10248 dir_fd: dir_fd(requires='symlinkat')=None
10249
10250# "symlink(src, dst, target_is_directory=False, *, dir_fd=None)\n\n\
10251
10252Create a symbolic link pointing to src named dst.
10253
10254target_is_directory is required on Windows if the target is to be
10255 interpreted as a directory. (On Windows, symlink requires
10256 Windows 6.0 or greater, and raises a NotImplementedError otherwise.)
10257 target_is_directory is ignored on non-Windows platforms.
10258
10259If dir_fd is not None, it should be a file descriptor open to a directory,
10260 and path should be relative; path will then be relative to that directory.
10261dir_fd may not be implemented on your platform.
10262 If it is unavailable, using it will raise a NotImplementedError.
10263
10264[clinic start generated code]*/
10265
10266PyDoc_STRVAR(os_symlink__doc__,
10267"symlink($module, /, src, dst, target_is_directory=False, *, dir_fd=None)\n"
10268"--\n"
10269"\n"
10270"Create a symbolic link pointing to src named dst.\n"
10271"\n"
10272"target_is_directory is required on Windows if the target is to be\n"
10273" interpreted as a directory. (On Windows, symlink requires\n"
10274" Windows 6.0 or greater, and raises a NotImplementedError otherwise.)\n"
10275" target_is_directory is ignored on non-Windows platforms.\n"
10276"\n"
10277"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10278" and path should be relative; path will then be relative to that directory.\n"
10279"dir_fd may not be implemented on your platform.\n"
10280" If it is unavailable, using it will raise a NotImplementedError.");
10281
10282#define OS_SYMLINK_METHODDEF \
10283 {"symlink", (PyCFunction)os_symlink, METH_VARARGS|METH_KEYWORDS, os_symlink__doc__},
10284
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010285static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010286os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd);
10287
10288static PyObject *
10289os_symlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010290{
Larry Hastings2f936352014-08-05 14:04:04 +100010291 PyObject *return_value = NULL;
10292 static char *_keywords[] = {"src", "dst", "target_is_directory", "dir_fd", NULL};
10293 path_t src = PATH_T_INITIALIZE("symlink", "src", 0, 0);
10294 path_t dst = PATH_T_INITIALIZE("symlink", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010295 int target_is_directory = 0;
Larry Hastings2f936352014-08-05 14:04:04 +100010296 int dir_fd = DEFAULT_DIR_FD;
10297
10298 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10299 "O&O&|p$O&:symlink", _keywords,
10300 path_converter, &src, path_converter, &dst, &target_is_directory, SYMLINKAT_DIR_FD_CONVERTER, &dir_fd))
10301 goto exit;
10302 return_value = os_symlink_impl(module, &src, &dst, target_is_directory, dir_fd);
10303
10304exit:
10305 /* Cleanup for src */
10306 path_cleanup(&src);
10307 /* Cleanup for dst */
10308 path_cleanup(&dst);
10309
10310 return return_value;
10311}
10312
10313static PyObject *
10314os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd)
10315/*[clinic end generated code: output=1a31e6d88aafe9b6 input=e820ec4472547bc3]*/
10316{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010317#ifdef MS_WINDOWS
10318 DWORD result;
10319#else
10320 int result;
10321#endif
10322
Larry Hastings9cf065c2012-06-22 16:30:09 -070010323#ifdef MS_WINDOWS
10324 if (!check_CreateSymbolicLink()) {
10325 PyErr_SetString(PyExc_NotImplementedError,
10326 "CreateSymbolicLink functions not found");
Larry Hastings2f936352014-08-05 14:04:04 +100010327 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010328 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010329 if (!win32_can_symlink) {
10330 PyErr_SetString(PyExc_OSError, "symbolic link privilege not held");
Larry Hastings2f936352014-08-05 14:04:04 +100010331 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010332 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010333#endif
10334
Larry Hastings2f936352014-08-05 14:04:04 +100010335 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070010336 PyErr_SetString(PyExc_ValueError,
10337 "symlink: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +100010338 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010339 }
10340
10341#ifdef MS_WINDOWS
Jason R. Coombs3a092862013-05-27 23:21:28 -040010342
Larry Hastings9cf065c2012-06-22 16:30:09 -070010343 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010344 if (dst->wide) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010345 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010346 target_is_directory |= _check_dirW(src->wide, dst->wide);
10347 result = Py_CreateSymbolicLinkW(dst->wide, src->wide,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010348 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010349 }
10350 else {
10351 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010352 target_is_directory |= _check_dirA(src->narrow, dst->narrow);
10353 result = Py_CreateSymbolicLinkA(dst->narrow, src->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010354 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010355 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010356 Py_END_ALLOW_THREADS
10357
Larry Hastings2f936352014-08-05 14:04:04 +100010358 if (!result)
10359 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010360
10361#else
10362
10363 Py_BEGIN_ALLOW_THREADS
10364#if HAVE_SYMLINKAT
10365 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010366 result = symlinkat(src->narrow, dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010367 else
10368#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010369 result = symlink(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010370 Py_END_ALLOW_THREADS
10371
Larry Hastings2f936352014-08-05 14:04:04 +100010372 if (result)
10373 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010374#endif
10375
Larry Hastings2f936352014-08-05 14:04:04 +100010376 Py_RETURN_NONE;
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010377}
10378#endif /* HAVE_SYMLINK */
10379
Larry Hastings9cf065c2012-06-22 16:30:09 -070010380
Brian Curtind40e6f72010-07-08 21:39:08 +000010381
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010382
Larry Hastings605a62d2012-06-24 04:33:36 -070010383static PyStructSequence_Field times_result_fields[] = {
10384 {"user", "user time"},
10385 {"system", "system time"},
10386 {"children_user", "user time of children"},
10387 {"children_system", "system time of children"},
10388 {"elapsed", "elapsed time since an arbitrary point in the past"},
10389 {NULL}
10390};
10391
10392PyDoc_STRVAR(times_result__doc__,
10393"times_result: Result from os.times().\n\n\
10394This object may be accessed either as a tuple of\n\
10395 (user, system, children_user, children_system, elapsed),\n\
10396or via the attributes user, system, children_user, children_system,\n\
10397and elapsed.\n\
10398\n\
10399See os.times for more information.");
10400
10401static PyStructSequence_Desc times_result_desc = {
10402 "times_result", /* name */
10403 times_result__doc__, /* doc */
10404 times_result_fields,
10405 5
10406};
10407
10408static PyTypeObject TimesResultType;
10409
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010410#ifdef MS_WINDOWS
10411#define HAVE_TIMES /* mandatory, for the method table */
10412#endif
Larry Hastings605a62d2012-06-24 04:33:36 -070010413
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010414#ifdef HAVE_TIMES
Larry Hastings605a62d2012-06-24 04:33:36 -070010415
10416static PyObject *
10417build_times_result(double user, double system,
10418 double children_user, double children_system,
10419 double elapsed)
10420{
10421 PyObject *value = PyStructSequence_New(&TimesResultType);
10422 if (value == NULL)
10423 return NULL;
10424
10425#define SET(i, field) \
10426 { \
10427 PyObject *o = PyFloat_FromDouble(field); \
10428 if (!o) { \
10429 Py_DECREF(value); \
10430 return NULL; \
10431 } \
10432 PyStructSequence_SET_ITEM(value, i, o); \
10433 } \
10434
10435 SET(0, user);
10436 SET(1, system);
10437 SET(2, children_user);
10438 SET(3, children_system);
10439 SET(4, elapsed);
10440
10441#undef SET
10442
10443 return value;
10444}
10445
Larry Hastings605a62d2012-06-24 04:33:36 -070010446
Larry Hastings2f936352014-08-05 14:04:04 +100010447#ifndef MS_WINDOWS
10448#define NEED_TICKS_PER_SECOND
10449static long ticks_per_second = -1;
10450#endif /* MS_WINDOWS */
10451
10452/*[clinic input]
10453os.times
10454
10455Return a collection containing process timing information.
10456
10457The object returned behaves like a named tuple with these fields:
10458 (utime, stime, cutime, cstime, elapsed_time)
10459All fields are floating point numbers.
10460[clinic start generated code]*/
10461
10462PyDoc_STRVAR(os_times__doc__,
10463"times($module, /)\n"
10464"--\n"
10465"\n"
10466"Return a collection containing process timing information.\n"
10467"\n"
10468"The object returned behaves like a named tuple with these fields:\n"
10469" (utime, stime, cutime, cstime, elapsed_time)\n"
10470"All fields are floating point numbers.");
10471
10472#define OS_TIMES_METHODDEF \
10473 {"times", (PyCFunction)os_times, METH_NOARGS, os_times__doc__},
10474
Barry Warsaw53699e91996-12-10 23:23:01 +000010475static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010476os_times_impl(PyModuleDef *module);
10477
10478static PyObject *
10479os_times(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10480{
10481 return os_times_impl(module);
10482}
10483
10484static PyObject *
10485os_times_impl(PyModuleDef *module)
10486/*[clinic end generated code: output=b86896d031a9b768 input=2bf9df3d6ab2e48b]*/
10487#ifdef MS_WINDOWS
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010488{
Victor Stinner8c62be82010-05-06 00:08:46 +000010489 FILETIME create, exit, kernel, user;
10490 HANDLE hProc;
10491 hProc = GetCurrentProcess();
10492 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
10493 /* The fields of a FILETIME structure are the hi and lo part
10494 of a 64-bit value expressed in 100 nanosecond units.
10495 1e7 is one second in such units; 1e-7 the inverse.
10496 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
10497 */
Larry Hastings605a62d2012-06-24 04:33:36 -070010498 return build_times_result(
Victor Stinner8c62be82010-05-06 00:08:46 +000010499 (double)(user.dwHighDateTime*429.4967296 +
10500 user.dwLowDateTime*1e-7),
10501 (double)(kernel.dwHighDateTime*429.4967296 +
10502 kernel.dwLowDateTime*1e-7),
10503 (double)0,
10504 (double)0,
10505 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010506}
Larry Hastings2f936352014-08-05 14:04:04 +100010507#else /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010508{
Larry Hastings2f936352014-08-05 14:04:04 +100010509
10510
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010511 struct tms t;
10512 clock_t c;
10513 errno = 0;
10514 c = times(&t);
10515 if (c == (clock_t) -1)
10516 return posix_error();
10517 return build_times_result(
10518 (double)t.tms_utime / ticks_per_second,
10519 (double)t.tms_stime / ticks_per_second,
10520 (double)t.tms_cutime / ticks_per_second,
10521 (double)t.tms_cstime / ticks_per_second,
10522 (double)c / ticks_per_second);
10523}
Larry Hastings2f936352014-08-05 14:04:04 +100010524#endif /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010525#endif /* HAVE_TIMES */
10526
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010527
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010528#ifdef HAVE_GETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010529/*[clinic input]
10530os.getsid
10531
10532 pid: pid_t
10533 /
10534
10535Call the system call getsid(pid) and return the result.
10536[clinic start generated code]*/
10537
10538PyDoc_STRVAR(os_getsid__doc__,
10539"getsid($module, pid, /)\n"
10540"--\n"
10541"\n"
10542"Call the system call getsid(pid) and return the result.");
10543
10544#define OS_GETSID_METHODDEF \
10545 {"getsid", (PyCFunction)os_getsid, METH_VARARGS, os_getsid__doc__},
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010546
10547static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010548os_getsid_impl(PyModuleDef *module, pid_t pid);
10549
10550static PyObject *
10551os_getsid(PyModuleDef *module, PyObject *args)
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010552{
Larry Hastings2f936352014-08-05 14:04:04 +100010553 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010554 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010555
10556 if (!PyArg_ParseTuple(args,
10557 "" _Py_PARSE_PID ":getsid",
10558 &pid))
10559 goto exit;
10560 return_value = os_getsid_impl(module, pid);
10561
10562exit:
10563 return return_value;
10564}
10565
10566static PyObject *
10567os_getsid_impl(PyModuleDef *module, pid_t pid)
10568/*[clinic end generated code: output=ea8390f395f4e0e1 input=eeb2b923a30ce04e]*/
10569{
Victor Stinner8c62be82010-05-06 00:08:46 +000010570 int sid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010571 sid = getsid(pid);
10572 if (sid < 0)
10573 return posix_error();
10574 return PyLong_FromLong((long)sid);
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010575}
10576#endif /* HAVE_GETSID */
10577
10578
Guido van Rossumb6775db1994-08-01 11:34:53 +000010579#ifdef HAVE_SETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010580/*[clinic input]
10581os.setsid
10582
10583Call the system call setsid().
10584[clinic start generated code]*/
10585
10586PyDoc_STRVAR(os_setsid__doc__,
10587"setsid($module, /)\n"
10588"--\n"
10589"\n"
10590"Call the system call setsid().");
10591
10592#define OS_SETSID_METHODDEF \
10593 {"setsid", (PyCFunction)os_setsid, METH_NOARGS, os_setsid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010594
Barry Warsaw53699e91996-12-10 23:23:01 +000010595static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010596os_setsid_impl(PyModuleDef *module);
10597
10598static PyObject *
10599os_setsid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10600{
10601 return os_setsid_impl(module);
10602}
10603
10604static PyObject *
10605os_setsid_impl(PyModuleDef *module)
10606/*[clinic end generated code: output=2a9a1435d8d764d5 input=5fff45858e2f0776]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +000010607{
Victor Stinner8c62be82010-05-06 00:08:46 +000010608 if (setsid() < 0)
10609 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010610 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010611}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010612#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010613
Larry Hastings2f936352014-08-05 14:04:04 +100010614
Guido van Rossumb6775db1994-08-01 11:34:53 +000010615#ifdef HAVE_SETPGID
Larry Hastings2f936352014-08-05 14:04:04 +100010616/*[clinic input]
10617os.setpgid
10618
10619 pid: pid_t
10620 pgrp: pid_t
10621 /
10622
10623Call the system call setpgid(pid, pgrp).
10624[clinic start generated code]*/
10625
10626PyDoc_STRVAR(os_setpgid__doc__,
10627"setpgid($module, pid, pgrp, /)\n"
10628"--\n"
10629"\n"
10630"Call the system call setpgid(pid, pgrp).");
10631
10632#define OS_SETPGID_METHODDEF \
10633 {"setpgid", (PyCFunction)os_setpgid, METH_VARARGS, os_setpgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010634
Barry Warsaw53699e91996-12-10 23:23:01 +000010635static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010636os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp);
10637
10638static PyObject *
10639os_setpgid(PyModuleDef *module, PyObject *args)
Guido van Rossumc2670a01992-09-13 20:07:29 +000010640{
Larry Hastings2f936352014-08-05 14:04:04 +100010641 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010642 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010643 pid_t pgrp;
10644
10645 if (!PyArg_ParseTuple(args,
10646 "" _Py_PARSE_PID "" _Py_PARSE_PID ":setpgid",
10647 &pid, &pgrp))
10648 goto exit;
10649 return_value = os_setpgid_impl(module, pid, pgrp);
10650
10651exit:
10652 return return_value;
10653}
10654
10655static PyObject *
10656os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp)
10657/*[clinic end generated code: output=7ad79b725f890e1f input=fceb395eca572e1a]*/
10658{
Victor Stinner8c62be82010-05-06 00:08:46 +000010659 if (setpgid(pid, pgrp) < 0)
10660 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010661 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010662}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010663#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010664
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010665
Guido van Rossumb6775db1994-08-01 11:34:53 +000010666#ifdef HAVE_TCGETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010667/*[clinic input]
10668os.tcgetpgrp
10669
10670 fd: int
10671 /
10672
10673Return the process group associated with the terminal specified by fd.
10674[clinic start generated code]*/
10675
10676PyDoc_STRVAR(os_tcgetpgrp__doc__,
10677"tcgetpgrp($module, fd, /)\n"
10678"--\n"
10679"\n"
10680"Return the process group associated with the terminal specified by fd.");
10681
10682#define OS_TCGETPGRP_METHODDEF \
10683 {"tcgetpgrp", (PyCFunction)os_tcgetpgrp, METH_VARARGS, os_tcgetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010684
Barry Warsaw53699e91996-12-10 23:23:01 +000010685static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010686os_tcgetpgrp_impl(PyModuleDef *module, int fd);
10687
10688static PyObject *
10689os_tcgetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010690{
Larry Hastings2f936352014-08-05 14:04:04 +100010691 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010692 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100010693
10694 if (!PyArg_ParseTuple(args,
10695 "i:tcgetpgrp",
10696 &fd))
10697 goto exit;
10698 return_value = os_tcgetpgrp_impl(module, fd);
10699
10700exit:
10701 return return_value;
10702}
10703
10704static PyObject *
10705os_tcgetpgrp_impl(PyModuleDef *module, int fd)
10706/*[clinic end generated code: output=abcf52ed4c8d22cb input=7f6c18eac10ada86]*/
10707{
10708 pid_t pgid = tcgetpgrp(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +000010709 if (pgid < 0)
10710 return posix_error();
10711 return PyLong_FromPid(pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +000010712}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010713#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +000010714
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010715
Guido van Rossumb6775db1994-08-01 11:34:53 +000010716#ifdef HAVE_TCSETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010717/*[clinic input]
10718os.tcsetpgrp
10719
10720 fd: int
10721 pgid: pid_t
10722 /
10723
10724Set the process group associated with the terminal specified by fd.
10725[clinic start generated code]*/
10726
10727PyDoc_STRVAR(os_tcsetpgrp__doc__,
10728"tcsetpgrp($module, fd, pgid, /)\n"
10729"--\n"
10730"\n"
10731"Set the process group associated with the terminal specified by fd.");
10732
10733#define OS_TCSETPGRP_METHODDEF \
10734 {"tcsetpgrp", (PyCFunction)os_tcsetpgrp, METH_VARARGS, os_tcsetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010735
Barry Warsaw53699e91996-12-10 23:23:01 +000010736static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010737os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid);
10738
10739static PyObject *
10740os_tcsetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010741{
Larry Hastings2f936352014-08-05 14:04:04 +100010742 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010743 int fd;
10744 pid_t pgid;
Larry Hastings2f936352014-08-05 14:04:04 +100010745
10746 if (!PyArg_ParseTuple(args,
10747 "i" _Py_PARSE_PID ":tcsetpgrp",
10748 &fd, &pgid))
10749 goto exit;
10750 return_value = os_tcsetpgrp_impl(module, fd, pgid);
10751
10752exit:
10753 return return_value;
10754}
10755
10756static PyObject *
10757os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid)
10758/*[clinic end generated code: output=76f9bb8fd00f20f5 input=5bdc997c6a619020]*/
10759{
Victor Stinner8c62be82010-05-06 00:08:46 +000010760 if (tcsetpgrp(fd, pgid) < 0)
10761 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010762 Py_RETURN_NONE;
Guido van Rossum7066dd71992-09-17 17:54:56 +000010763}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010764#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +000010765
Guido van Rossum687dd131993-05-17 08:34:16 +000010766/* Functions acting on file descriptors */
10767
Victor Stinnerdaf45552013-08-28 00:53:59 +020010768#ifdef O_CLOEXEC
10769extern int _Py_open_cloexec_works;
10770#endif
10771
Larry Hastings2f936352014-08-05 14:04:04 +100010772
10773/*[clinic input]
10774os.open -> int
10775 path: path_t
10776 flags: int
10777 mode: int = 0o777
10778 *
10779 dir_fd: dir_fd(requires='openat') = None
10780
10781# "open(path, flags, mode=0o777, *, dir_fd=None)\n\n\
10782
10783Open a file for low level IO. Returns a file descriptor (integer).
10784
10785If dir_fd is not None, it should be a file descriptor open to a directory,
10786 and path should be relative; path will then be relative to that directory.
10787dir_fd may not be implemented on your platform.
10788 If it is unavailable, using it will raise a NotImplementedError.
10789[clinic start generated code]*/
10790
10791PyDoc_STRVAR(os_open__doc__,
10792"open($module, /, path, flags, mode=511, *, dir_fd=None)\n"
10793"--\n"
10794"\n"
10795"Open a file for low level IO. Returns a file descriptor (integer).\n"
10796"\n"
10797"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10798" and path should be relative; path will then be relative to that directory.\n"
10799"dir_fd may not be implemented on your platform.\n"
10800" If it is unavailable, using it will raise a NotImplementedError.");
10801
10802#define OS_OPEN_METHODDEF \
10803 {"open", (PyCFunction)os_open, METH_VARARGS|METH_KEYWORDS, os_open__doc__},
10804
10805static int
10806os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010807
Barry Warsaw53699e91996-12-10 23:23:01 +000010808static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010809os_open(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000010810{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010811 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100010812 static char *_keywords[] = {"path", "flags", "mode", "dir_fd", NULL};
10813 path_t path = PATH_T_INITIALIZE("open", "path", 0, 0);
10814 int flags;
10815 int mode = 511;
10816 int dir_fd = DEFAULT_DIR_FD;
10817 int _return_value;
10818
10819 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10820 "O&i|i$O&:open", _keywords,
10821 path_converter, &path, &flags, &mode, OPENAT_DIR_FD_CONVERTER, &dir_fd))
10822 goto exit;
10823 _return_value = os_open_impl(module, &path, flags, mode, dir_fd);
10824 if ((_return_value == -1) && PyErr_Occurred())
10825 goto exit;
10826 return_value = PyLong_FromLong((long)_return_value);
10827
10828exit:
10829 /* Cleanup for path */
10830 path_cleanup(&path);
10831
10832 return return_value;
10833}
10834
10835static int
10836os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd)
10837/*[clinic end generated code: output=05b68fc4ed5e29c9 input=ad8623b29acd2934]*/
10838{
10839 int fd;
10840
Victor Stinnerdaf45552013-08-28 00:53:59 +020010841#ifdef O_CLOEXEC
10842 int *atomic_flag_works = &_Py_open_cloexec_works;
10843#elif !defined(MS_WINDOWS)
10844 int *atomic_flag_works = NULL;
10845#endif
Mark Hammondc2e85bd2002-10-03 05:10:39 +000010846
Victor Stinnerdaf45552013-08-28 00:53:59 +020010847#ifdef MS_WINDOWS
10848 flags |= O_NOINHERIT;
10849#elif defined(O_CLOEXEC)
10850 flags |= O_CLOEXEC;
10851#endif
10852
Victor Stinner8c62be82010-05-06 00:08:46 +000010853 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -070010854#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100010855 if (path->wide)
10856 fd = _wopen(path->wide, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010857 else
10858#endif
10859#ifdef HAVE_OPENAT
10860 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010861 fd = openat(dir_fd, path->narrow, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010862 else
10863#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010864 fd = open(path->narrow, flags, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +000010865 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +000010866
Larry Hastings9cf065c2012-06-22 16:30:09 -070010867 if (fd == -1) {
Larry Hastings2f936352014-08-05 14:04:04 +100010868 PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
10869 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010870 }
10871
Victor Stinnerdaf45552013-08-28 00:53:59 +020010872#ifndef MS_WINDOWS
10873 if (_Py_set_inheritable(fd, 0, atomic_flag_works) < 0) {
10874 close(fd);
Larry Hastings2f936352014-08-05 14:04:04 +100010875 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020010876 }
10877#endif
10878
Larry Hastings2f936352014-08-05 14:04:04 +100010879 return fd;
10880}
10881
10882
10883/*[clinic input]
10884os.close
10885
10886 fd: int
10887
10888Close a file descriptor.
10889[clinic start generated code]*/
10890
10891PyDoc_STRVAR(os_close__doc__,
10892"close($module, /, fd)\n"
10893"--\n"
10894"\n"
10895"Close a file descriptor.");
10896
10897#define OS_CLOSE_METHODDEF \
10898 {"close", (PyCFunction)os_close, METH_VARARGS|METH_KEYWORDS, os_close__doc__},
10899
10900static PyObject *
10901os_close_impl(PyModuleDef *module, int fd);
10902
10903static PyObject *
10904os_close(PyModuleDef *module, PyObject *args, PyObject *kwargs)
10905{
10906 PyObject *return_value = NULL;
10907 static char *_keywords[] = {"fd", NULL};
10908 int fd;
10909
10910 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10911 "i:close", _keywords,
10912 &fd))
10913 goto exit;
10914 return_value = os_close_impl(module, fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010915
10916exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070010917 return return_value;
10918}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010919
Barry Warsaw53699e91996-12-10 23:23:01 +000010920static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010921os_close_impl(PyModuleDef *module, int fd)
10922/*[clinic end generated code: output=927004e29ad55808 input=2bc42451ca5c3223]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000010923{
Larry Hastings2f936352014-08-05 14:04:04 +100010924 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +000010925 if (!_PyVerify_fd(fd))
10926 return posix_error();
10927 Py_BEGIN_ALLOW_THREADS
10928 res = close(fd);
10929 Py_END_ALLOW_THREADS
10930 if (res < 0)
10931 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010932 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000010933}
10934
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010935
Larry Hastings2f936352014-08-05 14:04:04 +100010936/*[clinic input]
10937os.closerange
10938
10939 fd_low: int
10940 fd_high: int
10941 /
10942
10943Closes all file descriptors in [fd_low, fd_high), ignoring errors.
10944[clinic start generated code]*/
10945
10946PyDoc_STRVAR(os_closerange__doc__,
10947"closerange($module, fd_low, fd_high, /)\n"
10948"--\n"
10949"\n"
10950"Closes all file descriptors in [fd_low, fd_high), ignoring errors.");
10951
10952#define OS_CLOSERANGE_METHODDEF \
10953 {"closerange", (PyCFunction)os_closerange, METH_VARARGS, os_closerange__doc__},
Christian Heimesfdab48e2008-01-20 09:06:41 +000010954
10955static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010956os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high);
10957
10958static PyObject *
10959os_closerange(PyModuleDef *module, PyObject *args)
Christian Heimesfdab48e2008-01-20 09:06:41 +000010960{
Larry Hastings2f936352014-08-05 14:04:04 +100010961 PyObject *return_value = NULL;
10962 int fd_low;
10963 int fd_high;
10964
10965 if (!PyArg_ParseTuple(args,
10966 "ii:closerange",
10967 &fd_low, &fd_high))
10968 goto exit;
10969 return_value = os_closerange_impl(module, fd_low, fd_high);
10970
10971exit:
10972 return return_value;
10973}
10974
10975static PyObject *
10976os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high)
10977/*[clinic end generated code: output=0a929ece386811c3 input=5855a3d053ebd4ec]*/
10978{
10979 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +000010980 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010981 for (i = fd_low; i < fd_high; i++)
Victor Stinner8c62be82010-05-06 00:08:46 +000010982 if (_PyVerify_fd(i))
10983 close(i);
10984 Py_END_ALLOW_THREADS
10985 Py_RETURN_NONE;
Christian Heimesfdab48e2008-01-20 09:06:41 +000010986}
10987
10988
Larry Hastings2f936352014-08-05 14:04:04 +100010989/*[clinic input]
10990os.dup -> int
10991
10992 fd: int
10993 /
10994
10995Return a duplicate of a file descriptor.
10996[clinic start generated code]*/
10997
10998PyDoc_STRVAR(os_dup__doc__,
10999"dup($module, fd, /)\n"
11000"--\n"
11001"\n"
11002"Return a duplicate of a file descriptor.");
11003
11004#define OS_DUP_METHODDEF \
11005 {"dup", (PyCFunction)os_dup, METH_VARARGS, os_dup__doc__},
11006
11007static int
11008os_dup_impl(PyModuleDef *module, int fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011009
Barry Warsaw53699e91996-12-10 23:23:01 +000011010static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011011os_dup(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011012{
Larry Hastings2f936352014-08-05 14:04:04 +100011013 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011014 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011015 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011016
Larry Hastings2f936352014-08-05 14:04:04 +100011017 if (!PyArg_ParseTuple(args,
11018 "i:dup",
11019 &fd))
11020 goto exit;
11021 _return_value = os_dup_impl(module, fd);
11022 if ((_return_value == -1) && PyErr_Occurred())
11023 goto exit;
11024 return_value = PyLong_FromLong((long)_return_value);
Tim Golden23005082013-10-25 11:22:37 +010011025
Larry Hastings2f936352014-08-05 14:04:04 +100011026exit:
11027 return return_value;
11028}
Victor Stinnerdaf45552013-08-28 00:53:59 +020011029
Larry Hastings2f936352014-08-05 14:04:04 +100011030static int
11031os_dup_impl(PyModuleDef *module, int fd)
11032/*[clinic end generated code: output=75943e057b25e1bd input=6f10f7ea97f7852a]*/
11033{
11034 return _Py_dup(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +000011035}
11036
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011037
Larry Hastings2f936352014-08-05 14:04:04 +100011038/*[clinic input]
11039os.dup2
11040 fd: int
11041 fd2: int
11042 inheritable: bool=True
11043
11044Duplicate file descriptor.
11045[clinic start generated code]*/
11046
11047PyDoc_STRVAR(os_dup2__doc__,
11048"dup2($module, /, fd, fd2, inheritable=True)\n"
11049"--\n"
11050"\n"
11051"Duplicate file descriptor.");
11052
11053#define OS_DUP2_METHODDEF \
11054 {"dup2", (PyCFunction)os_dup2, METH_VARARGS|METH_KEYWORDS, os_dup2__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011055
Barry Warsaw53699e91996-12-10 23:23:01 +000011056static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011057os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable);
11058
11059static PyObject *
11060os_dup2(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011061{
Larry Hastings2f936352014-08-05 14:04:04 +100011062 PyObject *return_value = NULL;
11063 static char *_keywords[] = {"fd", "fd2", "inheritable", NULL};
11064 int fd;
11065 int fd2;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011066 int inheritable = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100011067
11068 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11069 "ii|p:dup2", _keywords,
11070 &fd, &fd2, &inheritable))
11071 goto exit;
11072 return_value = os_dup2_impl(module, fd, fd2, inheritable);
11073
11074exit:
11075 return return_value;
11076}
11077
11078static PyObject *
11079os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable)
11080/*[clinic end generated code: output=531e482dd11a99a0 input=76e96f511be0352f]*/
11081{
Victor Stinnerdaf45552013-08-28 00:53:59 +020011082 int res;
11083#if defined(HAVE_DUP3) && \
11084 !(defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC))
11085 /* dup3() is available on Linux 2.6.27+ and glibc 2.9 */
11086 int dup3_works = -1;
11087#endif
11088
Victor Stinner8c62be82010-05-06 00:08:46 +000011089 if (!_PyVerify_fd_dup2(fd, fd2))
11090 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011091
11092#ifdef MS_WINDOWS
11093 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011094 res = dup2(fd, fd2);
Victor Stinnerdaf45552013-08-28 00:53:59 +020011095 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011096 if (res < 0)
11097 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011098
11099 /* Character files like console cannot be make non-inheritable */
11100 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11101 close(fd2);
11102 return NULL;
11103 }
11104
11105#elif defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC)
11106 Py_BEGIN_ALLOW_THREADS
11107 if (!inheritable)
11108 res = fcntl(fd, F_DUP2FD_CLOEXEC, fd2);
11109 else
11110 res = dup2(fd, fd2);
11111 Py_END_ALLOW_THREADS
11112 if (res < 0)
11113 return posix_error();
11114
11115#else
11116
11117#ifdef HAVE_DUP3
11118 if (!inheritable && dup3_works != 0) {
11119 Py_BEGIN_ALLOW_THREADS
11120 res = dup3(fd, fd2, O_CLOEXEC);
11121 Py_END_ALLOW_THREADS
11122 if (res < 0) {
11123 if (dup3_works == -1)
11124 dup3_works = (errno != ENOSYS);
11125 if (dup3_works)
11126 return posix_error();
11127 }
11128 }
11129
11130 if (inheritable || dup3_works == 0)
11131 {
11132#endif
11133 Py_BEGIN_ALLOW_THREADS
11134 res = dup2(fd, fd2);
11135 Py_END_ALLOW_THREADS
11136 if (res < 0)
11137 return posix_error();
11138
11139 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11140 close(fd2);
11141 return NULL;
11142 }
11143#ifdef HAVE_DUP3
11144 }
11145#endif
11146
11147#endif
11148
Larry Hastings2f936352014-08-05 14:04:04 +100011149 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000011150}
11151
Larry Hastings2f936352014-08-05 14:04:04 +100011152
Ross Lagerwall7807c352011-03-17 20:20:30 +020011153#ifdef HAVE_LOCKF
Larry Hastings2f936352014-08-05 14:04:04 +100011154/*[clinic input]
11155os.lockf
11156
11157 fd: int
11158 An open file descriptor.
11159 command: int
11160 One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.
11161 length: Py_off_t
11162 The number of bytes to lock, starting at the current position.
11163 /
11164
11165Apply, test or remove a POSIX lock on an open file descriptor.
11166
11167[clinic start generated code]*/
11168
11169PyDoc_STRVAR(os_lockf__doc__,
11170"lockf($module, fd, command, length, /)\n"
11171"--\n"
11172"\n"
11173"Apply, test or remove a POSIX lock on an open file descriptor.\n"
11174"\n"
11175" fd\n"
11176" An open file descriptor.\n"
11177" command\n"
11178" One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.\n"
11179" length\n"
11180" The number of bytes to lock, starting at the current position.");
11181
11182#define OS_LOCKF_METHODDEF \
11183 {"lockf", (PyCFunction)os_lockf, METH_VARARGS, os_lockf__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011184
11185static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011186os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length);
11187
11188static PyObject *
11189os_lockf(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011190{
Larry Hastings2f936352014-08-05 14:04:04 +100011191 PyObject *return_value = NULL;
11192 int fd;
11193 int command;
11194 Py_off_t length;
11195
11196 if (!PyArg_ParseTuple(args,
11197 "iiO&:lockf",
11198 &fd, &command, Py_off_t_converter, &length))
11199 goto exit;
11200 return_value = os_lockf_impl(module, fd, command, length);
11201
11202exit:
11203 return return_value;
11204}
11205
11206static PyObject *
11207os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length)
11208/*[clinic end generated code: output=1b28346ac7335c0f input=65da41d2106e9b79]*/
11209{
11210 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011211
11212 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011213 res = lockf(fd, command, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011214 Py_END_ALLOW_THREADS
11215
11216 if (res < 0)
11217 return posix_error();
11218
11219 Py_RETURN_NONE;
11220}
Larry Hastings2f936352014-08-05 14:04:04 +100011221#endif /* HAVE_LOCKF */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011222
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011223
Larry Hastings2f936352014-08-05 14:04:04 +100011224/*[clinic input]
11225os.lseek -> Py_off_t
11226
11227 fd: int
11228 position: Py_off_t
11229 how: int
11230 /
11231
11232Set the position of a file descriptor. Return the new position.
11233
11234Return the new cursor position in number of bytes
11235relative to the beginning of the file.
11236[clinic start generated code]*/
11237
11238PyDoc_STRVAR(os_lseek__doc__,
11239"lseek($module, fd, position, how, /)\n"
11240"--\n"
11241"\n"
11242"Set the position of a file descriptor. Return the new position.\n"
11243"\n"
11244"Return the new cursor position in number of bytes\n"
11245"relative to the beginning of the file.");
11246
11247#define OS_LSEEK_METHODDEF \
11248 {"lseek", (PyCFunction)os_lseek, METH_VARARGS, os_lseek__doc__},
11249
11250static Py_off_t
11251os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011252
Barry Warsaw53699e91996-12-10 23:23:01 +000011253static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011254os_lseek(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011255{
Larry Hastings2f936352014-08-05 14:04:04 +100011256 PyObject *return_value = NULL;
11257 int fd;
11258 Py_off_t position;
11259 int how;
11260 Py_off_t _return_value;
11261
11262 if (!PyArg_ParseTuple(args,
11263 "iO&i:lseek",
11264 &fd, Py_off_t_converter, &position, &how))
11265 goto exit;
11266 _return_value = os_lseek_impl(module, fd, position, how);
11267 if ((_return_value == -1) && PyErr_Occurred())
11268 goto exit;
11269 return_value = PyLong_FromPy_off_t(_return_value);
11270
11271exit:
11272 return return_value;
11273}
11274
11275static Py_off_t
11276os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how)
11277/*[clinic end generated code: output=88cfc146f55667af input=902654ad3f96a6d3]*/
11278{
11279 Py_off_t result;
11280
11281 if (!_PyVerify_fd(fd)) {
11282 posix_error();
11283 return -1;
11284 }
Guido van Rossum687dd131993-05-17 08:34:16 +000011285#ifdef SEEK_SET
Victor Stinner8c62be82010-05-06 00:08:46 +000011286 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
11287 switch (how) {
Larry Hastings2f936352014-08-05 14:04:04 +100011288 case 0: how = SEEK_SET; break;
11289 case 1: how = SEEK_CUR; break;
11290 case 2: how = SEEK_END; break;
Victor Stinner8c62be82010-05-06 00:08:46 +000011291 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000011292#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +000011293
Victor Stinner8c62be82010-05-06 00:08:46 +000011294 if (PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100011295 return -1;
Guido van Rossum94f6f721999-01-06 18:42:14 +000011296
Larry Hastings2f936352014-08-05 14:04:04 +100011297 if (!_PyVerify_fd(fd)) {
11298 posix_error();
11299 return -1;
11300 }
Victor Stinner8c62be82010-05-06 00:08:46 +000011301 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011302#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100011303 result = _lseeki64(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011304#else
Larry Hastings2f936352014-08-05 14:04:04 +100011305 result = lseek(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011306#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011307 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011308 if (result < 0)
11309 posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +000011310
Larry Hastings2f936352014-08-05 14:04:04 +100011311 return result;
Guido van Rossum687dd131993-05-17 08:34:16 +000011312}
11313
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011314
Larry Hastings2f936352014-08-05 14:04:04 +100011315/*[clinic input]
11316os.read
11317 fd: int
11318 length: Py_ssize_t
11319 /
11320
11321Read from a file descriptor. Returns a bytes object.
11322[clinic start generated code]*/
11323
11324PyDoc_STRVAR(os_read__doc__,
11325"read($module, fd, length, /)\n"
11326"--\n"
11327"\n"
11328"Read from a file descriptor. Returns a bytes object.");
11329
11330#define OS_READ_METHODDEF \
11331 {"read", (PyCFunction)os_read, METH_VARARGS, os_read__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011332
Barry Warsaw53699e91996-12-10 23:23:01 +000011333static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011334os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length);
11335
11336static PyObject *
11337os_read(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011338{
Larry Hastings2f936352014-08-05 14:04:04 +100011339 PyObject *return_value = NULL;
Victor Stinnerb28ed922014-07-11 17:04:41 +020011340 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011341 Py_ssize_t length;
11342
11343 if (!PyArg_ParseTuple(args,
11344 "in:read",
11345 &fd, &length))
11346 goto exit;
11347 return_value = os_read_impl(module, fd, length);
11348
11349exit:
11350 return return_value;
11351}
11352
11353static PyObject *
11354os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length)
11355/*[clinic end generated code: output=1f3bc27260a24968 input=1df2eaa27c0bf1d3]*/
11356{
Victor Stinner8c62be82010-05-06 00:08:46 +000011357 Py_ssize_t n;
11358 PyObject *buffer;
Larry Hastings2f936352014-08-05 14:04:04 +100011359
11360 if (length < 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +000011361 errno = EINVAL;
11362 return posix_error();
11363 }
Larry Hastings2f936352014-08-05 14:04:04 +100011364 if (!_PyVerify_fd(fd))
11365 return posix_error();
11366
11367#ifdef MS_WINDOWS
11368 #define READ_CAST (int)
11369 if (length > INT_MAX)
11370 length = INT_MAX;
11371#else
11372 #define READ_CAST
11373#endif
11374
11375 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011376 if (buffer == NULL)
11377 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011378 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011379 n = read(fd, PyBytes_AS_STRING(buffer), READ_CAST length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011380 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011381
Victor Stinner8c62be82010-05-06 00:08:46 +000011382 if (n < 0) {
11383 Py_DECREF(buffer);
11384 return posix_error();
11385 }
Larry Hastings2f936352014-08-05 14:04:04 +100011386
11387 if (n != length)
Victor Stinner8c62be82010-05-06 00:08:46 +000011388 _PyBytes_Resize(&buffer, n);
Larry Hastings2f936352014-08-05 14:04:04 +100011389
Victor Stinner8c62be82010-05-06 00:08:46 +000011390 return buffer;
Guido van Rossum687dd131993-05-17 08:34:16 +000011391}
11392
Ross Lagerwall7807c352011-03-17 20:20:30 +020011393#if (defined(HAVE_SENDFILE) && (defined(__FreeBSD__) || defined(__DragonFly__) \
11394 || defined(__APPLE__))) || defined(HAVE_READV) || defined(HAVE_WRITEV)
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011395static Py_ssize_t
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011396iov_setup(struct iovec **iov, Py_buffer **buf, PyObject *seq, int cnt, int type)
11397{
11398 int i, j;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011399 Py_ssize_t blen, total = 0;
11400
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011401 *iov = PyMem_New(struct iovec, cnt);
11402 if (*iov == NULL) {
11403 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011404 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011405 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011406
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011407 *buf = PyMem_New(Py_buffer, cnt);
11408 if (*buf == NULL) {
11409 PyMem_Del(*iov);
11410 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011411 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011412 }
11413
11414 for (i = 0; i < cnt; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011415 PyObject *item = PySequence_GetItem(seq, i);
11416 if (item == NULL)
11417 goto fail;
11418 if (PyObject_GetBuffer(item, &(*buf)[i], type) == -1) {
11419 Py_DECREF(item);
11420 goto fail;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011421 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011422 Py_DECREF(item);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011423 (*iov)[i].iov_base = (*buf)[i].buf;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011424 blen = (*buf)[i].len;
11425 (*iov)[i].iov_len = blen;
11426 total += blen;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011427 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011428 return total;
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011429
11430fail:
11431 PyMem_Del(*iov);
11432 for (j = 0; j < i; j++) {
11433 PyBuffer_Release(&(*buf)[j]);
11434 }
11435 PyMem_Del(*buf);
Victor Stinner57ddf782014-01-08 15:21:28 +010011436 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011437}
11438
11439static void
11440iov_cleanup(struct iovec *iov, Py_buffer *buf, int cnt)
11441{
11442 int i;
11443 PyMem_Del(iov);
11444 for (i = 0; i < cnt; i++) {
11445 PyBuffer_Release(&buf[i]);
11446 }
11447 PyMem_Del(buf);
11448}
11449#endif
11450
Larry Hastings2f936352014-08-05 14:04:04 +100011451
Ross Lagerwall7807c352011-03-17 20:20:30 +020011452#ifdef HAVE_READV
Larry Hastings2f936352014-08-05 14:04:04 +100011453/*[clinic input]
11454os.readv -> Py_ssize_t
11455
11456 fd: int
11457 buffers: object
11458 /
11459
11460Read from a file descriptor fd into an iterable of buffers.
11461
11462The buffers should be mutable buffers accepting bytes.
11463readv will transfer data into each buffer until it is full
11464and then move on to the next buffer in the sequence to hold
11465the rest of the data.
11466
11467readv returns the total number of bytes read,
11468which may be less than the total capacity of all the buffers.
11469[clinic start generated code]*/
11470
11471PyDoc_STRVAR(os_readv__doc__,
11472"readv($module, fd, buffers, /)\n"
11473"--\n"
11474"\n"
11475"Read from a file descriptor fd into an iterable of buffers.\n"
11476"\n"
11477"The buffers should be mutable buffers accepting bytes.\n"
11478"readv will transfer data into each buffer until it is full\n"
11479"and then move on to the next buffer in the sequence to hold\n"
11480"the rest of the data.\n"
11481"\n"
11482"readv returns the total number of bytes read,\n"
11483"which may be less than the total capacity of all the buffers.");
11484
11485#define OS_READV_METHODDEF \
11486 {"readv", (PyCFunction)os_readv, METH_VARARGS, os_readv__doc__},
11487
11488static Py_ssize_t
11489os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011490
11491static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011492os_readv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011493{
Larry Hastings2f936352014-08-05 14:04:04 +100011494 PyObject *return_value = NULL;
11495 int fd;
11496 PyObject *buffers;
11497 Py_ssize_t _return_value;
11498
11499 if (!PyArg_ParseTuple(args,
11500 "iO:readv",
11501 &fd, &buffers))
11502 goto exit;
11503 _return_value = os_readv_impl(module, fd, buffers);
11504 if ((_return_value == -1) && PyErr_Occurred())
11505 goto exit;
11506 return_value = PyLong_FromSsize_t(_return_value);
11507
11508exit:
11509 return return_value;
11510}
11511
11512static Py_ssize_t
11513os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers)
11514/*[clinic end generated code: output=72748b1c32a6e2a1 input=e679eb5dbfa0357d]*/
11515{
11516 int cnt;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011517 Py_ssize_t n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011518 struct iovec *iov;
11519 Py_buffer *buf;
11520
Larry Hastings2f936352014-08-05 14:04:04 +100011521 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011522 PyErr_SetString(PyExc_TypeError,
11523 "readv() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100011524 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011525 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020011526
Larry Hastings2f936352014-08-05 14:04:04 +100011527 cnt = PySequence_Size(buffers);
11528
11529 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_WRITABLE) < 0)
11530 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011531
11532 Py_BEGIN_ALLOW_THREADS
11533 n = readv(fd, iov, cnt);
11534 Py_END_ALLOW_THREADS
11535
11536 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100011537 if (n < 0) {
11538 posix_error();
11539 return -1;
11540 }
Victor Stinner57ddf782014-01-08 15:21:28 +010011541
Larry Hastings2f936352014-08-05 14:04:04 +100011542 return n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011543}
Larry Hastings2f936352014-08-05 14:04:04 +100011544#endif /* HAVE_READV */
11545
Ross Lagerwall7807c352011-03-17 20:20:30 +020011546
11547#ifdef HAVE_PREAD
Larry Hastings2f936352014-08-05 14:04:04 +100011548/*[clinic input]
11549# TODO length should be size_t! but Python doesn't support parsing size_t yet.
11550os.pread
11551
11552 fd: int
11553 length: int
11554 offset: Py_off_t
11555 /
11556
11557Read a number of bytes from a file descriptor starting at a particular offset.
11558
11559Read length bytes from file descriptor fd, starting at offset bytes from
11560the beginning of the file. The file offset remains unchanged.
11561[clinic start generated code]*/
11562
11563PyDoc_STRVAR(os_pread__doc__,
11564"pread($module, fd, length, offset, /)\n"
11565"--\n"
11566"\n"
11567"Read a number of bytes from a file descriptor starting at a particular offset.\n"
11568"\n"
11569"Read length bytes from file descriptor fd, starting at offset bytes from\n"
11570"the beginning of the file. The file offset remains unchanged.");
11571
11572#define OS_PREAD_METHODDEF \
11573 {"pread", (PyCFunction)os_pread, METH_VARARGS, os_pread__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011574
11575static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011576os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset);
11577
11578static PyObject *
11579os_pread(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011580{
Larry Hastings2f936352014-08-05 14:04:04 +100011581 PyObject *return_value = NULL;
11582 int fd;
11583 int length;
11584 Py_off_t offset;
11585
11586 if (!PyArg_ParseTuple(args,
11587 "iiO&:pread",
11588 &fd, &length, Py_off_t_converter, &offset))
11589 goto exit;
11590 return_value = os_pread_impl(module, fd, length, offset);
11591
11592exit:
11593 return return_value;
11594}
11595
11596static PyObject *
11597os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset)
11598/*[clinic end generated code: output=7b62bf6c06e20ae8 input=084948dcbaa35d4c]*/
11599{
Ross Lagerwall7807c352011-03-17 20:20:30 +020011600 Py_ssize_t n;
11601 PyObject *buffer;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011602
Larry Hastings2f936352014-08-05 14:04:04 +100011603 if (length < 0) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011604 errno = EINVAL;
11605 return posix_error();
11606 }
Larry Hastings2f936352014-08-05 14:04:04 +100011607 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011608 if (buffer == NULL)
11609 return NULL;
11610 if (!_PyVerify_fd(fd)) {
11611 Py_DECREF(buffer);
11612 return posix_error();
11613 }
11614 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011615 n = pread(fd, PyBytes_AS_STRING(buffer), length, offset);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011616 Py_END_ALLOW_THREADS
11617 if (n < 0) {
11618 Py_DECREF(buffer);
11619 return posix_error();
11620 }
Larry Hastings2f936352014-08-05 14:04:04 +100011621 if (n != length)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011622 _PyBytes_Resize(&buffer, n);
11623 return buffer;
11624}
Larry Hastings2f936352014-08-05 14:04:04 +100011625#endif /* HAVE_PREAD */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011626
Larry Hastings2f936352014-08-05 14:04:04 +100011627
11628/*[clinic input]
11629os.write -> Py_ssize_t
11630
11631 fd: int
11632 data: Py_buffer
11633 /
11634
11635Write a bytes object to a file descriptor.
11636[clinic start generated code]*/
11637
11638PyDoc_STRVAR(os_write__doc__,
11639"write($module, fd, data, /)\n"
11640"--\n"
11641"\n"
11642"Write a bytes object to a file descriptor.");
11643
11644#define OS_WRITE_METHODDEF \
11645 {"write", (PyCFunction)os_write, METH_VARARGS, os_write__doc__},
11646
11647static Py_ssize_t
11648os_write_impl(PyModuleDef *module, int fd, Py_buffer *data);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011649
11650static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011651os_write(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011652{
Larry Hastings2f936352014-08-05 14:04:04 +100011653 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011654 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011655 Py_buffer data = {NULL, NULL};
11656 Py_ssize_t _return_value;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011657
Larry Hastings2f936352014-08-05 14:04:04 +100011658 if (!PyArg_ParseTuple(args,
11659 "iy*:write",
11660 &fd, &data))
11661 goto exit;
11662 _return_value = os_write_impl(module, fd, &data);
11663 if ((_return_value == -1) && PyErr_Occurred())
11664 goto exit;
11665 return_value = PyLong_FromSsize_t(_return_value);
11666
11667exit:
11668 /* Cleanup for data */
11669 if (data.obj)
11670 PyBuffer_Release(&data);
11671
11672 return return_value;
11673}
11674
11675static Py_ssize_t
11676os_write_impl(PyModuleDef *module, int fd, Py_buffer *data)
11677/*[clinic end generated code: output=aeb96acfdd4d5112 input=3207e28963234f3c]*/
11678{
11679 Py_ssize_t size;
11680 Py_ssize_t len = data->len;
11681
Ross Lagerwall7807c352011-03-17 20:20:30 +020011682 if (!_PyVerify_fd(fd)) {
Larry Hastings2f936352014-08-05 14:04:04 +100011683 posix_error();
11684 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011685 }
Larry Hastings2f936352014-08-05 14:04:04 +100011686
Ross Lagerwall7807c352011-03-17 20:20:30 +020011687 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011688#ifdef MS_WINDOWS
Ross Lagerwall7807c352011-03-17 20:20:30 +020011689 if (len > INT_MAX)
11690 len = INT_MAX;
Larry Hastings2f936352014-08-05 14:04:04 +100011691 size = write(fd, data->buf, (int)len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011692#else
Larry Hastings2f936352014-08-05 14:04:04 +100011693 size = write(fd, data->buf, len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011694#endif
11695 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011696 if (size < 0) {
11697 posix_error();
11698 return -1;
11699 }
11700 return size;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011701}
11702
11703#ifdef HAVE_SENDFILE
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011704PyDoc_STRVAR(posix_sendfile__doc__,
11705"sendfile(out, in, offset, nbytes) -> byteswritten\n\
11706sendfile(out, in, offset, nbytes, headers=None, trailers=None, flags=0)\n\
11707 -> byteswritten\n\
11708Copy nbytes bytes from file descriptor in to file descriptor out.");
11709
Larry Hastings2f936352014-08-05 14:04:04 +100011710/* AC 3.5: don't bother converting, has optional group*/
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011711static PyObject *
11712posix_sendfile(PyObject *self, PyObject *args, PyObject *kwdict)
11713{
11714 int in, out;
11715 Py_ssize_t ret;
11716 off_t offset;
11717
11718#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
11719#ifndef __APPLE__
11720 Py_ssize_t len;
11721#endif
11722 PyObject *headers = NULL, *trailers = NULL;
11723 Py_buffer *hbuf, *tbuf;
11724 off_t sbytes;
11725 struct sf_hdtr sf;
11726 int flags = 0;
Benjamin Petersond8a43b42011-02-26 21:35:16 +000011727 static char *keywords[] = {"out", "in",
11728 "offset", "count",
11729 "headers", "trailers", "flags", NULL};
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011730
Victor Stinner6ce0dbf2013-07-07 16:32:36 +020011731 sf.headers = NULL;
11732 sf.trailers = NULL;
11733
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011734#ifdef __APPLE__
11735 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&O&|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011736 keywords, &out, &in, Py_off_t_converter, &offset, Py_off_t_converter, &sbytes,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011737#else
11738 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&n|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011739 keywords, &out, &in, Py_off_t_converter, &offset, &len,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011740#endif
11741 &headers, &trailers, &flags))
11742 return NULL;
11743 if (headers != NULL) {
11744 if (!PySequence_Check(headers)) {
11745 PyErr_SetString(PyExc_TypeError,
11746 "sendfile() headers must be a sequence or None");
11747 return NULL;
11748 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011749 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011750 sf.hdr_cnt = PySequence_Size(headers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011751 if (sf.hdr_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011752 (i = iov_setup(&(sf.headers), &hbuf,
11753 headers, sf.hdr_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011754 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011755#ifdef __APPLE__
11756 sbytes += i;
11757#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011758 }
11759 }
11760 if (trailers != NULL) {
11761 if (!PySequence_Check(trailers)) {
11762 PyErr_SetString(PyExc_TypeError,
11763 "sendfile() trailers must be a sequence or None");
11764 return NULL;
11765 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011766 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011767 sf.trl_cnt = PySequence_Size(trailers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011768 if (sf.trl_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011769 (i = iov_setup(&(sf.trailers), &tbuf,
11770 trailers, sf.trl_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011771 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011772#ifdef __APPLE__
11773 sbytes += i;
11774#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011775 }
11776 }
11777
11778 Py_BEGIN_ALLOW_THREADS
11779#ifdef __APPLE__
11780 ret = sendfile(in, out, offset, &sbytes, &sf, flags);
11781#else
11782 ret = sendfile(in, out, offset, len, &sf, &sbytes, flags);
11783#endif
11784 Py_END_ALLOW_THREADS
11785
11786 if (sf.headers != NULL)
11787 iov_cleanup(sf.headers, hbuf, sf.hdr_cnt);
11788 if (sf.trailers != NULL)
11789 iov_cleanup(sf.trailers, tbuf, sf.trl_cnt);
11790
11791 if (ret < 0) {
11792 if ((errno == EAGAIN) || (errno == EBUSY)) {
11793 if (sbytes != 0) {
11794 // some data has been sent
11795 goto done;
11796 }
11797 else {
11798 // no data has been sent; upper application is supposed
11799 // to retry on EAGAIN or EBUSY
11800 return posix_error();
11801 }
11802 }
11803 return posix_error();
11804 }
11805 goto done;
11806
11807done:
11808 #if !defined(HAVE_LARGEFILE_SUPPORT)
11809 return Py_BuildValue("l", sbytes);
11810 #else
11811 return Py_BuildValue("L", sbytes);
11812 #endif
11813
11814#else
11815 Py_ssize_t count;
11816 PyObject *offobj;
11817 static char *keywords[] = {"out", "in",
11818 "offset", "count", NULL};
11819 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiOn:sendfile",
11820 keywords, &out, &in, &offobj, &count))
11821 return NULL;
11822#ifdef linux
11823 if (offobj == Py_None) {
11824 Py_BEGIN_ALLOW_THREADS
11825 ret = sendfile(out, in, NULL, count);
11826 Py_END_ALLOW_THREADS
11827 if (ret < 0)
11828 return posix_error();
Giampaolo Rodola'ff1a7352011-04-19 09:47:16 +020011829 return Py_BuildValue("n", ret);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011830 }
11831#endif
Larry Hastings2f936352014-08-05 14:04:04 +100011832 if (!Py_off_t_converter(offobj, &offset))
Antoine Pitroudcc20b82011-02-26 13:38:35 +000011833 return NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011834 Py_BEGIN_ALLOW_THREADS
11835 ret = sendfile(out, in, &offset, count);
11836 Py_END_ALLOW_THREADS
11837 if (ret < 0)
11838 return posix_error();
11839 return Py_BuildValue("n", ret);
11840#endif
11841}
Larry Hastings2f936352014-08-05 14:04:04 +100011842#endif /* HAVE_SENDFILE */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011843
Larry Hastings2f936352014-08-05 14:04:04 +100011844
11845/*[clinic input]
11846os.fstat
11847
11848 fd : int
11849
11850Perform a stat system call on the given file descriptor.
11851
11852Like stat(), but for an open file descriptor.
11853Equivalent to os.stat(fd).
11854[clinic start generated code]*/
11855
11856PyDoc_STRVAR(os_fstat__doc__,
11857"fstat($module, /, fd)\n"
11858"--\n"
11859"\n"
11860"Perform a stat system call on the given file descriptor.\n"
11861"\n"
11862"Like stat(), but for an open file descriptor.\n"
11863"Equivalent to os.stat(fd).");
11864
11865#define OS_FSTAT_METHODDEF \
11866 {"fstat", (PyCFunction)os_fstat, METH_VARARGS|METH_KEYWORDS, os_fstat__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011867
Barry Warsaw53699e91996-12-10 23:23:01 +000011868static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011869os_fstat_impl(PyModuleDef *module, int fd);
11870
11871static PyObject *
11872os_fstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011873{
Larry Hastings2f936352014-08-05 14:04:04 +100011874 PyObject *return_value = NULL;
11875 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000011876 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011877
11878 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11879 "i:fstat", _keywords,
11880 &fd))
11881 goto exit;
11882 return_value = os_fstat_impl(module, fd);
11883
11884exit:
11885 return return_value;
11886}
11887
11888static PyObject *
11889os_fstat_impl(PyModuleDef *module, int fd)
11890/*[clinic end generated code: output=dae4a9678c7bd881 input=27e0e0ebbe5600c9]*/
11891{
Victor Stinner8c62be82010-05-06 00:08:46 +000011892 STRUCT_STAT st;
11893 int res;
Larry Hastings2f936352014-08-05 14:04:04 +100011894
Victor Stinner8c62be82010-05-06 00:08:46 +000011895 Py_BEGIN_ALLOW_THREADS
11896 res = FSTAT(fd, &st);
11897 Py_END_ALLOW_THREADS
11898 if (res != 0) {
Martin v. Löwis14694662006-02-03 12:54:16 +000011899#ifdef MS_WINDOWS
Victor Stinnerb024e842012-10-31 22:24:06 +010011900 return PyErr_SetFromWindowsErr(0);
Martin v. Löwis14694662006-02-03 12:54:16 +000011901#else
Victor Stinner8c62be82010-05-06 00:08:46 +000011902 return posix_error();
Martin v. Löwis14694662006-02-03 12:54:16 +000011903#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011904 }
Tim Peters5aa91602002-01-30 05:46:57 +000011905
Victor Stinner4195b5c2012-02-08 23:03:19 +010011906 return _pystat_fromstructstat(&st);
Guido van Rossum687dd131993-05-17 08:34:16 +000011907}
11908
Larry Hastings2f936352014-08-05 14:04:04 +100011909
11910/*[clinic input]
11911os.isatty -> bool
11912 fd: int
11913 /
11914
11915Return True if the fd is connected to a terminal.
11916
11917Return True if the file descriptor is an open file descriptor
11918connected to the slave end of a terminal.
11919[clinic start generated code]*/
11920
11921PyDoc_STRVAR(os_isatty__doc__,
11922"isatty($module, fd, /)\n"
11923"--\n"
11924"\n"
11925"Return True if the fd is connected to a terminal.\n"
11926"\n"
11927"Return True if the file descriptor is an open file descriptor\n"
11928"connected to the slave end of a terminal.");
11929
11930#define OS_ISATTY_METHODDEF \
11931 {"isatty", (PyCFunction)os_isatty, METH_VARARGS, os_isatty__doc__},
11932
11933static int
11934os_isatty_impl(PyModuleDef *module, int fd);
Skip Montanaro1517d842000-07-19 14:34:14 +000011935
11936static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011937os_isatty(PyModuleDef *module, PyObject *args)
Skip Montanaro1517d842000-07-19 14:34:14 +000011938{
Larry Hastings2f936352014-08-05 14:04:04 +100011939 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011940 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011941 int _return_value;
11942
11943 if (!PyArg_ParseTuple(args,
11944 "i:isatty",
11945 &fd))
11946 goto exit;
11947 _return_value = os_isatty_impl(module, fd);
11948 if ((_return_value == -1) && PyErr_Occurred())
11949 goto exit;
11950 return_value = PyBool_FromLong((long)_return_value);
11951
11952exit:
11953 return return_value;
Skip Montanaro1517d842000-07-19 14:34:14 +000011954}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011955
Larry Hastings2f936352014-08-05 14:04:04 +100011956static int
11957os_isatty_impl(PyModuleDef *module, int fd)
11958/*[clinic end generated code: output=4bfadbfe22715097 input=08ce94aa1eaf7b5e]*/
11959{
11960 if (!_PyVerify_fd(fd))
11961 return 0;
11962 return isatty(fd);
11963}
11964
11965
Guido van Rossuma4916fa1996-05-23 22:58:55 +000011966#ifdef HAVE_PIPE
Larry Hastings2f936352014-08-05 14:04:04 +100011967/*[clinic input]
11968os.pipe
11969
11970Create a pipe.
11971
11972Returns a tuple of two file descriptors:
11973 (read_fd, write_fd)
11974[clinic start generated code]*/
11975
11976PyDoc_STRVAR(os_pipe__doc__,
11977"pipe($module, /)\n"
11978"--\n"
11979"\n"
11980"Create a pipe.\n"
11981"\n"
11982"Returns a tuple of two file descriptors:\n"
11983" (read_fd, write_fd)");
11984
11985#define OS_PIPE_METHODDEF \
11986 {"pipe", (PyCFunction)os_pipe, METH_NOARGS, os_pipe__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011987
Barry Warsaw53699e91996-12-10 23:23:01 +000011988static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011989os_pipe_impl(PyModuleDef *module);
11990
11991static PyObject *
11992os_pipe(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
11993{
11994 return os_pipe_impl(module);
11995}
11996
11997static PyObject *
11998os_pipe_impl(PyModuleDef *module)
11999/*[clinic end generated code: output=0da2479f2266e774 input=02535e8c8fa6c4d4]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000012000{
Victor Stinner8c62be82010-05-06 00:08:46 +000012001 int fds[2];
Victor Stinnerdaf45552013-08-28 00:53:59 +020012002#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000012003 HANDLE read, write;
Victor Stinnerdaf45552013-08-28 00:53:59 +020012004 SECURITY_ATTRIBUTES attr;
Victor Stinner8c62be82010-05-06 00:08:46 +000012005 BOOL ok;
Victor Stinnerdaf45552013-08-28 00:53:59 +020012006#else
12007 int res;
12008#endif
12009
12010#ifdef MS_WINDOWS
12011 attr.nLength = sizeof(attr);
12012 attr.lpSecurityDescriptor = NULL;
12013 attr.bInheritHandle = FALSE;
12014
12015 Py_BEGIN_ALLOW_THREADS
12016 ok = CreatePipe(&read, &write, &attr, 0);
12017 if (ok) {
12018 fds[0] = _open_osfhandle((Py_intptr_t)read, _O_RDONLY);
12019 fds[1] = _open_osfhandle((Py_intptr_t)write, _O_WRONLY);
12020 if (fds[0] == -1 || fds[1] == -1) {
12021 CloseHandle(read);
12022 CloseHandle(write);
12023 ok = 0;
12024 }
12025 }
12026 Py_END_ALLOW_THREADS
12027
Victor Stinner8c62be82010-05-06 00:08:46 +000012028 if (!ok)
Victor Stinnerb024e842012-10-31 22:24:06 +010012029 return PyErr_SetFromWindowsErr(0);
Victor Stinnerdaf45552013-08-28 00:53:59 +020012030#else
12031
12032#ifdef HAVE_PIPE2
12033 Py_BEGIN_ALLOW_THREADS
12034 res = pipe2(fds, O_CLOEXEC);
12035 Py_END_ALLOW_THREADS
12036
12037 if (res != 0 && errno == ENOSYS)
12038 {
12039#endif
12040 Py_BEGIN_ALLOW_THREADS
12041 res = pipe(fds);
12042 Py_END_ALLOW_THREADS
12043
12044 if (res == 0) {
12045 if (_Py_set_inheritable(fds[0], 0, NULL) < 0) {
12046 close(fds[0]);
12047 close(fds[1]);
12048 return NULL;
12049 }
12050 if (_Py_set_inheritable(fds[1], 0, NULL) < 0) {
12051 close(fds[0]);
12052 close(fds[1]);
12053 return NULL;
12054 }
12055 }
12056#ifdef HAVE_PIPE2
12057 }
12058#endif
12059
12060 if (res != 0)
12061 return PyErr_SetFromErrno(PyExc_OSError);
12062#endif /* !MS_WINDOWS */
12063 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum687dd131993-05-17 08:34:16 +000012064}
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012065#endif /* HAVE_PIPE */
12066
Larry Hastings2f936352014-08-05 14:04:04 +100012067
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012068#ifdef HAVE_PIPE2
Larry Hastings2f936352014-08-05 14:04:04 +100012069/*[clinic input]
12070os.pipe2
12071
12072 flags: int
12073 /
12074
12075Create a pipe with flags set atomically.
12076
12077Returns a tuple of two file descriptors:
12078 (read_fd, write_fd)
12079
12080flags can be constructed by ORing together one or more of these values:
12081O_NONBLOCK, O_CLOEXEC.
12082[clinic start generated code]*/
12083
12084PyDoc_STRVAR(os_pipe2__doc__,
12085"pipe2($module, flags, /)\n"
12086"--\n"
12087"\n"
12088"Create a pipe with flags set atomically.\n"
12089"\n"
12090"Returns a tuple of two file descriptors:\n"
12091" (read_fd, write_fd)\n"
12092"\n"
12093"flags can be constructed by ORing together one or more of these values:\n"
12094"O_NONBLOCK, O_CLOEXEC.");
12095
12096#define OS_PIPE2_METHODDEF \
12097 {"pipe2", (PyCFunction)os_pipe2, METH_VARARGS, os_pipe2__doc__},
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012098
12099static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012100os_pipe2_impl(PyModuleDef *module, int flags);
12101
12102static PyObject *
12103os_pipe2(PyModuleDef *module, PyObject *args)
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012104{
Larry Hastings2f936352014-08-05 14:04:04 +100012105 PyObject *return_value = NULL;
Charles-François Natali368f34b2011-06-06 19:49:47 +020012106 int flags;
Larry Hastings2f936352014-08-05 14:04:04 +100012107
12108 if (!PyArg_ParseTuple(args,
12109 "i:pipe2",
12110 &flags))
12111 goto exit;
12112 return_value = os_pipe2_impl(module, flags);
12113
12114exit:
12115 return return_value;
12116}
12117
12118static PyObject *
12119os_pipe2_impl(PyModuleDef *module, int flags)
12120/*[clinic end generated code: output=9e27c799ce19220b input=f261b6e7e63c6817]*/
12121{
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012122 int fds[2];
12123 int res;
12124
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012125 res = pipe2(fds, flags);
12126 if (res != 0)
12127 return posix_error();
12128 return Py_BuildValue("(ii)", fds[0], fds[1]);
12129}
12130#endif /* HAVE_PIPE2 */
12131
Larry Hastings2f936352014-08-05 14:04:04 +100012132
Ross Lagerwall7807c352011-03-17 20:20:30 +020012133#ifdef HAVE_WRITEV
Larry Hastings2f936352014-08-05 14:04:04 +100012134/*[clinic input]
12135os.writev -> Py_ssize_t
12136 fd: int
12137 buffers: object
12138 /
12139
12140Iterate over buffers, and write the contents of each to a file descriptor.
12141
12142Returns the total number of bytes written.
12143buffers must be a sequence of bytes-like objects.
12144[clinic start generated code]*/
12145
12146PyDoc_STRVAR(os_writev__doc__,
12147"writev($module, fd, buffers, /)\n"
12148"--\n"
12149"\n"
12150"Iterate over buffers, and write the contents of each to a file descriptor.\n"
12151"\n"
12152"Returns the total number of bytes written.\n"
12153"buffers must be a sequence of bytes-like objects.");
12154
12155#define OS_WRITEV_METHODDEF \
12156 {"writev", (PyCFunction)os_writev, METH_VARARGS, os_writev__doc__},
12157
12158static Py_ssize_t
12159os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012160
12161static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012162os_writev(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020012163{
Larry Hastings2f936352014-08-05 14:04:04 +100012164 PyObject *return_value = NULL;
12165 int fd;
12166 PyObject *buffers;
12167 Py_ssize_t _return_value;
12168
12169 if (!PyArg_ParseTuple(args,
12170 "iO:writev",
12171 &fd, &buffers))
12172 goto exit;
12173 _return_value = os_writev_impl(module, fd, buffers);
12174 if ((_return_value == -1) && PyErr_Occurred())
12175 goto exit;
12176 return_value = PyLong_FromSsize_t(_return_value);
12177
12178exit:
12179 return return_value;
12180}
12181
12182static Py_ssize_t
12183os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers)
12184/*[clinic end generated code: output=591c662dccbe4951 input=5b8d17fe4189d2fe]*/
12185{
12186 int cnt;
12187 Py_ssize_t result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012188 struct iovec *iov;
12189 Py_buffer *buf;
Larry Hastings2f936352014-08-05 14:04:04 +100012190
12191 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020012192 PyErr_SetString(PyExc_TypeError,
12193 "writev() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100012194 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012195 }
Larry Hastings2f936352014-08-05 14:04:04 +100012196 cnt = PySequence_Size(buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012197
Larry Hastings2f936352014-08-05 14:04:04 +100012198 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_SIMPLE) < 0) {
12199 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012200 }
12201
12202 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012203 result = writev(fd, iov, cnt);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012204 Py_END_ALLOW_THREADS
12205
12206 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100012207 if (result < 0)
12208 posix_error();
Victor Stinner57ddf782014-01-08 15:21:28 +010012209
Georg Brandl306336b2012-06-24 12:55:33 +020012210 return result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012211}
Larry Hastings2f936352014-08-05 14:04:04 +100012212#endif /* HAVE_WRITEV */
12213
12214
12215#ifdef HAVE_PWRITE
12216/*[clinic input]
12217os.pwrite -> Py_ssize_t
12218
12219 fd: int
12220 buffer: Py_buffer
12221 offset: Py_off_t
12222 /
12223
12224Write bytes to a file descriptor starting at a particular offset.
12225
12226Write buffer to fd, starting at offset bytes from the beginning of
12227the file. Returns the number of bytes writte. Does not change the
12228current file offset.
12229[clinic start generated code]*/
12230
12231PyDoc_STRVAR(os_pwrite__doc__,
12232"pwrite($module, fd, buffer, offset, /)\n"
12233"--\n"
12234"\n"
12235"Write bytes to a file descriptor starting at a particular offset.\n"
12236"\n"
12237"Write buffer to fd, starting at offset bytes from the beginning of\n"
12238"the file. Returns the number of bytes writte. Does not change the\n"
12239"current file offset.");
12240
12241#define OS_PWRITE_METHODDEF \
12242 {"pwrite", (PyCFunction)os_pwrite, METH_VARARGS, os_pwrite__doc__},
12243
12244static Py_ssize_t
12245os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset);
12246
12247static PyObject *
12248os_pwrite(PyModuleDef *module, PyObject *args)
12249{
12250 PyObject *return_value = NULL;
12251 int fd;
12252 Py_buffer buffer = {NULL, NULL};
12253 Py_off_t offset;
12254 Py_ssize_t _return_value;
12255
12256 if (!PyArg_ParseTuple(args,
12257 "iy*O&:pwrite",
12258 &fd, &buffer, Py_off_t_converter, &offset))
12259 goto exit;
12260 _return_value = os_pwrite_impl(module, fd, &buffer, offset);
12261 if ((_return_value == -1) && PyErr_Occurred())
12262 goto exit;
12263 return_value = PyLong_FromSsize_t(_return_value);
12264
12265exit:
12266 /* Cleanup for buffer */
12267 if (buffer.obj)
12268 PyBuffer_Release(&buffer);
12269
12270 return return_value;
12271}
12272
12273static Py_ssize_t
12274os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset)
12275/*[clinic end generated code: output=ec9cc5b2238e96a7 input=19903f1b3dd26377]*/
12276{
12277 Py_ssize_t size;
12278
12279 if (!_PyVerify_fd(fd)) {
12280 posix_error();
12281 return -1;
12282 }
12283
12284 Py_BEGIN_ALLOW_THREADS
12285 size = pwrite(fd, buffer->buf, (size_t)buffer->len, offset);
12286 Py_END_ALLOW_THREADS
12287
12288 if (size < 0)
12289 posix_error();
12290 return size;
12291}
12292#endif /* HAVE_PWRITE */
12293
12294
12295#ifdef HAVE_MKFIFO
12296/*[clinic input]
12297os.mkfifo
12298
12299 path: path_t
12300 mode: int=0o666
12301 *
12302 dir_fd: dir_fd(requires='mkfifoat')=None
12303
12304Create a "fifo" (a POSIX named pipe).
12305
12306If dir_fd is not None, it should be a file descriptor open to a directory,
12307 and path should be relative; path will then be relative to that directory.
12308dir_fd may not be implemented on your platform.
12309 If it is unavailable, using it will raise a NotImplementedError.
12310[clinic start generated code]*/
12311
12312PyDoc_STRVAR(os_mkfifo__doc__,
12313"mkfifo($module, /, path, mode=438, *, dir_fd=None)\n"
12314"--\n"
12315"\n"
12316"Create a \"fifo\" (a POSIX named pipe).\n"
12317"\n"
12318"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12319" and path should be relative; path will then be relative to that directory.\n"
12320"dir_fd may not be implemented on your platform.\n"
12321" If it is unavailable, using it will raise a NotImplementedError.");
12322
12323#define OS_MKFIFO_METHODDEF \
12324 {"mkfifo", (PyCFunction)os_mkfifo, METH_VARARGS|METH_KEYWORDS, os_mkfifo__doc__},
12325
12326static PyObject *
12327os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
12328
12329static PyObject *
12330os_mkfifo(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12331{
12332 PyObject *return_value = NULL;
12333 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
12334 path_t path = PATH_T_INITIALIZE("mkfifo", "path", 0, 0);
12335 int mode = 438;
12336 int dir_fd = DEFAULT_DIR_FD;
12337
12338 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12339 "O&|i$O&:mkfifo", _keywords,
12340 path_converter, &path, &mode, MKFIFOAT_DIR_FD_CONVERTER, &dir_fd))
12341 goto exit;
12342 return_value = os_mkfifo_impl(module, &path, mode, dir_fd);
12343
12344exit:
12345 /* Cleanup for path */
12346 path_cleanup(&path);
12347
12348 return return_value;
12349}
12350
12351static PyObject *
12352os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
12353/*[clinic end generated code: output=b3321927546893d0 input=73032e98a36e0e19]*/
12354{
12355 int result;
12356
12357 Py_BEGIN_ALLOW_THREADS
12358#ifdef HAVE_MKFIFOAT
12359 if (dir_fd != DEFAULT_DIR_FD)
12360 result = mkfifoat(dir_fd, path->narrow, mode);
12361 else
Ross Lagerwall7807c352011-03-17 20:20:30 +020012362#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012363 result = mkfifo(path->narrow, mode);
12364 Py_END_ALLOW_THREADS
12365
12366 if (result < 0)
12367 return posix_error();
12368
12369 Py_RETURN_NONE;
12370}
12371#endif /* HAVE_MKFIFO */
12372
12373
12374#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
12375/*[clinic input]
12376os.mknod
12377
12378 path: path_t
12379 mode: int=0o600
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012380 device: dev_t=0
Larry Hastings2f936352014-08-05 14:04:04 +100012381 *
12382 dir_fd: dir_fd(requires='mknodat')=None
12383
12384Create a node in the file system.
12385
12386Create a node in the file system (file, device special file or named pipe)
12387at path. mode specifies both the permissions to use and the
12388type of node to be created, being combined (bitwise OR) with one of
12389S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,
12390device defines the newly created device special file (probably using
12391os.makedev()). Otherwise device is ignored.
12392
12393If dir_fd is not None, it should be a file descriptor open to a directory,
12394 and path should be relative; path will then be relative to that directory.
12395dir_fd may not be implemented on your platform.
12396 If it is unavailable, using it will raise a NotImplementedError.
12397[clinic start generated code]*/
12398
12399PyDoc_STRVAR(os_mknod__doc__,
12400"mknod($module, /, path, mode=384, device=0, *, dir_fd=None)\n"
12401"--\n"
12402"\n"
12403"Create a node in the file system.\n"
12404"\n"
12405"Create a node in the file system (file, device special file or named pipe)\n"
12406"at path. mode specifies both the permissions to use and the\n"
12407"type of node to be created, being combined (bitwise OR) with one of\n"
12408"S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,\n"
12409"device defines the newly created device special file (probably using\n"
12410"os.makedev()). Otherwise device is ignored.\n"
12411"\n"
12412"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12413" and path should be relative; path will then be relative to that directory.\n"
12414"dir_fd may not be implemented on your platform.\n"
12415" If it is unavailable, using it will raise a NotImplementedError.");
12416
12417#define OS_MKNOD_METHODDEF \
12418 {"mknod", (PyCFunction)os_mknod, METH_VARARGS|METH_KEYWORDS, os_mknod__doc__},
12419
12420static PyObject *
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012421os_mknod_impl(PyModuleDef *module, path_t *path, int mode, dev_t device, int dir_fd);
Larry Hastings2f936352014-08-05 14:04:04 +100012422
12423static PyObject *
12424os_mknod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12425{
12426 PyObject *return_value = NULL;
12427 static char *_keywords[] = {"path", "mode", "device", "dir_fd", NULL};
12428 path_t path = PATH_T_INITIALIZE("mknod", "path", 0, 0);
12429 int mode = 384;
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012430 dev_t device = 0;
Larry Hastings2f936352014-08-05 14:04:04 +100012431 int dir_fd = DEFAULT_DIR_FD;
12432
12433 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012434 "O&|iO&$O&:mknod", _keywords,
12435 path_converter, &path, &mode, _Py_Dev_Converter, &device, MKNODAT_DIR_FD_CONVERTER, &dir_fd))
Larry Hastings2f936352014-08-05 14:04:04 +100012436 goto exit;
12437 return_value = os_mknod_impl(module, &path, mode, device, dir_fd);
12438
12439exit:
12440 /* Cleanup for path */
12441 path_cleanup(&path);
12442
12443 return return_value;
12444}
12445
12446static PyObject *
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012447os_mknod_impl(PyModuleDef *module, path_t *path, int mode, dev_t device, int dir_fd)
12448/*[clinic end generated code: output=f71d54eaf9bb6f1a input=ee44531551a4d83b]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012449{
12450 int result;
12451
12452 Py_BEGIN_ALLOW_THREADS
12453#ifdef HAVE_MKNODAT
12454 if (dir_fd != DEFAULT_DIR_FD)
12455 result = mknodat(dir_fd, path->narrow, mode, device);
12456 else
12457#endif
12458 result = mknod(path->narrow, mode, device);
12459 Py_END_ALLOW_THREADS
12460
12461 if (result < 0)
12462 return posix_error();
12463
12464 Py_RETURN_NONE;
12465}
12466#endif /* defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV) */
12467
12468
12469#ifdef HAVE_DEVICE_MACROS
12470/*[clinic input]
12471os.major -> unsigned_int
12472
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012473 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +100012474 /
12475
12476Extracts a device major number from a raw device number.
12477[clinic start generated code]*/
12478
12479PyDoc_STRVAR(os_major__doc__,
12480"major($module, device, /)\n"
12481"--\n"
12482"\n"
12483"Extracts a device major number from a raw device number.");
12484
12485#define OS_MAJOR_METHODDEF \
12486 {"major", (PyCFunction)os_major, METH_VARARGS, os_major__doc__},
12487
12488static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012489os_major_impl(PyModuleDef *module, dev_t device);
Larry Hastings2f936352014-08-05 14:04:04 +100012490
12491static PyObject *
12492os_major(PyModuleDef *module, PyObject *args)
12493{
12494 PyObject *return_value = NULL;
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012495 dev_t device;
Larry Hastings2f936352014-08-05 14:04:04 +100012496 unsigned int _return_value;
12497
12498 if (!PyArg_ParseTuple(args,
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012499 "O&:major",
12500 _Py_Dev_Converter, &device))
Larry Hastings2f936352014-08-05 14:04:04 +100012501 goto exit;
12502 _return_value = os_major_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012503 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012504 goto exit;
12505 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12506
12507exit:
12508 return return_value;
12509}
12510
12511static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012512os_major_impl(PyModuleDef *module, dev_t device)
12513/*[clinic end generated code: output=a2d06e908ebf95b5 input=1e16a4d30c4d4462]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012514{
12515 return major(device);
12516}
12517
12518
12519/*[clinic input]
12520os.minor -> unsigned_int
12521
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012522 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +100012523 /
12524
12525Extracts a device minor number from a raw device number.
12526[clinic start generated code]*/
12527
12528PyDoc_STRVAR(os_minor__doc__,
12529"minor($module, device, /)\n"
12530"--\n"
12531"\n"
12532"Extracts a device minor number from a raw device number.");
12533
12534#define OS_MINOR_METHODDEF \
12535 {"minor", (PyCFunction)os_minor, METH_VARARGS, os_minor__doc__},
12536
12537static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012538os_minor_impl(PyModuleDef *module, dev_t device);
Larry Hastings2f936352014-08-05 14:04:04 +100012539
12540static PyObject *
12541os_minor(PyModuleDef *module, PyObject *args)
12542{
12543 PyObject *return_value = NULL;
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012544 dev_t device;
Larry Hastings2f936352014-08-05 14:04:04 +100012545 unsigned int _return_value;
12546
12547 if (!PyArg_ParseTuple(args,
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012548 "O&:minor",
12549 _Py_Dev_Converter, &device))
Larry Hastings2f936352014-08-05 14:04:04 +100012550 goto exit;
12551 _return_value = os_minor_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012552 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012553 goto exit;
12554 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12555
12556exit:
12557 return return_value;
12558}
12559
12560static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012561os_minor_impl(PyModuleDef *module, dev_t device)
12562/*[clinic end generated code: output=6332287ee3f006e2 input=0842c6d23f24c65e]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012563{
12564 return minor(device);
12565}
12566
12567
12568/*[clinic input]
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012569os.makedev -> dev_t
Larry Hastings2f936352014-08-05 14:04:04 +100012570
12571 major: int
12572 minor: int
12573 /
12574
12575Composes a raw device number from the major and minor device numbers.
12576[clinic start generated code]*/
12577
12578PyDoc_STRVAR(os_makedev__doc__,
12579"makedev($module, major, minor, /)\n"
12580"--\n"
12581"\n"
12582"Composes a raw device number from the major and minor device numbers.");
12583
12584#define OS_MAKEDEV_METHODDEF \
12585 {"makedev", (PyCFunction)os_makedev, METH_VARARGS, os_makedev__doc__},
12586
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012587static dev_t
Larry Hastings2f936352014-08-05 14:04:04 +100012588os_makedev_impl(PyModuleDef *module, int major, int minor);
12589
12590static PyObject *
12591os_makedev(PyModuleDef *module, PyObject *args)
12592{
12593 PyObject *return_value = NULL;
12594 int major;
12595 int minor;
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012596 dev_t _return_value;
Larry Hastings2f936352014-08-05 14:04:04 +100012597
12598 if (!PyArg_ParseTuple(args,
12599 "ii:makedev",
12600 &major, &minor))
12601 goto exit;
12602 _return_value = os_makedev_impl(module, major, minor);
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012603 if ((_return_value == (dev_t)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012604 goto exit;
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012605 return_value = _PyLong_FromDev(_return_value);
Larry Hastings2f936352014-08-05 14:04:04 +100012606
12607exit:
12608 return return_value;
12609}
12610
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012611static dev_t
Larry Hastings2f936352014-08-05 14:04:04 +100012612os_makedev_impl(PyModuleDef *module, int major, int minor)
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +020012613/*[clinic end generated code: output=38e9a9774c96511a input=4b9fd8fc73cbe48f]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012614{
12615 return makedev(major, minor);
12616}
12617#endif /* HAVE_DEVICE_MACROS */
12618
12619
12620#ifdef HAVE_FTRUNCATE
12621/*[clinic input]
12622os.ftruncate
12623
12624 fd: int
12625 length: Py_off_t
12626 /
12627
12628Truncate a file, specified by file descriptor, to a specific length.
12629[clinic start generated code]*/
12630
12631PyDoc_STRVAR(os_ftruncate__doc__,
12632"ftruncate($module, fd, length, /)\n"
12633"--\n"
12634"\n"
12635"Truncate a file, specified by file descriptor, to a specific length.");
12636
12637#define OS_FTRUNCATE_METHODDEF \
12638 {"ftruncate", (PyCFunction)os_ftruncate, METH_VARARGS, os_ftruncate__doc__},
12639
12640static PyObject *
12641os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length);
12642
12643static PyObject *
12644os_ftruncate(PyModuleDef *module, PyObject *args)
12645{
12646 PyObject *return_value = NULL;
12647 int fd;
12648 Py_off_t length;
12649
12650 if (!PyArg_ParseTuple(args,
12651 "iO&:ftruncate",
12652 &fd, Py_off_t_converter, &length))
12653 goto exit;
12654 return_value = os_ftruncate_impl(module, fd, length);
12655
12656exit:
12657 return return_value;
12658}
12659
12660static PyObject *
12661os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length)
12662/*[clinic end generated code: output=62326766cb9b76bf input=63b43641e52818f2]*/
12663{
12664 int result;
12665
12666 Py_BEGIN_ALLOW_THREADS
12667 result = ftruncate(fd, length);
12668 Py_END_ALLOW_THREADS
12669 if (result < 0)
12670 return posix_error();
12671 Py_RETURN_NONE;
12672}
12673#endif /* HAVE_FTRUNCATE */
12674
12675
12676#ifdef HAVE_TRUNCATE
12677/*[clinic input]
12678os.truncate
12679 path: path_t(allow_fd='PATH_HAVE_FTRUNCATE')
12680 length: Py_off_t
12681
12682Truncate a file, specified by path, to a specific length.
12683
12684On some platforms, path may also be specified as an open file descriptor.
12685 If this functionality is unavailable, using it raises an exception.
12686[clinic start generated code]*/
12687
12688PyDoc_STRVAR(os_truncate__doc__,
12689"truncate($module, /, path, length)\n"
12690"--\n"
12691"\n"
12692"Truncate a file, specified by path, to a specific length.\n"
12693"\n"
12694"On some platforms, path may also be specified as an open file descriptor.\n"
12695" If this functionality is unavailable, using it raises an exception.");
12696
12697#define OS_TRUNCATE_METHODDEF \
12698 {"truncate", (PyCFunction)os_truncate, METH_VARARGS|METH_KEYWORDS, os_truncate__doc__},
12699
12700static PyObject *
12701os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length);
12702
12703static PyObject *
12704os_truncate(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12705{
12706 PyObject *return_value = NULL;
12707 static char *_keywords[] = {"path", "length", NULL};
12708 path_t path = PATH_T_INITIALIZE("truncate", "path", 0, PATH_HAVE_FTRUNCATE);
12709 Py_off_t length;
12710
12711 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12712 "O&O&:truncate", _keywords,
12713 path_converter, &path, Py_off_t_converter, &length))
12714 goto exit;
12715 return_value = os_truncate_impl(module, &path, length);
12716
12717exit:
12718 /* Cleanup for path */
12719 path_cleanup(&path);
12720
12721 return return_value;
12722}
12723
12724static PyObject *
12725os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length)
12726/*[clinic end generated code: output=6bd76262d2e027c6 input=77229cf0b50a9b77]*/
12727{
12728 int result;
12729
12730 Py_BEGIN_ALLOW_THREADS
12731#ifdef HAVE_FTRUNCATE
12732 if (path->fd != -1)
12733 result = ftruncate(path->fd, length);
12734 else
12735#endif
12736 result = truncate(path->narrow, length);
12737 Py_END_ALLOW_THREADS
12738 if (result < 0)
12739 return path_error(path);
12740
12741 Py_RETURN_NONE;
12742}
12743#endif /* HAVE_TRUNCATE */
12744
Ross Lagerwall7807c352011-03-17 20:20:30 +020012745
Victor Stinnerd6b17692014-09-30 12:20:05 +020012746/* Issue #22396: On 32-bit AIX platform, the prototypes of os.posix_fadvise()
12747 and os.posix_fallocate() in system headers are wrong if _LARGE_FILES is
12748 defined, which is the case in Python on AIX. AIX bug report:
12749 http://www-01.ibm.com/support/docview.wss?uid=isg1IV56170 */
12750#if defined(_AIX) && defined(_LARGE_FILES) && !defined(__64BIT__)
12751# define POSIX_FADVISE_AIX_BUG
12752#endif
12753
Victor Stinnerec39e262014-09-30 12:35:58 +020012754
Victor Stinnerd6b17692014-09-30 12:20:05 +020012755#if defined(HAVE_POSIX_FALLOCATE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +100012756/*[clinic input]
12757os.posix_fallocate
12758
12759 fd: int
12760 offset: Py_off_t
12761 length: Py_off_t
12762 /
12763
12764Ensure a file has allocated at least a particular number of bytes on disk.
12765
12766Ensure that the file specified by fd encompasses a range of bytes
12767starting at offset bytes from the beginning and continuing for length bytes.
12768[clinic start generated code]*/
12769
12770PyDoc_STRVAR(os_posix_fallocate__doc__,
12771"posix_fallocate($module, fd, offset, length, /)\n"
12772"--\n"
12773"\n"
12774"Ensure a file has allocated at least a particular number of bytes on disk.\n"
12775"\n"
12776"Ensure that the file specified by fd encompasses a range of bytes\n"
12777"starting at offset bytes from the beginning and continuing for length bytes.");
12778
12779#define OS_POSIX_FALLOCATE_METHODDEF \
12780 {"posix_fallocate", (PyCFunction)os_posix_fallocate, METH_VARARGS, os_posix_fallocate__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012781
12782static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012783os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012784
Larry Hastings2f936352014-08-05 14:04:04 +100012785static PyObject *
12786os_posix_fallocate(PyModuleDef *module, PyObject *args)
12787{
12788 PyObject *return_value = NULL;
12789 int fd;
12790 Py_off_t offset;
12791 Py_off_t length;
12792
12793 if (!PyArg_ParseTuple(args,
12794 "iO&O&:posix_fallocate",
12795 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length))
12796 goto exit;
12797 return_value = os_posix_fallocate_impl(module, fd, offset, length);
12798
12799exit:
12800 return return_value;
12801}
12802
12803static PyObject *
12804os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length)
12805/*[clinic end generated code: output=0cd702d2065c79db input=d7a2ef0ab2ca52fb]*/
12806{
12807 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012808
12809 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012810 result = posix_fallocate(fd, offset, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012811 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012812 if (result != 0) {
12813 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012814 return posix_error();
12815 }
12816 Py_RETURN_NONE;
12817}
Victor Stinnerec39e262014-09-30 12:35:58 +020012818#endif /* HAVE_POSIX_FALLOCATE) && !POSIX_FADVISE_AIX_BUG */
Larry Hastings2f936352014-08-05 14:04:04 +100012819
Ross Lagerwall7807c352011-03-17 20:20:30 +020012820
Victor Stinnerd6b17692014-09-30 12:20:05 +020012821#if defined(HAVE_POSIX_FADVISE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +100012822/*[clinic input]
12823os.posix_fadvise
12824
12825 fd: int
12826 offset: Py_off_t
12827 length: Py_off_t
12828 advice: int
12829 /
12830
12831Announce an intention to access data in a specific pattern.
12832
12833Announce an intention to access data in a specific pattern, thus allowing
12834the kernel to make optimizations.
12835The advice applies to the region of the file specified by fd starting at
12836offset and continuing for length bytes.
12837advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,
12838POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or
12839POSIX_FADV_DONTNEED.
12840[clinic start generated code]*/
12841
12842PyDoc_STRVAR(os_posix_fadvise__doc__,
12843"posix_fadvise($module, fd, offset, length, advice, /)\n"
12844"--\n"
12845"\n"
12846"Announce an intention to access data in a specific pattern.\n"
12847"\n"
12848"Announce an intention to access data in a specific pattern, thus allowing\n"
12849"the kernel to make optimizations.\n"
12850"The advice applies to the region of the file specified by fd starting at\n"
12851"offset and continuing for length bytes.\n"
12852"advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,\n"
12853"POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or\n"
12854"POSIX_FADV_DONTNEED.");
12855
12856#define OS_POSIX_FADVISE_METHODDEF \
12857 {"posix_fadvise", (PyCFunction)os_posix_fadvise, METH_VARARGS, os_posix_fadvise__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012858
12859static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012860os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012861
Larry Hastings2f936352014-08-05 14:04:04 +100012862static PyObject *
12863os_posix_fadvise(PyModuleDef *module, PyObject *args)
12864{
12865 PyObject *return_value = NULL;
12866 int fd;
12867 Py_off_t offset;
12868 Py_off_t length;
12869 int advice;
12870
12871 if (!PyArg_ParseTuple(args,
12872 "iO&O&i:posix_fadvise",
12873 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length, &advice))
12874 goto exit;
12875 return_value = os_posix_fadvise_impl(module, fd, offset, length, advice);
12876
12877exit:
12878 return return_value;
12879}
12880
12881static PyObject *
12882os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice)
12883/*[clinic end generated code: output=dad93f32c04dd4f7 input=0fbe554edc2f04b5]*/
12884{
12885 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012886
12887 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012888 result = posix_fadvise(fd, offset, length, advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012889 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012890 if (result != 0) {
12891 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012892 return posix_error();
12893 }
12894 Py_RETURN_NONE;
12895}
Victor Stinnerec39e262014-09-30 12:35:58 +020012896#endif /* HAVE_POSIX_FADVISE && !POSIX_FADVISE_AIX_BUG */
Ross Lagerwall7807c352011-03-17 20:20:30 +020012897
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012898#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000012899
Fred Drake762e2061999-08-26 17:23:54 +000012900/* Save putenv() parameters as values here, so we can collect them when they
12901 * get re-set with another call for the same key. */
12902static PyObject *posix_putenv_garbage;
12903
Larry Hastings2f936352014-08-05 14:04:04 +100012904static void
12905posix_putenv_garbage_setitem(PyObject *name, PyObject *value)
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012906{
Larry Hastings2f936352014-08-05 14:04:04 +100012907 /* Install the first arg and newstr in posix_putenv_garbage;
12908 * this will cause previous value to be collected. This has to
12909 * happen after the real putenv() call because the old value
12910 * was still accessible until then. */
12911 if (PyDict_SetItem(posix_putenv_garbage, name, value))
12912 /* really not much we can do; just leak */
12913 PyErr_Clear();
12914 else
12915 Py_DECREF(value);
12916}
12917
12918
Thomas Hellerf78f12a2007-11-08 19:33:05 +000012919#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100012920/*[clinic input]
12921os.putenv
12922
12923 name: unicode
12924 value: unicode
12925 /
12926
12927Change or add an environment variable.
12928[clinic start generated code]*/
12929
12930PyDoc_STRVAR(os_putenv__doc__,
12931"putenv($module, name, value, /)\n"
12932"--\n"
12933"\n"
12934"Change or add an environment variable.");
12935
12936#define OS_PUTENV_METHODDEF \
12937 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
12938
12939static PyObject *
12940os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
12941
12942static PyObject *
12943os_putenv(PyModuleDef *module, PyObject *args)
12944{
12945 PyObject *return_value = NULL;
12946 PyObject *name;
12947 PyObject *value;
Victor Stinner65170952011-11-22 22:16:17 +010012948
Victor Stinner8c62be82010-05-06 00:08:46 +000012949 if (!PyArg_ParseTuple(args,
Larry Hastings2f936352014-08-05 14:04:04 +100012950 "UU:putenv",
12951 &name, &value))
12952 goto exit;
12953 return_value = os_putenv_impl(module, name, value);
Guido van Rossumd48f2521997-12-05 22:19:34 +000012954
Larry Hastings2f936352014-08-05 14:04:04 +100012955exit:
12956 return return_value;
12957}
12958
12959static PyObject *
12960os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
12961/*[clinic end generated code: output=5ce9ef9b15606e7e input=ba586581c2e6105f]*/
12962{
12963 wchar_t *env;
12964
12965 PyObject *unicode = PyUnicode_FromFormat("%U=%U", name, value);
12966 if (unicode == NULL) {
Victor Stinner84ae1182010-05-06 22:05:07 +000012967 PyErr_NoMemory();
Larry Hastings2f936352014-08-05 14:04:04 +100012968 return NULL;
Victor Stinner84ae1182010-05-06 22:05:07 +000012969 }
Larry Hastings2f936352014-08-05 14:04:04 +100012970 if (_MAX_ENV < PyUnicode_GET_LENGTH(unicode)) {
Victor Stinner65170952011-11-22 22:16:17 +010012971 PyErr_Format(PyExc_ValueError,
12972 "the environment variable is longer than %u characters",
12973 _MAX_ENV);
12974 goto error;
12975 }
12976
Larry Hastings2f936352014-08-05 14:04:04 +100012977 env = PyUnicode_AsUnicode(unicode);
12978 if (env == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +020012979 goto error;
Larry Hastings2f936352014-08-05 14:04:04 +100012980 if (_wputenv(env)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000012981 posix_error();
Victor Stinner84ae1182010-05-06 22:05:07 +000012982 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +000012983 }
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012984
Larry Hastings2f936352014-08-05 14:04:04 +100012985 posix_putenv_garbage_setitem(name, unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012986 Py_RETURN_NONE;
12987
12988error:
Larry Hastings2f936352014-08-05 14:04:04 +100012989 Py_DECREF(unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012990 return NULL;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012991}
Larry Hastings2f936352014-08-05 14:04:04 +100012992#else /* MS_WINDOWS */
12993/*[clinic input]
12994os.putenv
Guido van Rossumb6a47161997-09-15 22:54:34 +000012995
Larry Hastings2f936352014-08-05 14:04:04 +100012996 name: FSConverter
12997 value: FSConverter
12998 /
12999
13000Change or add an environment variable.
13001[clinic start generated code]*/
13002
13003PyDoc_STRVAR(os_putenv__doc__,
13004"putenv($module, name, value, /)\n"
13005"--\n"
13006"\n"
13007"Change or add an environment variable.");
13008
13009#define OS_PUTENV_METHODDEF \
13010 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
Guido van Rossumc524d952001-10-19 01:31:59 +000013011
13012static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013013os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
13014
13015static PyObject *
13016os_putenv(PyModuleDef *module, PyObject *args)
Guido van Rossumc524d952001-10-19 01:31:59 +000013017{
Larry Hastings2f936352014-08-05 14:04:04 +100013018 PyObject *return_value = NULL;
13019 PyObject *name = NULL;
13020 PyObject *value = NULL;
13021
13022 if (!PyArg_ParseTuple(args,
13023 "O&O&:putenv",
13024 PyUnicode_FSConverter, &name, PyUnicode_FSConverter, &value))
13025 goto exit;
13026 return_value = os_putenv_impl(module, name, value);
13027
13028exit:
13029 /* Cleanup for name */
13030 Py_XDECREF(name);
13031 /* Cleanup for value */
13032 Py_XDECREF(value);
13033
13034 return return_value;
13035}
13036
13037static PyObject *
13038os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
13039/*[clinic end generated code: output=85ab223393dc7afd input=a97bc6152f688d31]*/
13040{
13041 PyObject *bytes = NULL;
13042 char *env;
13043 char *name_string = PyBytes_AsString(name);
13044 char *value_string = PyBytes_AsString(value);
13045
13046 bytes = PyBytes_FromFormat("%s=%s", name_string, value_string);
13047 if (bytes == NULL) {
13048 PyErr_NoMemory();
13049 return NULL;
13050 }
13051
13052 env = PyBytes_AS_STRING(bytes);
13053 if (putenv(env)) {
13054 Py_DECREF(bytes);
13055 return posix_error();
13056 }
13057
13058 posix_putenv_garbage_setitem(name, bytes);
13059 Py_RETURN_NONE;
13060}
13061#endif /* MS_WINDOWS */
13062#endif /* HAVE_PUTENV */
13063
13064
13065#ifdef HAVE_UNSETENV
13066/*[clinic input]
13067os.unsetenv
13068 name: FSConverter
13069 /
13070
13071Delete an environment variable.
13072[clinic start generated code]*/
13073
13074PyDoc_STRVAR(os_unsetenv__doc__,
13075"unsetenv($module, name, /)\n"
13076"--\n"
13077"\n"
13078"Delete an environment variable.");
13079
13080#define OS_UNSETENV_METHODDEF \
13081 {"unsetenv", (PyCFunction)os_unsetenv, METH_VARARGS, os_unsetenv__doc__},
13082
13083static PyObject *
13084os_unsetenv_impl(PyModuleDef *module, PyObject *name);
13085
13086static PyObject *
13087os_unsetenv(PyModuleDef *module, PyObject *args)
13088{
13089 PyObject *return_value = NULL;
13090 PyObject *name = NULL;
13091
13092 if (!PyArg_ParseTuple(args,
13093 "O&:unsetenv",
13094 PyUnicode_FSConverter, &name))
13095 goto exit;
13096 return_value = os_unsetenv_impl(module, name);
13097
13098exit:
13099 /* Cleanup for name */
13100 Py_XDECREF(name);
13101
13102 return return_value;
13103}
13104
13105static PyObject *
13106os_unsetenv_impl(PyModuleDef *module, PyObject *name)
13107/*[clinic end generated code: output=91318c995f9a0767 input=2bb5288a599c7107]*/
13108{
Victor Stinner984890f2011-11-24 13:53:38 +010013109#ifndef HAVE_BROKEN_UNSETENV
Victor Stinner60b385e2011-11-22 22:01:28 +010013110 int err;
Victor Stinner984890f2011-11-24 13:53:38 +010013111#endif
Victor Stinner84ae1182010-05-06 22:05:07 +000013112
Victor Stinner984890f2011-11-24 13:53:38 +010013113#ifdef HAVE_BROKEN_UNSETENV
13114 unsetenv(PyBytes_AS_STRING(name));
13115#else
Victor Stinner65170952011-11-22 22:16:17 +010013116 err = unsetenv(PyBytes_AS_STRING(name));
Larry Hastings2f936352014-08-05 14:04:04 +100013117 if (err)
Victor Stinner60b385e2011-11-22 22:01:28 +010013118 return posix_error();
Victor Stinner984890f2011-11-24 13:53:38 +010013119#endif
Guido van Rossumc524d952001-10-19 01:31:59 +000013120
Victor Stinner8c62be82010-05-06 00:08:46 +000013121 /* Remove the key from posix_putenv_garbage;
13122 * this will cause it to be collected. This has to
13123 * happen after the real unsetenv() call because the
13124 * old value was still accessible until then.
13125 */
Victor Stinner65170952011-11-22 22:16:17 +010013126 if (PyDict_DelItem(posix_putenv_garbage, name)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013127 /* really not much we can do; just leak */
13128 PyErr_Clear();
13129 }
Victor Stinner84ae1182010-05-06 22:05:07 +000013130 Py_RETURN_NONE;
Guido van Rossumc524d952001-10-19 01:31:59 +000013131}
Larry Hastings2f936352014-08-05 14:04:04 +100013132#endif /* HAVE_UNSETENV */
Guido van Rossumc524d952001-10-19 01:31:59 +000013133
Larry Hastings2f936352014-08-05 14:04:04 +100013134
13135/*[clinic input]
13136os.strerror
13137
13138 code: int
13139 /
13140
13141Translate an error code to a message string.
13142[clinic start generated code]*/
13143
13144PyDoc_STRVAR(os_strerror__doc__,
13145"strerror($module, code, /)\n"
13146"--\n"
13147"\n"
13148"Translate an error code to a message string.");
13149
13150#define OS_STRERROR_METHODDEF \
13151 {"strerror", (PyCFunction)os_strerror, METH_VARARGS, os_strerror__doc__},
Guido van Rossumb6a47161997-09-15 22:54:34 +000013152
Guido van Rossumf68d8e52001-04-14 17:55:09 +000013153static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013154os_strerror_impl(PyModuleDef *module, int code);
13155
13156static PyObject *
13157os_strerror(PyModuleDef *module, PyObject *args)
Guido van Rossumb6a47161997-09-15 22:54:34 +000013158{
Larry Hastings2f936352014-08-05 14:04:04 +100013159 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013160 int code;
Larry Hastings2f936352014-08-05 14:04:04 +100013161
13162 if (!PyArg_ParseTuple(args,
13163 "i:strerror",
13164 &code))
13165 goto exit;
13166 return_value = os_strerror_impl(module, code);
13167
13168exit:
13169 return return_value;
13170}
13171
13172static PyObject *
13173os_strerror_impl(PyModuleDef *module, int code)
13174/*[clinic end generated code: output=8665c70bb2ca4720 input=75a8673d97915a91]*/
13175{
13176 char *message = strerror(code);
Victor Stinner8c62be82010-05-06 00:08:46 +000013177 if (message == NULL) {
13178 PyErr_SetString(PyExc_ValueError,
13179 "strerror() argument out of range");
13180 return NULL;
13181 }
Victor Stinner1b579672011-12-17 05:47:23 +010013182 return PyUnicode_DecodeLocale(message, "surrogateescape");
Guido van Rossumb6a47161997-09-15 22:54:34 +000013183}
Guido van Rossumb6a47161997-09-15 22:54:34 +000013184
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000013185
Guido van Rossumc9641791998-08-04 15:26:23 +000013186#ifdef HAVE_SYS_WAIT_H
Fred Drake106c1a02002-04-23 15:58:02 +000013187#ifdef WCOREDUMP
Larry Hastings2f936352014-08-05 14:04:04 +100013188/*[clinic input]
13189os.WCOREDUMP -> bool
13190
13191 status: int
13192 /
13193
13194Return True if the process returning status was dumped to a core file.
13195[clinic start generated code]*/
13196
13197PyDoc_STRVAR(os_WCOREDUMP__doc__,
13198"WCOREDUMP($module, status, /)\n"
13199"--\n"
13200"\n"
13201"Return True if the process returning status was dumped to a core file.");
13202
13203#define OS_WCOREDUMP_METHODDEF \
13204 {"WCOREDUMP", (PyCFunction)os_WCOREDUMP, METH_VARARGS, os_WCOREDUMP__doc__},
13205
13206static int
13207os_WCOREDUMP_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013208
13209static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013210os_WCOREDUMP(PyModuleDef *module, PyObject *args)
Fred Drake106c1a02002-04-23 15:58:02 +000013211{
Larry Hastings2f936352014-08-05 14:04:04 +100013212 PyObject *return_value = NULL;
13213 int status;
13214 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013215
Larry Hastings2f936352014-08-05 14:04:04 +100013216 if (!PyArg_ParseTuple(args,
13217 "i:WCOREDUMP",
13218 &status))
13219 goto exit;
13220 _return_value = os_WCOREDUMP_impl(module, status);
13221 if ((_return_value == -1) && PyErr_Occurred())
13222 goto exit;
13223 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013224
Larry Hastings2f936352014-08-05 14:04:04 +100013225exit:
13226 return return_value;
13227}
13228
13229static int
13230os_WCOREDUMP_impl(PyModuleDef *module, int status)
13231/*[clinic end generated code: output=e04d55c09c299828 input=8b05e7ab38528d04]*/
13232{
13233 WAIT_TYPE wait_status;
13234 WAIT_STATUS_INT(wait_status) = status;
13235 return WCOREDUMP(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013236}
13237#endif /* WCOREDUMP */
13238
Larry Hastings2f936352014-08-05 14:04:04 +100013239
Fred Drake106c1a02002-04-23 15:58:02 +000013240#ifdef WIFCONTINUED
Larry Hastings2f936352014-08-05 14:04:04 +100013241/*[clinic input]
13242os.WIFCONTINUED -> bool
13243
13244 status: int
13245
13246Return True if a particular process was continued from a job control stop.
13247
13248Return True if the process returning status was continued from a
13249job control stop.
13250[clinic start generated code]*/
13251
13252PyDoc_STRVAR(os_WIFCONTINUED__doc__,
13253"WIFCONTINUED($module, /, status)\n"
13254"--\n"
13255"\n"
13256"Return True if a particular process was continued from a job control stop.\n"
13257"\n"
13258"Return True if the process returning status was continued from a\n"
13259"job control stop.");
13260
13261#define OS_WIFCONTINUED_METHODDEF \
13262 {"WIFCONTINUED", (PyCFunction)os_WIFCONTINUED, METH_VARARGS|METH_KEYWORDS, os_WIFCONTINUED__doc__},
13263
13264static int
13265os_WIFCONTINUED_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013266
13267static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013268os_WIFCONTINUED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drake106c1a02002-04-23 15:58:02 +000013269{
Larry Hastings2f936352014-08-05 14:04:04 +100013270 PyObject *return_value = NULL;
13271 static char *_keywords[] = {"status", NULL};
13272 int status;
13273 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013274
Larry Hastings2f936352014-08-05 14:04:04 +100013275 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13276 "i:WIFCONTINUED", _keywords,
13277 &status))
13278 goto exit;
13279 _return_value = os_WIFCONTINUED_impl(module, status);
13280 if ((_return_value == -1) && PyErr_Occurred())
13281 goto exit;
13282 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013283
Larry Hastings2f936352014-08-05 14:04:04 +100013284exit:
13285 return return_value;
13286}
13287
13288static int
13289os_WIFCONTINUED_impl(PyModuleDef *module, int status)
13290/*[clinic end generated code: output=9c4e6105a4520ab5 input=e777e7d38eb25bd9]*/
13291{
13292 WAIT_TYPE wait_status;
13293 WAIT_STATUS_INT(wait_status) = status;
13294 return WIFCONTINUED(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013295}
13296#endif /* WIFCONTINUED */
13297
Larry Hastings2f936352014-08-05 14:04:04 +100013298
Guido van Rossumc9641791998-08-04 15:26:23 +000013299#ifdef WIFSTOPPED
Larry Hastings2f936352014-08-05 14:04:04 +100013300/*[clinic input]
13301os.WIFSTOPPED -> bool
13302
13303 status: int
13304
13305Return True if the process returning status was stopped.
13306[clinic start generated code]*/
13307
13308PyDoc_STRVAR(os_WIFSTOPPED__doc__,
13309"WIFSTOPPED($module, /, status)\n"
13310"--\n"
13311"\n"
13312"Return True if the process returning status was stopped.");
13313
13314#define OS_WIFSTOPPED_METHODDEF \
13315 {"WIFSTOPPED", (PyCFunction)os_WIFSTOPPED, METH_VARARGS|METH_KEYWORDS, os_WIFSTOPPED__doc__},
13316
13317static int
13318os_WIFSTOPPED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013319
13320static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013321os_WIFSTOPPED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013322{
Larry Hastings2f936352014-08-05 14:04:04 +100013323 PyObject *return_value = NULL;
13324 static char *_keywords[] = {"status", NULL};
13325 int status;
13326 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013327
Larry Hastings2f936352014-08-05 14:04:04 +100013328 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13329 "i:WIFSTOPPED", _keywords,
13330 &status))
13331 goto exit;
13332 _return_value = os_WIFSTOPPED_impl(module, status);
13333 if ((_return_value == -1) && PyErr_Occurred())
13334 goto exit;
13335 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013336
Larry Hastings2f936352014-08-05 14:04:04 +100013337exit:
13338 return return_value;
13339}
13340
13341static int
13342os_WIFSTOPPED_impl(PyModuleDef *module, int status)
13343/*[clinic end generated code: output=e0de2da8ec9593ff input=043cb7f1289ef904]*/
13344{
13345 WAIT_TYPE wait_status;
13346 WAIT_STATUS_INT(wait_status) = status;
13347 return WIFSTOPPED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013348}
13349#endif /* WIFSTOPPED */
13350
Larry Hastings2f936352014-08-05 14:04:04 +100013351
Guido van Rossumc9641791998-08-04 15:26:23 +000013352#ifdef WIFSIGNALED
Larry Hastings2f936352014-08-05 14:04:04 +100013353/*[clinic input]
13354os.WIFSIGNALED -> bool
13355
13356 status: int
13357
13358Return True if the process returning status was terminated by a signal.
13359[clinic start generated code]*/
13360
13361PyDoc_STRVAR(os_WIFSIGNALED__doc__,
13362"WIFSIGNALED($module, /, status)\n"
13363"--\n"
13364"\n"
13365"Return True if the process returning status was terminated by a signal.");
13366
13367#define OS_WIFSIGNALED_METHODDEF \
13368 {"WIFSIGNALED", (PyCFunction)os_WIFSIGNALED, METH_VARARGS|METH_KEYWORDS, os_WIFSIGNALED__doc__},
13369
13370static int
13371os_WIFSIGNALED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013372
13373static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013374os_WIFSIGNALED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013375{
Larry Hastings2f936352014-08-05 14:04:04 +100013376 PyObject *return_value = NULL;
13377 static char *_keywords[] = {"status", NULL};
13378 int status;
13379 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013380
Larry Hastings2f936352014-08-05 14:04:04 +100013381 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13382 "i:WIFSIGNALED", _keywords,
13383 &status))
13384 goto exit;
13385 _return_value = os_WIFSIGNALED_impl(module, status);
13386 if ((_return_value == -1) && PyErr_Occurred())
13387 goto exit;
13388 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013389
Larry Hastings2f936352014-08-05 14:04:04 +100013390exit:
13391 return return_value;
13392}
13393
13394static int
13395os_WIFSIGNALED_impl(PyModuleDef *module, int status)
13396/*[clinic end generated code: output=f14d106558f406be input=d55ba7cc9ce5dc43]*/
13397{
13398 WAIT_TYPE wait_status;
13399 WAIT_STATUS_INT(wait_status) = status;
13400 return WIFSIGNALED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013401}
13402#endif /* WIFSIGNALED */
13403
Larry Hastings2f936352014-08-05 14:04:04 +100013404
Guido van Rossumc9641791998-08-04 15:26:23 +000013405#ifdef WIFEXITED
Larry Hastings2f936352014-08-05 14:04:04 +100013406/*[clinic input]
13407os.WIFEXITED -> bool
13408
13409 status: int
13410
13411Return True if the process returning status exited via the exit() system call.
13412[clinic start generated code]*/
13413
13414PyDoc_STRVAR(os_WIFEXITED__doc__,
13415"WIFEXITED($module, /, status)\n"
13416"--\n"
13417"\n"
13418"Return True if the process returning status exited via the exit() system call.");
13419
13420#define OS_WIFEXITED_METHODDEF \
13421 {"WIFEXITED", (PyCFunction)os_WIFEXITED, METH_VARARGS|METH_KEYWORDS, os_WIFEXITED__doc__},
13422
13423static int
13424os_WIFEXITED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013425
13426static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013427os_WIFEXITED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013428{
Larry Hastings2f936352014-08-05 14:04:04 +100013429 PyObject *return_value = NULL;
13430 static char *_keywords[] = {"status", NULL};
13431 int status;
13432 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013433
Larry Hastings2f936352014-08-05 14:04:04 +100013434 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13435 "i:WIFEXITED", _keywords,
13436 &status))
13437 goto exit;
13438 _return_value = os_WIFEXITED_impl(module, status);
13439 if ((_return_value == -1) && PyErr_Occurred())
13440 goto exit;
13441 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013442
Larry Hastings2f936352014-08-05 14:04:04 +100013443exit:
13444 return return_value;
13445}
13446
13447static int
13448os_WIFEXITED_impl(PyModuleDef *module, int status)
13449/*[clinic end generated code: output=2f76087d53721255 input=d63775a6791586c0]*/
13450{
13451 WAIT_TYPE wait_status;
13452 WAIT_STATUS_INT(wait_status) = status;
13453 return WIFEXITED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013454}
13455#endif /* WIFEXITED */
13456
Larry Hastings2f936352014-08-05 14:04:04 +100013457
Guido van Rossum54ecc3d1999-01-27 17:53:11 +000013458#ifdef WEXITSTATUS
Larry Hastings2f936352014-08-05 14:04:04 +100013459/*[clinic input]
13460os.WEXITSTATUS -> int
13461
13462 status: int
13463
13464Return the process return code from status.
13465[clinic start generated code]*/
13466
13467PyDoc_STRVAR(os_WEXITSTATUS__doc__,
13468"WEXITSTATUS($module, /, status)\n"
13469"--\n"
13470"\n"
13471"Return the process return code from status.");
13472
13473#define OS_WEXITSTATUS_METHODDEF \
13474 {"WEXITSTATUS", (PyCFunction)os_WEXITSTATUS, METH_VARARGS|METH_KEYWORDS, os_WEXITSTATUS__doc__},
13475
13476static int
13477os_WEXITSTATUS_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013478
13479static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013480os_WEXITSTATUS(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013481{
Larry Hastings2f936352014-08-05 14:04:04 +100013482 PyObject *return_value = NULL;
13483 static char *_keywords[] = {"status", NULL};
13484 int status;
13485 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013486
Larry Hastings2f936352014-08-05 14:04:04 +100013487 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13488 "i:WEXITSTATUS", _keywords,
13489 &status))
13490 goto exit;
13491 _return_value = os_WEXITSTATUS_impl(module, status);
13492 if ((_return_value == -1) && PyErr_Occurred())
13493 goto exit;
13494 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013495
Larry Hastings2f936352014-08-05 14:04:04 +100013496exit:
13497 return return_value;
13498}
13499
13500static int
13501os_WEXITSTATUS_impl(PyModuleDef *module, int status)
13502/*[clinic end generated code: output=13b6c270e2a326b1 input=e1fb4944e377585b]*/
13503{
13504 WAIT_TYPE wait_status;
13505 WAIT_STATUS_INT(wait_status) = status;
13506 return WEXITSTATUS(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013507}
13508#endif /* WEXITSTATUS */
13509
Larry Hastings2f936352014-08-05 14:04:04 +100013510
Guido van Rossumc9641791998-08-04 15:26:23 +000013511#ifdef WTERMSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013512/*[clinic input]
13513os.WTERMSIG -> int
13514
13515 status: int
13516
13517Return the signal that terminated the process that provided the status value.
13518[clinic start generated code]*/
13519
13520PyDoc_STRVAR(os_WTERMSIG__doc__,
13521"WTERMSIG($module, /, status)\n"
13522"--\n"
13523"\n"
13524"Return the signal that terminated the process that provided the status value.");
13525
13526#define OS_WTERMSIG_METHODDEF \
13527 {"WTERMSIG", (PyCFunction)os_WTERMSIG, METH_VARARGS|METH_KEYWORDS, os_WTERMSIG__doc__},
13528
13529static int
13530os_WTERMSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013531
13532static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013533os_WTERMSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013534{
Larry Hastings2f936352014-08-05 14:04:04 +100013535 PyObject *return_value = NULL;
13536 static char *_keywords[] = {"status", NULL};
13537 int status;
13538 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013539
Larry Hastings2f936352014-08-05 14:04:04 +100013540 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13541 "i:WTERMSIG", _keywords,
13542 &status))
13543 goto exit;
13544 _return_value = os_WTERMSIG_impl(module, status);
13545 if ((_return_value == -1) && PyErr_Occurred())
13546 goto exit;
13547 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013548
Larry Hastings2f936352014-08-05 14:04:04 +100013549exit:
13550 return return_value;
13551}
13552
13553static int
13554os_WTERMSIG_impl(PyModuleDef *module, int status)
13555/*[clinic end generated code: output=bf1fd4b002d0a9ed input=727fd7f84ec3f243]*/
13556{
13557 WAIT_TYPE wait_status;
13558 WAIT_STATUS_INT(wait_status) = status;
13559 return WTERMSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013560}
13561#endif /* WTERMSIG */
13562
Larry Hastings2f936352014-08-05 14:04:04 +100013563
Guido van Rossumc9641791998-08-04 15:26:23 +000013564#ifdef WSTOPSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013565/*[clinic input]
13566os.WSTOPSIG -> int
13567
13568 status: int
13569
13570Return the signal that stopped the process that provided the status value.
13571[clinic start generated code]*/
13572
13573PyDoc_STRVAR(os_WSTOPSIG__doc__,
13574"WSTOPSIG($module, /, status)\n"
13575"--\n"
13576"\n"
13577"Return the signal that stopped the process that provided the status value.");
13578
13579#define OS_WSTOPSIG_METHODDEF \
13580 {"WSTOPSIG", (PyCFunction)os_WSTOPSIG, METH_VARARGS|METH_KEYWORDS, os_WSTOPSIG__doc__},
13581
13582static int
13583os_WSTOPSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013584
13585static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013586os_WSTOPSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013587{
Larry Hastings2f936352014-08-05 14:04:04 +100013588 PyObject *return_value = NULL;
13589 static char *_keywords[] = {"status", NULL};
13590 int status;
13591 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013592
Larry Hastings2f936352014-08-05 14:04:04 +100013593 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13594 "i:WSTOPSIG", _keywords,
13595 &status))
13596 goto exit;
13597 _return_value = os_WSTOPSIG_impl(module, status);
13598 if ((_return_value == -1) && PyErr_Occurred())
13599 goto exit;
13600 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013601
Larry Hastings2f936352014-08-05 14:04:04 +100013602exit:
13603 return return_value;
13604}
13605
13606static int
13607os_WSTOPSIG_impl(PyModuleDef *module, int status)
13608/*[clinic end generated code: output=92e1647d29ee0549 input=46ebf1d1b293c5c1]*/
13609{
13610 WAIT_TYPE wait_status;
13611 WAIT_STATUS_INT(wait_status) = status;
13612 return WSTOPSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013613}
13614#endif /* WSTOPSIG */
Guido van Rossumc9641791998-08-04 15:26:23 +000013615#endif /* HAVE_SYS_WAIT_H */
13616
13617
Larry Hastings2f936352014-08-05 14:04:04 +100013618#ifndef OS_WCOREDUMP_METHODDEF
13619#define OS_WCOREDUMP_METHODDEF
13620#endif /* OS_WCOREDUMP_METHODDEF */
13621
13622#ifndef OS_WIFCONTINUED_METHODDEF
13623#define OS_WIFCONTINUED_METHODDEF
13624#endif /* OS_WIFCONTINUED_METHODDEF */
13625
13626#ifndef OS_WIFSTOPPED_METHODDEF
13627#define OS_WIFSTOPPED_METHODDEF
13628#endif /* OS_WIFSTOPPED_METHODDEF */
13629
13630#ifndef OS_WIFSIGNALED_METHODDEF
13631#define OS_WIFSIGNALED_METHODDEF
13632#endif /* OS_WIFSIGNALED_METHODDEF */
13633
13634#ifndef OS_WIFEXITED_METHODDEF
13635#define OS_WIFEXITED_METHODDEF
13636#endif /* OS_WIFEXITED_METHODDEF */
13637
13638#ifndef OS_WEXITSTATUS_METHODDEF
13639#define OS_WEXITSTATUS_METHODDEF
13640#endif /* OS_WEXITSTATUS_METHODDEF */
13641
13642#ifndef OS_WTERMSIG_METHODDEF
13643#define OS_WTERMSIG_METHODDEF
13644#endif /* OS_WTERMSIG_METHODDEF */
13645
13646#ifndef OS_WSTOPSIG_METHODDEF
13647#define OS_WSTOPSIG_METHODDEF
13648#endif /* OS_WSTOPSIG_METHODDEF */
13649
13650
Thomas Wouters477c8d52006-05-27 19:21:47 +000013651#if defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossumd5753e11999-10-19 13:29:23 +000013652#ifdef _SCO_DS
13653/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
13654 needed definitions in sys/statvfs.h */
13655#define _SVID3
13656#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000013657#include <sys/statvfs.h>
13658
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013659static PyObject*
13660_pystatvfs_fromstructstatvfs(struct statvfs st) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013661 PyObject *v = PyStructSequence_New(&StatVFSResultType);
13662 if (v == NULL)
13663 return NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013664
13665#if !defined(HAVE_LARGEFILE_SUPPORT)
Victor Stinner8c62be82010-05-06 00:08:46 +000013666 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13667 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13668 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long) st.f_blocks));
13669 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long) st.f_bfree));
13670 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong((long) st.f_bavail));
13671 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong((long) st.f_files));
13672 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong((long) st.f_ffree));
13673 PyStructSequence_SET_ITEM(v, 7, PyLong_FromLong((long) st.f_favail));
13674 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13675 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013676#else
Victor Stinner8c62be82010-05-06 00:08:46 +000013677 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13678 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13679 PyStructSequence_SET_ITEM(v, 2,
13680 PyLong_FromLongLong((PY_LONG_LONG) st.f_blocks));
13681 PyStructSequence_SET_ITEM(v, 3,
13682 PyLong_FromLongLong((PY_LONG_LONG) st.f_bfree));
13683 PyStructSequence_SET_ITEM(v, 4,
13684 PyLong_FromLongLong((PY_LONG_LONG) st.f_bavail));
13685 PyStructSequence_SET_ITEM(v, 5,
13686 PyLong_FromLongLong((PY_LONG_LONG) st.f_files));
13687 PyStructSequence_SET_ITEM(v, 6,
13688 PyLong_FromLongLong((PY_LONG_LONG) st.f_ffree));
13689 PyStructSequence_SET_ITEM(v, 7,
13690 PyLong_FromLongLong((PY_LONG_LONG) st.f_favail));
13691 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13692 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013693#endif
Victor Stinnerf0a7bac2013-10-30 18:55:24 +010013694 if (PyErr_Occurred()) {
13695 Py_DECREF(v);
13696 return NULL;
13697 }
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013698
Victor Stinner8c62be82010-05-06 00:08:46 +000013699 return v;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013700}
13701
Larry Hastings2f936352014-08-05 14:04:04 +100013702
13703/*[clinic input]
13704os.fstatvfs
13705 fd: int
13706 /
13707
13708Perform an fstatvfs system call on the given fd.
13709
13710Equivalent to statvfs(fd).
13711[clinic start generated code]*/
13712
13713PyDoc_STRVAR(os_fstatvfs__doc__,
13714"fstatvfs($module, fd, /)\n"
13715"--\n"
13716"\n"
13717"Perform an fstatvfs system call on the given fd.\n"
13718"\n"
13719"Equivalent to statvfs(fd).");
13720
13721#define OS_FSTATVFS_METHODDEF \
13722 {"fstatvfs", (PyCFunction)os_fstatvfs, METH_VARARGS, os_fstatvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013723
13724static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013725os_fstatvfs_impl(PyModuleDef *module, int fd);
13726
13727static PyObject *
13728os_fstatvfs(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013729{
Larry Hastings2f936352014-08-05 14:04:04 +100013730 PyObject *return_value = NULL;
13731 int fd;
13732
13733 if (!PyArg_ParseTuple(args,
13734 "i:fstatvfs",
13735 &fd))
13736 goto exit;
13737 return_value = os_fstatvfs_impl(module, fd);
13738
13739exit:
13740 return return_value;
13741}
13742
13743static PyObject *
13744os_fstatvfs_impl(PyModuleDef *module, int fd)
13745/*[clinic end generated code: output=0e32bf07f946ec0d input=d8122243ac50975e]*/
13746{
13747 int result;
Victor Stinner8c62be82010-05-06 00:08:46 +000013748 struct statvfs st;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013749
Victor Stinner8c62be82010-05-06 00:08:46 +000013750 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013751 result = fstatvfs(fd, &st);
Victor Stinner8c62be82010-05-06 00:08:46 +000013752 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013753 if (result != 0)
Victor Stinner8c62be82010-05-06 00:08:46 +000013754 return posix_error();
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013755
Victor Stinner8c62be82010-05-06 00:08:46 +000013756 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013757}
Larry Hastings2f936352014-08-05 14:04:04 +100013758#endif /* defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H) */
Guido van Rossum94f6f721999-01-06 18:42:14 +000013759
13760
Thomas Wouters477c8d52006-05-27 19:21:47 +000013761#if defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013762#include <sys/statvfs.h>
Larry Hastings2f936352014-08-05 14:04:04 +100013763/*[clinic input]
13764os.statvfs
Guido van Rossum94f6f721999-01-06 18:42:14 +000013765
Larry Hastings2f936352014-08-05 14:04:04 +100013766 path: path_t(allow_fd='PATH_HAVE_FSTATVFS')
13767
13768Perform a statvfs system call on the given path.
13769
13770path may always be specified as a string.
13771On some platforms, path may also be specified as an open file descriptor.
13772 If this functionality is unavailable, using it raises an exception.
13773[clinic start generated code]*/
13774
13775PyDoc_STRVAR(os_statvfs__doc__,
13776"statvfs($module, /, path)\n"
13777"--\n"
13778"\n"
13779"Perform a statvfs system call on the given path.\n"
13780"\n"
13781"path may always be specified as a string.\n"
13782"On some platforms, path may also be specified as an open file descriptor.\n"
13783" If this functionality is unavailable, using it raises an exception.");
13784
13785#define OS_STATVFS_METHODDEF \
13786 {"statvfs", (PyCFunction)os_statvfs, METH_VARARGS|METH_KEYWORDS, os_statvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013787
13788static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013789os_statvfs_impl(PyModuleDef *module, path_t *path);
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013790
Larry Hastings2f936352014-08-05 14:04:04 +100013791static PyObject *
13792os_statvfs(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13793{
13794 PyObject *return_value = NULL;
13795 static char *_keywords[] = {"path", NULL};
13796 path_t path = PATH_T_INITIALIZE("statvfs", "path", 0, PATH_HAVE_FSTATVFS);
13797
13798 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13799 "O&:statvfs", _keywords,
13800 path_converter, &path))
13801 goto exit;
13802 return_value = os_statvfs_impl(module, &path);
13803
13804exit:
13805 /* Cleanup for path */
13806 path_cleanup(&path);
13807
13808 return return_value;
13809}
13810
13811static PyObject *
13812os_statvfs_impl(PyModuleDef *module, path_t *path)
13813/*[clinic end generated code: output=00ff54983360b446 input=3f5c35791c669bd9]*/
13814{
13815 int result;
13816 struct statvfs st;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013817
13818 Py_BEGIN_ALLOW_THREADS
13819#ifdef HAVE_FSTATVFS
Larry Hastings2f936352014-08-05 14:04:04 +100013820 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070013821#ifdef __APPLE__
13822 /* handle weak-linking on Mac OS X 10.3 */
13823 if (fstatvfs == NULL) {
Larry Hastings2f936352014-08-05 14:04:04 +100013824 fd_specified("statvfs", path->fd);
13825 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013826 }
13827#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013828 result = fstatvfs(path->fd, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013829 }
13830 else
13831#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013832 result = statvfs(path->narrow, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013833 Py_END_ALLOW_THREADS
13834
13835 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100013836 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013837 }
13838
Larry Hastings2f936352014-08-05 14:04:04 +100013839 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013840}
Larry Hastings2f936352014-08-05 14:04:04 +100013841#endif /* defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H) */
13842
Guido van Rossum94f6f721999-01-06 18:42:14 +000013843
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013844#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100013845/*[clinic input]
13846os._getdiskusage
13847
13848 path: Py_UNICODE
13849
13850Return disk usage statistics about the given path as a (total, free) tuple.
13851[clinic start generated code]*/
13852
13853PyDoc_STRVAR(os__getdiskusage__doc__,
13854"_getdiskusage($module, /, path)\n"
13855"--\n"
13856"\n"
13857"Return disk usage statistics about the given path as a (total, free) tuple.");
13858
13859#define OS__GETDISKUSAGE_METHODDEF \
13860 {"_getdiskusage", (PyCFunction)os__getdiskusage, METH_VARARGS|METH_KEYWORDS, os__getdiskusage__doc__},
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013861
13862static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013863os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path);
13864
13865static PyObject *
13866os__getdiskusage(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13867{
13868 PyObject *return_value = NULL;
13869 static char *_keywords[] = {"path", NULL};
13870 Py_UNICODE *path;
13871
13872 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13873 "u:_getdiskusage", _keywords,
13874 &path))
13875 goto exit;
13876 return_value = os__getdiskusage_impl(module, path);
13877
13878exit:
13879 return return_value;
13880}
13881
13882static PyObject *
13883os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path)
13884/*[clinic end generated code: output=054c972179b13708 input=6458133aed893c78]*/
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013885{
13886 BOOL retval;
13887 ULARGE_INTEGER _, total, free;
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013888
13889 Py_BEGIN_ALLOW_THREADS
Victor Stinner6139c1b2011-11-09 22:14:14 +010013890 retval = GetDiskFreeSpaceExW(path, &_, &total, &free);
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013891 Py_END_ALLOW_THREADS
13892 if (retval == 0)
13893 return PyErr_SetFromWindowsErr(0);
13894
13895 return Py_BuildValue("(LL)", total.QuadPart, free.QuadPart);
13896}
Larry Hastings2f936352014-08-05 14:04:04 +100013897#endif /* MS_WINDOWS */
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013898
13899
Fred Drakec9680921999-12-13 16:37:25 +000013900/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
13901 * It maps strings representing configuration variable names to
13902 * integer values, allowing those functions to be called with the
Thomas Wouters7e474022000-07-16 12:04:32 +000013903 * magic names instead of polluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +000013904 * rarely-used constants. There are three separate tables that use
13905 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +000013906 *
13907 * This code is always included, even if none of the interfaces that
13908 * need it are included. The #if hackery needed to avoid it would be
13909 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +000013910 */
13911struct constdef {
13912 char *name;
13913 long value;
13914};
13915
Fred Drake12c6e2d1999-12-14 21:25:03 +000013916static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000013917conv_confname(PyObject *arg, int *valuep, struct constdef *table,
Guido van Rossum7d5baac2007-08-27 23:24:46 +000013918 size_t tablesize)
Fred Drake12c6e2d1999-12-14 21:25:03 +000013919{
Christian Heimes217cfd12007-12-02 14:31:20 +000013920 if (PyLong_Check(arg)) {
Stefan Krah0e803b32010-11-26 16:16:47 +000013921 *valuep = PyLong_AS_LONG(arg);
13922 return 1;
Fred Drake12c6e2d1999-12-14 21:25:03 +000013923 }
Guido van Rossumbce56a62007-05-10 18:04:33 +000013924 else {
Stefan Krah0e803b32010-11-26 16:16:47 +000013925 /* look up the value in the table using a binary search */
13926 size_t lo = 0;
13927 size_t mid;
13928 size_t hi = tablesize;
13929 int cmp;
13930 const char *confname;
13931 if (!PyUnicode_Check(arg)) {
13932 PyErr_SetString(PyExc_TypeError,
13933 "configuration names must be strings or integers");
13934 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013935 }
Stefan Krah0e803b32010-11-26 16:16:47 +000013936 confname = _PyUnicode_AsString(arg);
13937 if (confname == NULL)
13938 return 0;
13939 while (lo < hi) {
13940 mid = (lo + hi) / 2;
13941 cmp = strcmp(confname, table[mid].name);
13942 if (cmp < 0)
13943 hi = mid;
13944 else if (cmp > 0)
13945 lo = mid + 1;
13946 else {
13947 *valuep = table[mid].value;
13948 return 1;
13949 }
13950 }
13951 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
13952 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013953 }
Fred Drake12c6e2d1999-12-14 21:25:03 +000013954}
13955
13956
13957#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
13958static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +000013959#ifdef _PC_ABI_AIO_XFER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013960 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000013961#endif
13962#ifdef _PC_ABI_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013963 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
Fred Draked86ed291999-12-15 15:34:33 +000013964#endif
Fred Drakec9680921999-12-13 16:37:25 +000013965#ifdef _PC_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013966 {"PC_ASYNC_IO", _PC_ASYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013967#endif
13968#ifdef _PC_CHOWN_RESTRICTED
Victor Stinner8c62be82010-05-06 00:08:46 +000013969 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
Fred Drakec9680921999-12-13 16:37:25 +000013970#endif
13971#ifdef _PC_FILESIZEBITS
Victor Stinner8c62be82010-05-06 00:08:46 +000013972 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
Fred Drakec9680921999-12-13 16:37:25 +000013973#endif
13974#ifdef _PC_LAST
Victor Stinner8c62be82010-05-06 00:08:46 +000013975 {"PC_LAST", _PC_LAST},
Fred Drakec9680921999-12-13 16:37:25 +000013976#endif
13977#ifdef _PC_LINK_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013978 {"PC_LINK_MAX", _PC_LINK_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013979#endif
13980#ifdef _PC_MAX_CANON
Victor Stinner8c62be82010-05-06 00:08:46 +000013981 {"PC_MAX_CANON", _PC_MAX_CANON},
Fred Drakec9680921999-12-13 16:37:25 +000013982#endif
13983#ifdef _PC_MAX_INPUT
Victor Stinner8c62be82010-05-06 00:08:46 +000013984 {"PC_MAX_INPUT", _PC_MAX_INPUT},
Fred Drakec9680921999-12-13 16:37:25 +000013985#endif
13986#ifdef _PC_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013987 {"PC_NAME_MAX", _PC_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013988#endif
13989#ifdef _PC_NO_TRUNC
Victor Stinner8c62be82010-05-06 00:08:46 +000013990 {"PC_NO_TRUNC", _PC_NO_TRUNC},
Fred Drakec9680921999-12-13 16:37:25 +000013991#endif
13992#ifdef _PC_PATH_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013993 {"PC_PATH_MAX", _PC_PATH_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013994#endif
13995#ifdef _PC_PIPE_BUF
Victor Stinner8c62be82010-05-06 00:08:46 +000013996 {"PC_PIPE_BUF", _PC_PIPE_BUF},
Fred Drakec9680921999-12-13 16:37:25 +000013997#endif
13998#ifdef _PC_PRIO_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013999 {"PC_PRIO_IO", _PC_PRIO_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014000#endif
14001#ifdef _PC_SOCK_MAXBUF
Victor Stinner8c62be82010-05-06 00:08:46 +000014002 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
Fred Drakec9680921999-12-13 16:37:25 +000014003#endif
14004#ifdef _PC_SYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014005 {"PC_SYNC_IO", _PC_SYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014006#endif
14007#ifdef _PC_VDISABLE
Victor Stinner8c62be82010-05-06 00:08:46 +000014008 {"PC_VDISABLE", _PC_VDISABLE},
Fred Drakec9680921999-12-13 16:37:25 +000014009#endif
Jesus Cea7e9065c2010-10-25 13:02:04 +000014010#ifdef _PC_ACL_ENABLED
14011 {"PC_ACL_ENABLED", _PC_ACL_ENABLED},
14012#endif
14013#ifdef _PC_MIN_HOLE_SIZE
14014 {"PC_MIN_HOLE_SIZE", _PC_MIN_HOLE_SIZE},
14015#endif
14016#ifdef _PC_ALLOC_SIZE_MIN
14017 {"PC_ALLOC_SIZE_MIN", _PC_ALLOC_SIZE_MIN},
14018#endif
14019#ifdef _PC_REC_INCR_XFER_SIZE
14020 {"PC_REC_INCR_XFER_SIZE", _PC_REC_INCR_XFER_SIZE},
14021#endif
14022#ifdef _PC_REC_MAX_XFER_SIZE
14023 {"PC_REC_MAX_XFER_SIZE", _PC_REC_MAX_XFER_SIZE},
14024#endif
14025#ifdef _PC_REC_MIN_XFER_SIZE
14026 {"PC_REC_MIN_XFER_SIZE", _PC_REC_MIN_XFER_SIZE},
14027#endif
14028#ifdef _PC_REC_XFER_ALIGN
14029 {"PC_REC_XFER_ALIGN", _PC_REC_XFER_ALIGN},
14030#endif
14031#ifdef _PC_SYMLINK_MAX
14032 {"PC_SYMLINK_MAX", _PC_SYMLINK_MAX},
14033#endif
14034#ifdef _PC_XATTR_ENABLED
14035 {"PC_XATTR_ENABLED", _PC_XATTR_ENABLED},
14036#endif
14037#ifdef _PC_XATTR_EXISTS
14038 {"PC_XATTR_EXISTS", _PC_XATTR_EXISTS},
14039#endif
14040#ifdef _PC_TIMESTAMP_RESOLUTION
14041 {"PC_TIMESTAMP_RESOLUTION", _PC_TIMESTAMP_RESOLUTION},
14042#endif
Fred Drakec9680921999-12-13 16:37:25 +000014043};
14044
Fred Drakec9680921999-12-13 16:37:25 +000014045static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014046conv_path_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014047{
14048 return conv_confname(arg, valuep, posix_constants_pathconf,
14049 sizeof(posix_constants_pathconf)
14050 / sizeof(struct constdef));
14051}
14052#endif
14053
Larry Hastings2f936352014-08-05 14:04:04 +100014054
Fred Drakec9680921999-12-13 16:37:25 +000014055#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014056/*[clinic input]
14057os.fpathconf -> long
14058
14059 fd: int
14060 name: path_confname
14061 /
14062
14063Return the configuration limit name for the file descriptor fd.
14064
14065If there is no limit, return -1.
14066[clinic start generated code]*/
14067
14068PyDoc_STRVAR(os_fpathconf__doc__,
14069"fpathconf($module, fd, name, /)\n"
14070"--\n"
14071"\n"
14072"Return the configuration limit name for the file descriptor fd.\n"
14073"\n"
14074"If there is no limit, return -1.");
14075
14076#define OS_FPATHCONF_METHODDEF \
14077 {"fpathconf", (PyCFunction)os_fpathconf, METH_VARARGS, os_fpathconf__doc__},
14078
14079static long
14080os_fpathconf_impl(PyModuleDef *module, int fd, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014081
14082static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014083os_fpathconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014084{
Larry Hastings2f936352014-08-05 14:04:04 +100014085 PyObject *return_value = NULL;
14086 int fd;
14087 int name;
14088 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014089
Larry Hastings2f936352014-08-05 14:04:04 +100014090 if (!PyArg_ParseTuple(args,
14091 "iO&:fpathconf",
14092 &fd, conv_path_confname, &name))
14093 goto exit;
14094 _return_value = os_fpathconf_impl(module, fd, name);
14095 if ((_return_value == -1) && PyErr_Occurred())
14096 goto exit;
14097 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014098
Larry Hastings2f936352014-08-05 14:04:04 +100014099exit:
14100 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014101}
Larry Hastings2f936352014-08-05 14:04:04 +100014102
14103static long
14104os_fpathconf_impl(PyModuleDef *module, int fd, int name)
14105/*[clinic end generated code: output=3bf04b40e0523a8c input=5942a024d3777810]*/
14106{
14107 long limit;
14108
14109 errno = 0;
14110 limit = fpathconf(fd, name);
14111 if (limit == -1 && errno != 0)
14112 posix_error();
14113
14114 return limit;
14115}
14116#endif /* HAVE_FPATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014117
14118
14119#ifdef HAVE_PATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014120/*[clinic input]
14121os.pathconf -> long
14122 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
14123 name: path_confname
14124
14125Return the configuration limit name for the file or directory path.
14126
14127If there is no limit, return -1.
14128On some platforms, path may also be specified as an open file descriptor.
14129 If this functionality is unavailable, using it raises an exception.
14130[clinic start generated code]*/
14131
14132PyDoc_STRVAR(os_pathconf__doc__,
14133"pathconf($module, /, path, name)\n"
14134"--\n"
14135"\n"
14136"Return the configuration limit name for the file or directory path.\n"
14137"\n"
14138"If there is no limit, return -1.\n"
14139"On some platforms, path may also be specified as an open file descriptor.\n"
14140" If this functionality is unavailable, using it raises an exception.");
14141
14142#define OS_PATHCONF_METHODDEF \
14143 {"pathconf", (PyCFunction)os_pathconf, METH_VARARGS|METH_KEYWORDS, os_pathconf__doc__},
14144
14145static long
14146os_pathconf_impl(PyModuleDef *module, path_t *path, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014147
14148static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014149os_pathconf(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drakec9680921999-12-13 16:37:25 +000014150{
Larry Hastings2f936352014-08-05 14:04:04 +100014151 PyObject *return_value = NULL;
14152 static char *_keywords[] = {"path", "name", NULL};
14153 path_t path = PATH_T_INITIALIZE("pathconf", "path", 0, PATH_HAVE_FPATHCONF);
Fred Drakec9680921999-12-13 16:37:25 +000014154 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014155 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014156
Larry Hastings2f936352014-08-05 14:04:04 +100014157 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
14158 "O&O&:pathconf", _keywords,
14159 path_converter, &path, conv_path_confname, &name))
14160 goto exit;
14161 _return_value = os_pathconf_impl(module, &path, name);
14162 if ((_return_value == -1) && PyErr_Occurred())
14163 goto exit;
14164 return_value = PyLong_FromLong(_return_value);
14165
14166exit:
14167 /* Cleanup for path */
14168 path_cleanup(&path);
14169
14170 return return_value;
14171}
14172
14173static long
14174os_pathconf_impl(PyModuleDef *module, path_t *path, int name)
14175/*[clinic end generated code: output=1a53e125b6cf63e4 input=bc3e2a985af27e5e]*/
14176{
Victor Stinner8c62be82010-05-06 00:08:46 +000014177 long limit;
Fred Drakec9680921999-12-13 16:37:25 +000014178
Victor Stinner8c62be82010-05-06 00:08:46 +000014179 errno = 0;
Georg Brandl306336b2012-06-24 12:55:33 +020014180#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014181 if (path->fd != -1)
14182 limit = fpathconf(path->fd, name);
Georg Brandl306336b2012-06-24 12:55:33 +020014183 else
14184#endif
Larry Hastings2f936352014-08-05 14:04:04 +100014185 limit = pathconf(path->narrow, name);
Victor Stinner8c62be82010-05-06 00:08:46 +000014186 if (limit == -1 && errno != 0) {
14187 if (errno == EINVAL)
Stefan Krah99439262010-11-26 12:58:05 +000014188 /* could be a path or name problem */
14189 posix_error();
Fred Drakec9680921999-12-13 16:37:25 +000014190 else
Larry Hastings2f936352014-08-05 14:04:04 +100014191 path_error(path);
Victor Stinner8c62be82010-05-06 00:08:46 +000014192 }
Larry Hastings2f936352014-08-05 14:04:04 +100014193
14194 return limit;
Fred Drakec9680921999-12-13 16:37:25 +000014195}
Larry Hastings2f936352014-08-05 14:04:04 +100014196#endif /* HAVE_PATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014197
14198#ifdef HAVE_CONFSTR
14199static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +000014200#ifdef _CS_ARCHITECTURE
Victor Stinner8c62be82010-05-06 00:08:46 +000014201 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
Fred Draked86ed291999-12-15 15:34:33 +000014202#endif
Mark Dickinson876d7c82010-04-16 12:47:52 +000014203#ifdef _CS_GNU_LIBC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014204 {"CS_GNU_LIBC_VERSION", _CS_GNU_LIBC_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014205#endif
14206#ifdef _CS_GNU_LIBPTHREAD_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014207 {"CS_GNU_LIBPTHREAD_VERSION", _CS_GNU_LIBPTHREAD_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014208#endif
Fred Draked86ed291999-12-15 15:34:33 +000014209#ifdef _CS_HOSTNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014210 {"CS_HOSTNAME", _CS_HOSTNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014211#endif
14212#ifdef _CS_HW_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014213 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014214#endif
14215#ifdef _CS_HW_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014216 {"CS_HW_SERIAL", _CS_HW_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014217#endif
14218#ifdef _CS_INITTAB_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014219 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014220#endif
Fred Drakec9680921999-12-13 16:37:25 +000014221#ifdef _CS_LFS64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014222 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014223#endif
14224#ifdef _CS_LFS64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014225 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014226#endif
14227#ifdef _CS_LFS64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014228 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014229#endif
14230#ifdef _CS_LFS64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014231 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014232#endif
14233#ifdef _CS_LFS_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014234 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014235#endif
14236#ifdef _CS_LFS_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014237 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014238#endif
14239#ifdef _CS_LFS_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014240 {"CS_LFS_LIBS", _CS_LFS_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014241#endif
14242#ifdef _CS_LFS_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014243 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014244#endif
Fred Draked86ed291999-12-15 15:34:33 +000014245#ifdef _CS_MACHINE
Victor Stinner8c62be82010-05-06 00:08:46 +000014246 {"CS_MACHINE", _CS_MACHINE},
Fred Draked86ed291999-12-15 15:34:33 +000014247#endif
Fred Drakec9680921999-12-13 16:37:25 +000014248#ifdef _CS_PATH
Victor Stinner8c62be82010-05-06 00:08:46 +000014249 {"CS_PATH", _CS_PATH},
Fred Drakec9680921999-12-13 16:37:25 +000014250#endif
Fred Draked86ed291999-12-15 15:34:33 +000014251#ifdef _CS_RELEASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014252 {"CS_RELEASE", _CS_RELEASE},
Fred Draked86ed291999-12-15 15:34:33 +000014253#endif
14254#ifdef _CS_SRPC_DOMAIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014255 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
Fred Draked86ed291999-12-15 15:34:33 +000014256#endif
14257#ifdef _CS_SYSNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014258 {"CS_SYSNAME", _CS_SYSNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014259#endif
14260#ifdef _CS_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014261 {"CS_VERSION", _CS_VERSION},
Fred Draked86ed291999-12-15 15:34:33 +000014262#endif
Fred Drakec9680921999-12-13 16:37:25 +000014263#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014264 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014265#endif
14266#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014267 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014268#endif
14269#ifdef _CS_XBS5_ILP32_OFF32_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014270 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014271#endif
14272#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014273 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014274#endif
14275#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014276 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014277#endif
14278#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014279 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014280#endif
14281#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014282 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014283#endif
14284#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014285 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014286#endif
14287#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014288 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014289#endif
14290#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014291 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014292#endif
14293#ifdef _CS_XBS5_LP64_OFF64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014294 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014295#endif
14296#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014297 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014298#endif
14299#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014300 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014301#endif
14302#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014303 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014304#endif
14305#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014306 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014307#endif
14308#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014309 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014310#endif
Fred Draked86ed291999-12-15 15:34:33 +000014311#ifdef _MIPS_CS_AVAIL_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014312 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014313#endif
14314#ifdef _MIPS_CS_BASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014315 {"MIPS_CS_BASE", _MIPS_CS_BASE},
Fred Draked86ed291999-12-15 15:34:33 +000014316#endif
14317#ifdef _MIPS_CS_HOSTID
Victor Stinner8c62be82010-05-06 00:08:46 +000014318 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
Fred Draked86ed291999-12-15 15:34:33 +000014319#endif
14320#ifdef _MIPS_CS_HW_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014321 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014322#endif
14323#ifdef _MIPS_CS_NUM_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014324 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014325#endif
14326#ifdef _MIPS_CS_OSREL_MAJ
Victor Stinner8c62be82010-05-06 00:08:46 +000014327 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
Fred Draked86ed291999-12-15 15:34:33 +000014328#endif
14329#ifdef _MIPS_CS_OSREL_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014330 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
Fred Draked86ed291999-12-15 15:34:33 +000014331#endif
14332#ifdef _MIPS_CS_OSREL_PATCH
Victor Stinner8c62be82010-05-06 00:08:46 +000014333 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
Fred Draked86ed291999-12-15 15:34:33 +000014334#endif
14335#ifdef _MIPS_CS_OS_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014336 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014337#endif
14338#ifdef _MIPS_CS_OS_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014339 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014340#endif
14341#ifdef _MIPS_CS_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014342 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014343#endif
14344#ifdef _MIPS_CS_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014345 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014346#endif
14347#ifdef _MIPS_CS_VENDOR
Victor Stinner8c62be82010-05-06 00:08:46 +000014348 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
Fred Draked86ed291999-12-15 15:34:33 +000014349#endif
Fred Drakec9680921999-12-13 16:37:25 +000014350};
14351
14352static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014353conv_confstr_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014354{
14355 return conv_confname(arg, valuep, posix_constants_confstr,
14356 sizeof(posix_constants_confstr)
14357 / sizeof(struct constdef));
14358}
14359
Larry Hastings2f936352014-08-05 14:04:04 +100014360
14361/*[clinic input]
14362os.confstr
14363
14364 name: confstr_confname
14365 /
14366
14367Return a string-valued system configuration variable.
14368[clinic start generated code]*/
14369
14370PyDoc_STRVAR(os_confstr__doc__,
14371"confstr($module, name, /)\n"
14372"--\n"
14373"\n"
14374"Return a string-valued system configuration variable.");
14375
14376#define OS_CONFSTR_METHODDEF \
14377 {"confstr", (PyCFunction)os_confstr, METH_VARARGS, os_confstr__doc__},
Fred Drakec9680921999-12-13 16:37:25 +000014378
14379static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014380os_confstr_impl(PyModuleDef *module, int name);
14381
14382static PyObject *
14383os_confstr(PyModuleDef *module, PyObject *args)
14384{
14385 PyObject *return_value = NULL;
14386 int name;
14387
14388 if (!PyArg_ParseTuple(args,
14389 "O&:confstr",
14390 conv_confstr_confname, &name))
14391 goto exit;
14392 return_value = os_confstr_impl(module, name);
14393
14394exit:
14395 return return_value;
14396}
14397
14398static PyObject *
14399os_confstr_impl(PyModuleDef *module, int name)
14400/*[clinic end generated code: output=3f5e8aba9f8e3174 input=18fb4d0567242e65]*/
Fred Drakec9680921999-12-13 16:37:25 +000014401{
14402 PyObject *result = NULL;
Victor Stinnercb043522010-09-10 23:49:04 +000014403 char buffer[255];
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014404 size_t len;
Fred Drakec9680921999-12-13 16:37:25 +000014405
Victor Stinnercb043522010-09-10 23:49:04 +000014406 errno = 0;
14407 len = confstr(name, buffer, sizeof(buffer));
14408 if (len == 0) {
14409 if (errno) {
14410 posix_error();
14411 return NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014412 }
14413 else {
Victor Stinnercb043522010-09-10 23:49:04 +000014414 Py_RETURN_NONE;
Fred Drakec9680921999-12-13 16:37:25 +000014415 }
14416 }
Victor Stinnercb043522010-09-10 23:49:04 +000014417
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014418 if (len >= sizeof(buffer)) {
Victor Stinnercbc18f32014-12-05 22:51:51 +010014419 size_t len2;
Victor Stinnercb043522010-09-10 23:49:04 +000014420 char *buf = PyMem_Malloc(len);
14421 if (buf == NULL)
14422 return PyErr_NoMemory();
Victor Stinnercbc18f32014-12-05 22:51:51 +010014423 len2 = confstr(name, buf, len);
14424 assert(len == len2);
Victor Stinnercb043522010-09-10 23:49:04 +000014425 result = PyUnicode_DecodeFSDefaultAndSize(buf, len-1);
14426 PyMem_Free(buf);
14427 }
14428 else
14429 result = PyUnicode_DecodeFSDefaultAndSize(buffer, len-1);
Fred Drakec9680921999-12-13 16:37:25 +000014430 return result;
14431}
Larry Hastings2f936352014-08-05 14:04:04 +100014432#endif /* HAVE_CONFSTR */
Fred Drakec9680921999-12-13 16:37:25 +000014433
14434
14435#ifdef HAVE_SYSCONF
14436static struct constdef posix_constants_sysconf[] = {
14437#ifdef _SC_2_CHAR_TERM
Victor Stinner8c62be82010-05-06 00:08:46 +000014438 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
Fred Drakec9680921999-12-13 16:37:25 +000014439#endif
14440#ifdef _SC_2_C_BIND
Victor Stinner8c62be82010-05-06 00:08:46 +000014441 {"SC_2_C_BIND", _SC_2_C_BIND},
Fred Drakec9680921999-12-13 16:37:25 +000014442#endif
14443#ifdef _SC_2_C_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014444 {"SC_2_C_DEV", _SC_2_C_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014445#endif
14446#ifdef _SC_2_C_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014447 {"SC_2_C_VERSION", _SC_2_C_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014448#endif
14449#ifdef _SC_2_FORT_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014450 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014451#endif
14452#ifdef _SC_2_FORT_RUN
Victor Stinner8c62be82010-05-06 00:08:46 +000014453 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
Fred Drakec9680921999-12-13 16:37:25 +000014454#endif
14455#ifdef _SC_2_LOCALEDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000014456 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
Fred Drakec9680921999-12-13 16:37:25 +000014457#endif
14458#ifdef _SC_2_SW_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014459 {"SC_2_SW_DEV", _SC_2_SW_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014460#endif
14461#ifdef _SC_2_UPE
Victor Stinner8c62be82010-05-06 00:08:46 +000014462 {"SC_2_UPE", _SC_2_UPE},
Fred Drakec9680921999-12-13 16:37:25 +000014463#endif
14464#ifdef _SC_2_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014465 {"SC_2_VERSION", _SC_2_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014466#endif
Fred Draked86ed291999-12-15 15:34:33 +000014467#ifdef _SC_ABI_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014468 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
Fred Draked86ed291999-12-15 15:34:33 +000014469#endif
14470#ifdef _SC_ACL
Victor Stinner8c62be82010-05-06 00:08:46 +000014471 {"SC_ACL", _SC_ACL},
Fred Draked86ed291999-12-15 15:34:33 +000014472#endif
Fred Drakec9680921999-12-13 16:37:25 +000014473#ifdef _SC_AIO_LISTIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014474 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014475#endif
Fred Drakec9680921999-12-13 16:37:25 +000014476#ifdef _SC_AIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014477 {"SC_AIO_MAX", _SC_AIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014478#endif
14479#ifdef _SC_AIO_PRIO_DELTA_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014480 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014481#endif
14482#ifdef _SC_ARG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014483 {"SC_ARG_MAX", _SC_ARG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014484#endif
14485#ifdef _SC_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014486 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014487#endif
14488#ifdef _SC_ATEXIT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014489 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014490#endif
Fred Draked86ed291999-12-15 15:34:33 +000014491#ifdef _SC_AUDIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014492 {"SC_AUDIT", _SC_AUDIT},
Fred Draked86ed291999-12-15 15:34:33 +000014493#endif
Fred Drakec9680921999-12-13 16:37:25 +000014494#ifdef _SC_AVPHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014495 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014496#endif
14497#ifdef _SC_BC_BASE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014498 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014499#endif
14500#ifdef _SC_BC_DIM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014501 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014502#endif
14503#ifdef _SC_BC_SCALE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014504 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014505#endif
14506#ifdef _SC_BC_STRING_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014507 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014508#endif
Fred Draked86ed291999-12-15 15:34:33 +000014509#ifdef _SC_CAP
Victor Stinner8c62be82010-05-06 00:08:46 +000014510 {"SC_CAP", _SC_CAP},
Fred Draked86ed291999-12-15 15:34:33 +000014511#endif
Fred Drakec9680921999-12-13 16:37:25 +000014512#ifdef _SC_CHARCLASS_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014513 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014514#endif
14515#ifdef _SC_CHAR_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014516 {"SC_CHAR_BIT", _SC_CHAR_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014517#endif
14518#ifdef _SC_CHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014519 {"SC_CHAR_MAX", _SC_CHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014520#endif
14521#ifdef _SC_CHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014522 {"SC_CHAR_MIN", _SC_CHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014523#endif
14524#ifdef _SC_CHILD_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014525 {"SC_CHILD_MAX", _SC_CHILD_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014526#endif
14527#ifdef _SC_CLK_TCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014528 {"SC_CLK_TCK", _SC_CLK_TCK},
Fred Drakec9680921999-12-13 16:37:25 +000014529#endif
14530#ifdef _SC_COHER_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014531 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014532#endif
14533#ifdef _SC_COLL_WEIGHTS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014534 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014535#endif
14536#ifdef _SC_DCACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014537 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014538#endif
14539#ifdef _SC_DCACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014540 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014541#endif
14542#ifdef _SC_DCACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014543 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014544#endif
14545#ifdef _SC_DCACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014546 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014547#endif
14548#ifdef _SC_DCACHE_TBLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014549 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014550#endif
14551#ifdef _SC_DELAYTIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014552 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014553#endif
14554#ifdef _SC_EQUIV_CLASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014555 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014556#endif
14557#ifdef _SC_EXPR_NEST_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014558 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014559#endif
14560#ifdef _SC_FSYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000014561 {"SC_FSYNC", _SC_FSYNC},
Fred Drakec9680921999-12-13 16:37:25 +000014562#endif
14563#ifdef _SC_GETGR_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014564 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014565#endif
14566#ifdef _SC_GETPW_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014567 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014568#endif
14569#ifdef _SC_ICACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014570 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014571#endif
14572#ifdef _SC_ICACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014573 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014574#endif
14575#ifdef _SC_ICACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014576 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014577#endif
14578#ifdef _SC_ICACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014579 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014580#endif
Fred Draked86ed291999-12-15 15:34:33 +000014581#ifdef _SC_INF
Victor Stinner8c62be82010-05-06 00:08:46 +000014582 {"SC_INF", _SC_INF},
Fred Draked86ed291999-12-15 15:34:33 +000014583#endif
Fred Drakec9680921999-12-13 16:37:25 +000014584#ifdef _SC_INT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014585 {"SC_INT_MAX", _SC_INT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014586#endif
14587#ifdef _SC_INT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014588 {"SC_INT_MIN", _SC_INT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014589#endif
14590#ifdef _SC_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014591 {"SC_IOV_MAX", _SC_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014592#endif
Fred Draked86ed291999-12-15 15:34:33 +000014593#ifdef _SC_IP_SECOPTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014594 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
Fred Draked86ed291999-12-15 15:34:33 +000014595#endif
Fred Drakec9680921999-12-13 16:37:25 +000014596#ifdef _SC_JOB_CONTROL
Victor Stinner8c62be82010-05-06 00:08:46 +000014597 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
Fred Drakec9680921999-12-13 16:37:25 +000014598#endif
Fred Draked86ed291999-12-15 15:34:33 +000014599#ifdef _SC_KERN_POINTERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014600 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
Fred Draked86ed291999-12-15 15:34:33 +000014601#endif
14602#ifdef _SC_KERN_SIM
Victor Stinner8c62be82010-05-06 00:08:46 +000014603 {"SC_KERN_SIM", _SC_KERN_SIM},
Fred Draked86ed291999-12-15 15:34:33 +000014604#endif
Fred Drakec9680921999-12-13 16:37:25 +000014605#ifdef _SC_LINE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014606 {"SC_LINE_MAX", _SC_LINE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014607#endif
14608#ifdef _SC_LOGIN_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014609 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014610#endif
14611#ifdef _SC_LOGNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014612 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014613#endif
14614#ifdef _SC_LONG_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014615 {"SC_LONG_BIT", _SC_LONG_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014616#endif
Fred Draked86ed291999-12-15 15:34:33 +000014617#ifdef _SC_MAC
Victor Stinner8c62be82010-05-06 00:08:46 +000014618 {"SC_MAC", _SC_MAC},
Fred Draked86ed291999-12-15 15:34:33 +000014619#endif
Fred Drakec9680921999-12-13 16:37:25 +000014620#ifdef _SC_MAPPED_FILES
Victor Stinner8c62be82010-05-06 00:08:46 +000014621 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
Fred Drakec9680921999-12-13 16:37:25 +000014622#endif
14623#ifdef _SC_MAXPID
Victor Stinner8c62be82010-05-06 00:08:46 +000014624 {"SC_MAXPID", _SC_MAXPID},
Fred Drakec9680921999-12-13 16:37:25 +000014625#endif
14626#ifdef _SC_MB_LEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014627 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014628#endif
14629#ifdef _SC_MEMLOCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014630 {"SC_MEMLOCK", _SC_MEMLOCK},
Fred Drakec9680921999-12-13 16:37:25 +000014631#endif
14632#ifdef _SC_MEMLOCK_RANGE
Victor Stinner8c62be82010-05-06 00:08:46 +000014633 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
Fred Drakec9680921999-12-13 16:37:25 +000014634#endif
14635#ifdef _SC_MEMORY_PROTECTION
Victor Stinner8c62be82010-05-06 00:08:46 +000014636 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
Fred Drakec9680921999-12-13 16:37:25 +000014637#endif
14638#ifdef _SC_MESSAGE_PASSING
Victor Stinner8c62be82010-05-06 00:08:46 +000014639 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
Fred Drakec9680921999-12-13 16:37:25 +000014640#endif
Fred Draked86ed291999-12-15 15:34:33 +000014641#ifdef _SC_MMAP_FIXED_ALIGNMENT
Victor Stinner8c62be82010-05-06 00:08:46 +000014642 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
Fred Draked86ed291999-12-15 15:34:33 +000014643#endif
Fred Drakec9680921999-12-13 16:37:25 +000014644#ifdef _SC_MQ_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014645 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014646#endif
14647#ifdef _SC_MQ_PRIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014648 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014649#endif
Fred Draked86ed291999-12-15 15:34:33 +000014650#ifdef _SC_NACLS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014651 {"SC_NACLS_MAX", _SC_NACLS_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000014652#endif
Fred Drakec9680921999-12-13 16:37:25 +000014653#ifdef _SC_NGROUPS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014654 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014655#endif
14656#ifdef _SC_NL_ARGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014657 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014658#endif
14659#ifdef _SC_NL_LANGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014660 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014661#endif
14662#ifdef _SC_NL_MSGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014663 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014664#endif
14665#ifdef _SC_NL_NMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014666 {"SC_NL_NMAX", _SC_NL_NMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014667#endif
14668#ifdef _SC_NL_SETMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014669 {"SC_NL_SETMAX", _SC_NL_SETMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014670#endif
14671#ifdef _SC_NL_TEXTMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014672 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014673#endif
14674#ifdef _SC_NPROCESSORS_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014675 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
Fred Drakec9680921999-12-13 16:37:25 +000014676#endif
14677#ifdef _SC_NPROCESSORS_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014678 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
Fred Drakec9680921999-12-13 16:37:25 +000014679#endif
Fred Draked86ed291999-12-15 15:34:33 +000014680#ifdef _SC_NPROC_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014681 {"SC_NPROC_CONF", _SC_NPROC_CONF},
Fred Draked86ed291999-12-15 15:34:33 +000014682#endif
14683#ifdef _SC_NPROC_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014684 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
Fred Draked86ed291999-12-15 15:34:33 +000014685#endif
Fred Drakec9680921999-12-13 16:37:25 +000014686#ifdef _SC_NZERO
Victor Stinner8c62be82010-05-06 00:08:46 +000014687 {"SC_NZERO", _SC_NZERO},
Fred Drakec9680921999-12-13 16:37:25 +000014688#endif
14689#ifdef _SC_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014690 {"SC_OPEN_MAX", _SC_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014691#endif
14692#ifdef _SC_PAGESIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014693 {"SC_PAGESIZE", _SC_PAGESIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014694#endif
14695#ifdef _SC_PAGE_SIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014696 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014697#endif
14698#ifdef _SC_PASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014699 {"SC_PASS_MAX", _SC_PASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014700#endif
14701#ifdef _SC_PHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014702 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014703#endif
14704#ifdef _SC_PII
Victor Stinner8c62be82010-05-06 00:08:46 +000014705 {"SC_PII", _SC_PII},
Fred Drakec9680921999-12-13 16:37:25 +000014706#endif
14707#ifdef _SC_PII_INTERNET
Victor Stinner8c62be82010-05-06 00:08:46 +000014708 {"SC_PII_INTERNET", _SC_PII_INTERNET},
Fred Drakec9680921999-12-13 16:37:25 +000014709#endif
14710#ifdef _SC_PII_INTERNET_DGRAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014711 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
Fred Drakec9680921999-12-13 16:37:25 +000014712#endif
14713#ifdef _SC_PII_INTERNET_STREAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014714 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
Fred Drakec9680921999-12-13 16:37:25 +000014715#endif
14716#ifdef _SC_PII_OSI
Victor Stinner8c62be82010-05-06 00:08:46 +000014717 {"SC_PII_OSI", _SC_PII_OSI},
Fred Drakec9680921999-12-13 16:37:25 +000014718#endif
14719#ifdef _SC_PII_OSI_CLTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014720 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
Fred Drakec9680921999-12-13 16:37:25 +000014721#endif
14722#ifdef _SC_PII_OSI_COTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014723 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
Fred Drakec9680921999-12-13 16:37:25 +000014724#endif
14725#ifdef _SC_PII_OSI_M
Victor Stinner8c62be82010-05-06 00:08:46 +000014726 {"SC_PII_OSI_M", _SC_PII_OSI_M},
Fred Drakec9680921999-12-13 16:37:25 +000014727#endif
14728#ifdef _SC_PII_SOCKET
Victor Stinner8c62be82010-05-06 00:08:46 +000014729 {"SC_PII_SOCKET", _SC_PII_SOCKET},
Fred Drakec9680921999-12-13 16:37:25 +000014730#endif
14731#ifdef _SC_PII_XTI
Victor Stinner8c62be82010-05-06 00:08:46 +000014732 {"SC_PII_XTI", _SC_PII_XTI},
Fred Drakec9680921999-12-13 16:37:25 +000014733#endif
14734#ifdef _SC_POLL
Victor Stinner8c62be82010-05-06 00:08:46 +000014735 {"SC_POLL", _SC_POLL},
Fred Drakec9680921999-12-13 16:37:25 +000014736#endif
14737#ifdef _SC_PRIORITIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014738 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014739#endif
14740#ifdef _SC_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014741 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014742#endif
14743#ifdef _SC_REALTIME_SIGNALS
Victor Stinner8c62be82010-05-06 00:08:46 +000014744 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
Fred Drakec9680921999-12-13 16:37:25 +000014745#endif
14746#ifdef _SC_RE_DUP_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014747 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014748#endif
14749#ifdef _SC_RTSIG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014750 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014751#endif
14752#ifdef _SC_SAVED_IDS
Victor Stinner8c62be82010-05-06 00:08:46 +000014753 {"SC_SAVED_IDS", _SC_SAVED_IDS},
Fred Drakec9680921999-12-13 16:37:25 +000014754#endif
14755#ifdef _SC_SCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014756 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014757#endif
14758#ifdef _SC_SCHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014759 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014760#endif
14761#ifdef _SC_SELECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014762 {"SC_SELECT", _SC_SELECT},
Fred Drakec9680921999-12-13 16:37:25 +000014763#endif
14764#ifdef _SC_SEMAPHORES
Victor Stinner8c62be82010-05-06 00:08:46 +000014765 {"SC_SEMAPHORES", _SC_SEMAPHORES},
Fred Drakec9680921999-12-13 16:37:25 +000014766#endif
14767#ifdef _SC_SEM_NSEMS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014768 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014769#endif
14770#ifdef _SC_SEM_VALUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014771 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014772#endif
14773#ifdef _SC_SHARED_MEMORY_OBJECTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014774 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
Fred Drakec9680921999-12-13 16:37:25 +000014775#endif
14776#ifdef _SC_SHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014777 {"SC_SHRT_MAX", _SC_SHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014778#endif
14779#ifdef _SC_SHRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014780 {"SC_SHRT_MIN", _SC_SHRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014781#endif
14782#ifdef _SC_SIGQUEUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014783 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014784#endif
14785#ifdef _SC_SIGRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014786 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014787#endif
14788#ifdef _SC_SIGRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014789 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014790#endif
Fred Draked86ed291999-12-15 15:34:33 +000014791#ifdef _SC_SOFTPOWER
Victor Stinner8c62be82010-05-06 00:08:46 +000014792 {"SC_SOFTPOWER", _SC_SOFTPOWER},
Fred Draked86ed291999-12-15 15:34:33 +000014793#endif
Fred Drakec9680921999-12-13 16:37:25 +000014794#ifdef _SC_SPLIT_CACHE
Victor Stinner8c62be82010-05-06 00:08:46 +000014795 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
Fred Drakec9680921999-12-13 16:37:25 +000014796#endif
14797#ifdef _SC_SSIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014798 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014799#endif
14800#ifdef _SC_STACK_PROT
Victor Stinner8c62be82010-05-06 00:08:46 +000014801 {"SC_STACK_PROT", _SC_STACK_PROT},
Fred Drakec9680921999-12-13 16:37:25 +000014802#endif
14803#ifdef _SC_STREAM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014804 {"SC_STREAM_MAX", _SC_STREAM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014805#endif
14806#ifdef _SC_SYNCHRONIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014807 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014808#endif
14809#ifdef _SC_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014810 {"SC_THREADS", _SC_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014811#endif
14812#ifdef _SC_THREAD_ATTR_STACKADDR
Victor Stinner8c62be82010-05-06 00:08:46 +000014813 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
Fred Drakec9680921999-12-13 16:37:25 +000014814#endif
14815#ifdef _SC_THREAD_ATTR_STACKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014816 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014817#endif
14818#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014819 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014820#endif
14821#ifdef _SC_THREAD_KEYS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014822 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014823#endif
14824#ifdef _SC_THREAD_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014825 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014826#endif
14827#ifdef _SC_THREAD_PRIO_INHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014828 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
Fred Drakec9680921999-12-13 16:37:25 +000014829#endif
14830#ifdef _SC_THREAD_PRIO_PROTECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014831 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
Fred Drakec9680921999-12-13 16:37:25 +000014832#endif
14833#ifdef _SC_THREAD_PROCESS_SHARED
Victor Stinner8c62be82010-05-06 00:08:46 +000014834 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
Fred Drakec9680921999-12-13 16:37:25 +000014835#endif
14836#ifdef _SC_THREAD_SAFE_FUNCTIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014837 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014838#endif
14839#ifdef _SC_THREAD_STACK_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014840 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014841#endif
14842#ifdef _SC_THREAD_THREADS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014843 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014844#endif
14845#ifdef _SC_TIMERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014846 {"SC_TIMERS", _SC_TIMERS},
Fred Drakec9680921999-12-13 16:37:25 +000014847#endif
14848#ifdef _SC_TIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014849 {"SC_TIMER_MAX", _SC_TIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014850#endif
14851#ifdef _SC_TTY_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014852 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014853#endif
14854#ifdef _SC_TZNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014855 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014856#endif
14857#ifdef _SC_T_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014858 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014859#endif
14860#ifdef _SC_UCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014861 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014862#endif
14863#ifdef _SC_UINT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014864 {"SC_UINT_MAX", _SC_UINT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014865#endif
14866#ifdef _SC_UIO_MAXIOV
Victor Stinner8c62be82010-05-06 00:08:46 +000014867 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
Fred Drakec9680921999-12-13 16:37:25 +000014868#endif
14869#ifdef _SC_ULONG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014870 {"SC_ULONG_MAX", _SC_ULONG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014871#endif
14872#ifdef _SC_USHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014873 {"SC_USHRT_MAX", _SC_USHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014874#endif
14875#ifdef _SC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014876 {"SC_VERSION", _SC_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014877#endif
14878#ifdef _SC_WORD_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014879 {"SC_WORD_BIT", _SC_WORD_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014880#endif
14881#ifdef _SC_XBS5_ILP32_OFF32
Victor Stinner8c62be82010-05-06 00:08:46 +000014882 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
Fred Drakec9680921999-12-13 16:37:25 +000014883#endif
14884#ifdef _SC_XBS5_ILP32_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014885 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014886#endif
14887#ifdef _SC_XBS5_LP64_OFF64
Victor Stinner8c62be82010-05-06 00:08:46 +000014888 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
Fred Drakec9680921999-12-13 16:37:25 +000014889#endif
14890#ifdef _SC_XBS5_LPBIG_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014891 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014892#endif
14893#ifdef _SC_XOPEN_CRYPT
Victor Stinner8c62be82010-05-06 00:08:46 +000014894 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
Fred Drakec9680921999-12-13 16:37:25 +000014895#endif
14896#ifdef _SC_XOPEN_ENH_I18N
Victor Stinner8c62be82010-05-06 00:08:46 +000014897 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
Fred Drakec9680921999-12-13 16:37:25 +000014898#endif
14899#ifdef _SC_XOPEN_LEGACY
Victor Stinner8c62be82010-05-06 00:08:46 +000014900 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
Fred Drakec9680921999-12-13 16:37:25 +000014901#endif
14902#ifdef _SC_XOPEN_REALTIME
Victor Stinner8c62be82010-05-06 00:08:46 +000014903 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
Fred Drakec9680921999-12-13 16:37:25 +000014904#endif
14905#ifdef _SC_XOPEN_REALTIME_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014906 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014907#endif
14908#ifdef _SC_XOPEN_SHM
Victor Stinner8c62be82010-05-06 00:08:46 +000014909 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
Fred Drakec9680921999-12-13 16:37:25 +000014910#endif
14911#ifdef _SC_XOPEN_UNIX
Victor Stinner8c62be82010-05-06 00:08:46 +000014912 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
Fred Drakec9680921999-12-13 16:37:25 +000014913#endif
14914#ifdef _SC_XOPEN_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014915 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014916#endif
14917#ifdef _SC_XOPEN_XCU_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014918 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014919#endif
14920#ifdef _SC_XOPEN_XPG2
Victor Stinner8c62be82010-05-06 00:08:46 +000014921 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
Fred Drakec9680921999-12-13 16:37:25 +000014922#endif
14923#ifdef _SC_XOPEN_XPG3
Victor Stinner8c62be82010-05-06 00:08:46 +000014924 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
Fred Drakec9680921999-12-13 16:37:25 +000014925#endif
14926#ifdef _SC_XOPEN_XPG4
Victor Stinner8c62be82010-05-06 00:08:46 +000014927 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
Fred Drakec9680921999-12-13 16:37:25 +000014928#endif
14929};
14930
14931static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014932conv_sysconf_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014933{
14934 return conv_confname(arg, valuep, posix_constants_sysconf,
14935 sizeof(posix_constants_sysconf)
14936 / sizeof(struct constdef));
14937}
14938
Larry Hastings2f936352014-08-05 14:04:04 +100014939
14940/*[clinic input]
14941os.sysconf -> long
14942 name: sysconf_confname
14943 /
14944
14945Return an integer-valued system configuration variable.
14946[clinic start generated code]*/
14947
14948PyDoc_STRVAR(os_sysconf__doc__,
14949"sysconf($module, name, /)\n"
14950"--\n"
14951"\n"
14952"Return an integer-valued system configuration variable.");
14953
14954#define OS_SYSCONF_METHODDEF \
14955 {"sysconf", (PyCFunction)os_sysconf, METH_VARARGS, os_sysconf__doc__},
14956
14957static long
14958os_sysconf_impl(PyModuleDef *module, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014959
14960static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014961os_sysconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014962{
Larry Hastings2f936352014-08-05 14:04:04 +100014963 PyObject *return_value = NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014964 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014965 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014966
Larry Hastings2f936352014-08-05 14:04:04 +100014967 if (!PyArg_ParseTuple(args,
14968 "O&:sysconf",
14969 conv_sysconf_confname, &name))
14970 goto exit;
14971 _return_value = os_sysconf_impl(module, name);
14972 if ((_return_value == -1) && PyErr_Occurred())
14973 goto exit;
14974 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014975
Larry Hastings2f936352014-08-05 14:04:04 +100014976exit:
14977 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014978}
Larry Hastings2f936352014-08-05 14:04:04 +100014979
14980static long
14981os_sysconf_impl(PyModuleDef *module, int name)
14982/*[clinic end generated code: output=7b06dfdc472431e4 input=279e3430a33f29e4]*/
14983{
14984 long value;
14985
14986 errno = 0;
14987 value = sysconf(name);
14988 if (value == -1 && errno != 0)
14989 posix_error();
14990 return value;
14991}
14992#endif /* HAVE_SYSCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014993
14994
Fred Drakebec628d1999-12-15 18:31:10 +000014995/* This code is used to ensure that the tables of configuration value names
Serhiy Storchaka56a6d852014-12-01 18:28:43 +020014996 * are in sorted order as required by conv_confname(), and also to build
Fred Drakebec628d1999-12-15 18:31:10 +000014997 * the exported dictionaries that are used to publish information about the
14998 * names available on the host platform.
14999 *
15000 * Sorting the table at runtime ensures that the table is properly ordered
15001 * when used, even for platforms we're not able to test on. It also makes
15002 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +000015003 */
Fred Drakebec628d1999-12-15 18:31:10 +000015004
15005static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000015006cmp_constdefs(const void *v1, const void *v2)
Fred Drakebec628d1999-12-15 18:31:10 +000015007{
15008 const struct constdef *c1 =
Victor Stinner8c62be82010-05-06 00:08:46 +000015009 (const struct constdef *) v1;
Fred Drakebec628d1999-12-15 18:31:10 +000015010 const struct constdef *c2 =
Victor Stinner8c62be82010-05-06 00:08:46 +000015011 (const struct constdef *) v2;
Fred Drakebec628d1999-12-15 18:31:10 +000015012
15013 return strcmp(c1->name, c2->name);
15014}
15015
15016static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000015017setup_confname_table(struct constdef *table, size_t tablesize,
Victor Stinner8c62be82010-05-06 00:08:46 +000015018 char *tablename, PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000015019{
Fred Drakebec628d1999-12-15 18:31:10 +000015020 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +000015021 size_t i;
Fred Drakebec628d1999-12-15 18:31:10 +000015022
15023 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
15024 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +000015025 if (d == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +000015026 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015027
Barry Warsaw3155db32000-04-13 15:20:40 +000015028 for (i=0; i < tablesize; ++i) {
Victor Stinner8c62be82010-05-06 00:08:46 +000015029 PyObject *o = PyLong_FromLong(table[i].value);
15030 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
15031 Py_XDECREF(o);
15032 Py_DECREF(d);
15033 return -1;
15034 }
15035 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +000015036 }
Fred Drake4d1e64b2002-04-15 19:40:07 +000015037 return PyModule_AddObject(module, tablename, d);
Fred Draked86ed291999-12-15 15:34:33 +000015038}
15039
Fred Drakebec628d1999-12-15 18:31:10 +000015040/* Return -1 on failure, 0 on success. */
15041static int
Fred Drake4d1e64b2002-04-15 19:40:07 +000015042setup_confname_tables(PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000015043{
15044#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +000015045 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +000015046 sizeof(posix_constants_pathconf)
15047 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015048 "pathconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015049 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015050#endif
15051#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +000015052 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +000015053 sizeof(posix_constants_confstr)
15054 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015055 "confstr_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015056 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015057#endif
15058#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +000015059 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +000015060 sizeof(posix_constants_sysconf)
15061 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015062 "sysconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015063 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015064#endif
Fred Drakebec628d1999-12-15 18:31:10 +000015065 return 0;
Fred Draked86ed291999-12-15 15:34:33 +000015066}
Fred Draked86ed291999-12-15 15:34:33 +000015067
15068
Larry Hastings2f936352014-08-05 14:04:04 +100015069/*[clinic input]
15070os.abort
15071
15072Abort the interpreter immediately.
15073
15074This function 'dumps core' or otherwise fails in the hardest way possible
15075on the hosting operating system. This function never returns.
15076[clinic start generated code]*/
15077
15078PyDoc_STRVAR(os_abort__doc__,
15079"abort($module, /)\n"
15080"--\n"
15081"\n"
15082"Abort the interpreter immediately.\n"
15083"\n"
15084"This function \'dumps core\' or otherwise fails in the hardest way possible\n"
15085"on the hosting operating system. This function never returns.");
15086
15087#define OS_ABORT_METHODDEF \
15088 {"abort", (PyCFunction)os_abort, METH_NOARGS, os_abort__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015089
15090static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015091os_abort_impl(PyModuleDef *module);
15092
15093static PyObject *
15094os_abort(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15095{
15096 return os_abort_impl(module);
15097}
15098
15099static PyObject *
15100os_abort_impl(PyModuleDef *module)
15101/*[clinic end generated code: output=cded2cc8c5453d3a input=cf2c7d98bc504047]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015102{
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015103 abort();
15104 /*NOTREACHED*/
15105 Py_FatalError("abort() called from Python code didn't abort!");
15106 return NULL;
15107}
Fred Drakebec628d1999-12-15 18:31:10 +000015108
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000015109#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100015110/* AC 3.5: change to path_t? but that might change exceptions */
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015111PyDoc_STRVAR(win32_startfile__doc__,
Larry Hastings2f936352014-08-05 14:04:04 +100015112"startfile(filepath [, operation])\n\
15113\n\
15114Start a file with its associated application.\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015115\n\
Georg Brandlf4f44152006-02-18 22:29:33 +000015116When \"operation\" is not specified or \"open\", this acts like\n\
15117double-clicking the file in Explorer, or giving the file name as an\n\
15118argument to the DOS \"start\" command: the file is opened with whatever\n\
15119application (if any) its extension is associated.\n\
15120When another \"operation\" is given, it specifies what should be done with\n\
15121the file. A typical operation is \"print\".\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015122\n\
15123startfile returns as soon as the associated application is launched.\n\
15124There is no option to wait for the application to close, and no way\n\
15125to retrieve the application's exit status.\n\
15126\n\
15127The filepath is relative to the current directory. If you want to use\n\
15128an absolute path, make sure the first character is not a slash (\"/\");\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015129the underlying Win32 ShellExecute function doesn't work if it is.");
Tim Petersf58a7aa2000-09-22 10:05:54 +000015130
15131static PyObject *
15132win32_startfile(PyObject *self, PyObject *args)
15133{
Victor Stinner8c62be82010-05-06 00:08:46 +000015134 PyObject *ofilepath;
15135 char *filepath;
15136 char *operation = NULL;
Victor Stinnereb5657a2011-09-30 01:44:27 +020015137 wchar_t *wpath, *woperation;
Victor Stinner8c62be82010-05-06 00:08:46 +000015138 HINSTANCE rc;
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +000015139
Victor Stinnereb5657a2011-09-30 01:44:27 +020015140 PyObject *unipath, *uoperation = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015141 if (!PyArg_ParseTuple(args, "U|s:startfile",
15142 &unipath, &operation)) {
15143 PyErr_Clear();
15144 goto normal;
15145 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015146
Victor Stinner8c62be82010-05-06 00:08:46 +000015147 if (operation) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015148 uoperation = PyUnicode_DecodeASCII(operation,
Victor Stinner8c62be82010-05-06 00:08:46 +000015149 strlen(operation), NULL);
Victor Stinnereb5657a2011-09-30 01:44:27 +020015150 if (!uoperation) {
Victor Stinner8c62be82010-05-06 00:08:46 +000015151 PyErr_Clear();
15152 operation = NULL;
15153 goto normal;
15154 }
15155 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015156
Victor Stinnereb5657a2011-09-30 01:44:27 +020015157 wpath = PyUnicode_AsUnicode(unipath);
15158 if (wpath == NULL)
15159 goto normal;
15160 if (uoperation) {
15161 woperation = PyUnicode_AsUnicode(uoperation);
15162 if (woperation == NULL)
15163 goto normal;
15164 }
15165 else
15166 woperation = NULL;
15167
Victor Stinner8c62be82010-05-06 00:08:46 +000015168 Py_BEGIN_ALLOW_THREADS
Victor Stinnereb5657a2011-09-30 01:44:27 +020015169 rc = ShellExecuteW((HWND)0, woperation, wpath,
15170 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000015171 Py_END_ALLOW_THREADS
15172
Victor Stinnereb5657a2011-09-30 01:44:27 +020015173 Py_XDECREF(uoperation);
Victor Stinner8c62be82010-05-06 00:08:46 +000015174 if (rc <= (HINSTANCE)32) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015175 win32_error_object("startfile", unipath);
15176 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015177 }
15178 Py_INCREF(Py_None);
15179 return Py_None;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000015180
15181normal:
Victor Stinner8c62be82010-05-06 00:08:46 +000015182 if (!PyArg_ParseTuple(args, "O&|s:startfile",
15183 PyUnicode_FSConverter, &ofilepath,
15184 &operation))
15185 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +010015186 if (win32_warn_bytes_api()) {
15187 Py_DECREF(ofilepath);
15188 return NULL;
15189 }
Victor Stinner8c62be82010-05-06 00:08:46 +000015190 filepath = PyBytes_AsString(ofilepath);
15191 Py_BEGIN_ALLOW_THREADS
15192 rc = ShellExecute((HWND)0, operation, filepath,
15193 NULL, NULL, SW_SHOWNORMAL);
15194 Py_END_ALLOW_THREADS
15195 if (rc <= (HINSTANCE)32) {
15196 PyObject *errval = win32_error("startfile", filepath);
15197 Py_DECREF(ofilepath);
15198 return errval;
15199 }
15200 Py_DECREF(ofilepath);
15201 Py_INCREF(Py_None);
15202 return Py_None;
Tim Petersf58a7aa2000-09-22 10:05:54 +000015203}
Larry Hastings2f936352014-08-05 14:04:04 +100015204#endif /* MS_WINDOWS */
15205
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015206
Martin v. Löwis438b5342002-12-27 10:16:42 +000015207#ifdef HAVE_GETLOADAVG
Larry Hastings2f936352014-08-05 14:04:04 +100015208/*[clinic input]
15209os.getloadavg
15210
15211Return average recent system load information.
15212
15213Return the number of processes in the system run queue averaged over
15214the last 1, 5, and 15 minutes as a tuple of three floats.
15215Raises OSError if the load average was unobtainable.
15216[clinic start generated code]*/
15217
15218PyDoc_STRVAR(os_getloadavg__doc__,
15219"getloadavg($module, /)\n"
15220"--\n"
15221"\n"
15222"Return average recent system load information.\n"
15223"\n"
15224"Return the number of processes in the system run queue averaged over\n"
15225"the last 1, 5, and 15 minutes as a tuple of three floats.\n"
15226"Raises OSError if the load average was unobtainable.");
15227
15228#define OS_GETLOADAVG_METHODDEF \
15229 {"getloadavg", (PyCFunction)os_getloadavg, METH_NOARGS, os_getloadavg__doc__},
Martin v. Löwis438b5342002-12-27 10:16:42 +000015230
15231static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015232os_getloadavg_impl(PyModuleDef *module);
15233
15234static PyObject *
15235os_getloadavg(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15236{
15237 return os_getloadavg_impl(module);
15238}
15239
15240static PyObject *
15241os_getloadavg_impl(PyModuleDef *module)
15242/*[clinic end generated code: output=67593a92457d55af input=3d6d826b76d8a34e]*/
Martin v. Löwis438b5342002-12-27 10:16:42 +000015243{
15244 double loadavg[3];
Martin v. Löwis438b5342002-12-27 10:16:42 +000015245 if (getloadavg(loadavg, 3)!=3) {
Stefan Krah0e803b32010-11-26 16:16:47 +000015246 PyErr_SetString(PyExc_OSError, "Load averages are unobtainable");
15247 return NULL;
Martin v. Löwis438b5342002-12-27 10:16:42 +000015248 } else
Stefan Krah0e803b32010-11-26 16:16:47 +000015249 return Py_BuildValue("ddd", loadavg[0], loadavg[1], loadavg[2]);
Martin v. Löwis438b5342002-12-27 10:16:42 +000015250}
Larry Hastings2f936352014-08-05 14:04:04 +100015251#endif /* HAVE_GETLOADAVG */
Martin v. Löwis438b5342002-12-27 10:16:42 +000015252
Larry Hastings2f936352014-08-05 14:04:04 +100015253
15254/*[clinic input]
15255os.device_encoding
15256 fd: int
15257
15258Return a string describing the encoding of a terminal's file descriptor.
15259
15260The file descriptor must be attached to a terminal.
15261If the device is not a terminal, return None.
15262[clinic start generated code]*/
15263
15264PyDoc_STRVAR(os_device_encoding__doc__,
15265"device_encoding($module, /, fd)\n"
15266"--\n"
15267"\n"
15268"Return a string describing the encoding of a terminal\'s file descriptor.\n"
15269"\n"
15270"The file descriptor must be attached to a terminal.\n"
15271"If the device is not a terminal, return None.");
15272
15273#define OS_DEVICE_ENCODING_METHODDEF \
15274 {"device_encoding", (PyCFunction)os_device_encoding, METH_VARARGS|METH_KEYWORDS, os_device_encoding__doc__},
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015275
15276static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015277os_device_encoding_impl(PyModuleDef *module, int fd);
15278
15279static PyObject *
15280os_device_encoding(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015281{
Larry Hastings2f936352014-08-05 14:04:04 +100015282 PyObject *return_value = NULL;
15283 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000015284 int fd;
Brett Cannonefb00c02012-02-29 18:31:31 -050015285
Larry Hastings2f936352014-08-05 14:04:04 +100015286 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15287 "i:device_encoding", _keywords,
15288 &fd))
15289 goto exit;
15290 return_value = os_device_encoding_impl(module, fd);
Brett Cannonefb00c02012-02-29 18:31:31 -050015291
Larry Hastings2f936352014-08-05 14:04:04 +100015292exit:
15293 return return_value;
15294}
15295
15296static PyObject *
15297os_device_encoding_impl(PyModuleDef *module, int fd)
15298/*[clinic end generated code: output=e9f8274d42f5cce3 input=9e1d4a42b66df312]*/
15299{
Brett Cannonefb00c02012-02-29 18:31:31 -050015300 return _Py_device_encoding(fd);
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015301}
15302
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015303
Larry Hastings2f936352014-08-05 14:04:04 +100015304#ifdef HAVE_SETRESUID
15305/*[clinic input]
15306os.setresuid
15307
15308 ruid: uid_t
15309 euid: uid_t
15310 suid: uid_t
15311 /
15312
15313Set the current process's real, effective, and saved user ids.
15314[clinic start generated code]*/
15315
15316PyDoc_STRVAR(os_setresuid__doc__,
15317"setresuid($module, ruid, euid, suid, /)\n"
15318"--\n"
15319"\n"
15320"Set the current process\'s real, effective, and saved user ids.");
15321
15322#define OS_SETRESUID_METHODDEF \
15323 {"setresuid", (PyCFunction)os_setresuid, METH_VARARGS, os_setresuid__doc__},
15324
15325static PyObject *
15326os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid);
15327
15328static PyObject *
15329os_setresuid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015330{
Larry Hastings2f936352014-08-05 14:04:04 +100015331 PyObject *return_value = NULL;
15332 uid_t ruid;
15333 uid_t euid;
15334 uid_t suid;
15335
15336 if (!PyArg_ParseTuple(args,
15337 "O&O&O&:setresuid",
15338 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid, _Py_Uid_Converter, &suid))
15339 goto exit;
15340 return_value = os_setresuid_impl(module, ruid, euid, suid);
15341
15342exit:
15343 return return_value;
15344}
15345
15346static PyObject *
15347os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid)
15348/*[clinic end generated code: output=2e3457cfe7cd1f94 input=9e33cb79a82792f3]*/
15349{
Victor Stinner8c62be82010-05-06 00:08:46 +000015350 if (setresuid(ruid, euid, suid) < 0)
15351 return posix_error();
15352 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015353}
Larry Hastings2f936352014-08-05 14:04:04 +100015354#endif /* HAVE_SETRESUID */
15355
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015356
15357#ifdef HAVE_SETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015358/*[clinic input]
15359os.setresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015360
Larry Hastings2f936352014-08-05 14:04:04 +100015361 rgid: gid_t
15362 egid: gid_t
15363 sgid: gid_t
15364 /
15365
15366Set the current process's real, effective, and saved group ids.
15367[clinic start generated code]*/
15368
15369PyDoc_STRVAR(os_setresgid__doc__,
15370"setresgid($module, rgid, egid, sgid, /)\n"
15371"--\n"
15372"\n"
15373"Set the current process\'s real, effective, and saved group ids.");
15374
15375#define OS_SETRESGID_METHODDEF \
15376 {"setresgid", (PyCFunction)os_setresgid, METH_VARARGS, os_setresgid__doc__},
15377
15378static PyObject *
15379os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid);
15380
15381static PyObject *
15382os_setresgid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015383{
Larry Hastings2f936352014-08-05 14:04:04 +100015384 PyObject *return_value = NULL;
15385 gid_t rgid;
15386 gid_t egid;
15387 gid_t sgid;
15388
15389 if (!PyArg_ParseTuple(args,
15390 "O&O&O&:setresgid",
15391 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid, _Py_Gid_Converter, &sgid))
15392 goto exit;
15393 return_value = os_setresgid_impl(module, rgid, egid, sgid);
15394
15395exit:
15396 return return_value;
15397}
15398
15399static PyObject *
15400os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid)
15401/*[clinic end generated code: output=8a7ee6c1f2482362 input=33e9e0785ef426b1]*/
15402{
Victor Stinner8c62be82010-05-06 00:08:46 +000015403 if (setresgid(rgid, egid, sgid) < 0)
15404 return posix_error();
15405 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015406}
Larry Hastings2f936352014-08-05 14:04:04 +100015407#endif /* HAVE_SETRESGID */
15408
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015409
15410#ifdef HAVE_GETRESUID
Larry Hastings2f936352014-08-05 14:04:04 +100015411/*[clinic input]
15412os.getresuid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015413
Larry Hastings2f936352014-08-05 14:04:04 +100015414Return a tuple of the current process's real, effective, and saved user ids.
15415[clinic start generated code]*/
15416
15417PyDoc_STRVAR(os_getresuid__doc__,
15418"getresuid($module, /)\n"
15419"--\n"
15420"\n"
15421"Return a tuple of the current process\'s real, effective, and saved user ids.");
15422
15423#define OS_GETRESUID_METHODDEF \
15424 {"getresuid", (PyCFunction)os_getresuid, METH_NOARGS, os_getresuid__doc__},
15425
15426static PyObject *
15427os_getresuid_impl(PyModuleDef *module);
15428
15429static PyObject *
15430os_getresuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15431{
15432 return os_getresuid_impl(module);
15433}
15434
15435static PyObject *
15436os_getresuid_impl(PyModuleDef *module)
15437/*[clinic end generated code: output=d0786686a6ef1320 input=41ccfa8e1f6517ad]*/
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015438{
Victor Stinner8c62be82010-05-06 00:08:46 +000015439 uid_t ruid, euid, suid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015440 if (getresuid(&ruid, &euid, &suid) < 0)
15441 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015442 return Py_BuildValue("(NNN)", _PyLong_FromUid(ruid),
15443 _PyLong_FromUid(euid),
15444 _PyLong_FromUid(suid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015445}
Larry Hastings2f936352014-08-05 14:04:04 +100015446#endif /* HAVE_GETRESUID */
15447
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015448
15449#ifdef HAVE_GETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015450/*[clinic input]
15451os.getresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015452
Larry Hastings2f936352014-08-05 14:04:04 +100015453Return a tuple of the current process's real, effective, and saved group ids.
15454[clinic start generated code]*/
15455
15456PyDoc_STRVAR(os_getresgid__doc__,
15457"getresgid($module, /)\n"
15458"--\n"
15459"\n"
15460"Return a tuple of the current process\'s real, effective, and saved group ids.");
15461
15462#define OS_GETRESGID_METHODDEF \
15463 {"getresgid", (PyCFunction)os_getresgid, METH_NOARGS, os_getresgid__doc__},
15464
15465static PyObject *
15466os_getresgid_impl(PyModuleDef *module);
15467
15468static PyObject *
15469os_getresgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015470{
Larry Hastings2f936352014-08-05 14:04:04 +100015471 return os_getresgid_impl(module);
15472}
15473
15474static PyObject *
15475os_getresgid_impl(PyModuleDef *module)
15476/*[clinic end generated code: output=05249ac795fa759f input=517e68db9ca32df6]*/
15477{
15478 gid_t rgid, egid, sgid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015479 if (getresgid(&rgid, &egid, &sgid) < 0)
15480 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015481 return Py_BuildValue("(NNN)", _PyLong_FromGid(rgid),
15482 _PyLong_FromGid(egid),
15483 _PyLong_FromGid(sgid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015484}
Larry Hastings2f936352014-08-05 14:04:04 +100015485#endif /* HAVE_GETRESGID */
15486
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015487
Benjamin Peterson9428d532011-09-14 11:45:52 -040015488#ifdef USE_XATTRS
Larry Hastings2f936352014-08-05 14:04:04 +100015489/*[clinic input]
15490os.getxattr
Benjamin Peterson799bd802011-08-31 22:15:17 -040015491
Larry Hastings2f936352014-08-05 14:04:04 +100015492 path: path_t(allow_fd=True)
15493 attribute: path_t
15494 *
15495 follow_symlinks: bool = True
15496
15497Return the value of extended attribute attribute on path.
15498
15499path may be either a string or an open file descriptor.
15500If follow_symlinks is False, and the last element of the path is a symbolic
15501 link, getxattr will examine the symbolic link itself instead of the file
15502 the link points to.
15503
15504[clinic start generated code]*/
15505
15506PyDoc_STRVAR(os_getxattr__doc__,
15507"getxattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15508"--\n"
15509"\n"
15510"Return the value of extended attribute attribute on path.\n"
15511"\n"
15512"path may be either a string or an open file descriptor.\n"
15513"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15514" link, getxattr will examine the symbolic link itself instead of the file\n"
15515" the link points to.");
15516
15517#define OS_GETXATTR_METHODDEF \
15518 {"getxattr", (PyCFunction)os_getxattr, METH_VARARGS|METH_KEYWORDS, os_getxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015519
15520static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015521os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15522
15523static PyObject *
15524os_getxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015525{
Larry Hastings2f936352014-08-05 14:04:04 +100015526 PyObject *return_value = NULL;
15527 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15528 path_t path = PATH_T_INITIALIZE("getxattr", "path", 0, 1);
15529 path_t attribute = PATH_T_INITIALIZE("getxattr", "attribute", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015530 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015531
Larry Hastings2f936352014-08-05 14:04:04 +100015532 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15533 "O&O&|$p:getxattr", _keywords,
15534 path_converter, &path, path_converter, &attribute, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015535 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015536 return_value = os_getxattr_impl(module, &path, &attribute, follow_symlinks);
15537
15538exit:
15539 /* Cleanup for path */
15540 path_cleanup(&path);
15541 /* Cleanup for attribute */
15542 path_cleanup(&attribute);
15543
15544 return return_value;
15545}
15546
15547static PyObject *
15548os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15549/*[clinic end generated code: output=bbc9454fe2b9ea86 input=8c8ea3bab78d89c2]*/
15550{
15551 Py_ssize_t i;
15552 PyObject *buffer = NULL;
15553
15554 if (fd_and_follow_symlinks_invalid("getxattr", path->fd, follow_symlinks))
15555 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015556
Larry Hastings9cf065c2012-06-22 16:30:09 -070015557 for (i = 0; ; i++) {
15558 void *ptr;
15559 ssize_t result;
15560 static Py_ssize_t buffer_sizes[] = {128, XATTR_SIZE_MAX, 0};
15561 Py_ssize_t buffer_size = buffer_sizes[i];
15562 if (!buffer_size) {
Larry Hastings2f936352014-08-05 14:04:04 +100015563 path_error(path);
15564 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015565 }
15566 buffer = PyBytes_FromStringAndSize(NULL, buffer_size);
15567 if (!buffer)
Larry Hastings2f936352014-08-05 14:04:04 +100015568 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015569 ptr = PyBytes_AS_STRING(buffer);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015570
Larry Hastings9cf065c2012-06-22 16:30:09 -070015571 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015572 if (path->fd >= 0)
15573 result = fgetxattr(path->fd, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015574 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015575 result = getxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015576 else
Larry Hastings2f936352014-08-05 14:04:04 +100015577 result = lgetxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015578 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015579
Larry Hastings9cf065c2012-06-22 16:30:09 -070015580 if (result < 0) {
15581 Py_DECREF(buffer);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015582 if (errno == ERANGE)
15583 continue;
Larry Hastings2f936352014-08-05 14:04:04 +100015584 path_error(path);
15585 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015586 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015587
Larry Hastings9cf065c2012-06-22 16:30:09 -070015588 if (result != buffer_size) {
15589 /* Can only shrink. */
15590 _PyBytes_Resize(&buffer, result);
15591 }
15592 break;
15593 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015594
Larry Hastings9cf065c2012-06-22 16:30:09 -070015595 return buffer;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015596}
15597
Larry Hastings2f936352014-08-05 14:04:04 +100015598
15599/*[clinic input]
15600os.setxattr
15601
15602 path: path_t(allow_fd=True)
15603 attribute: path_t
15604 value: Py_buffer
15605 flags: int = 0
15606 *
15607 follow_symlinks: bool = True
15608
15609Set extended attribute attribute on path to value.
15610
15611path may be either a string or an open file descriptor.
15612If follow_symlinks is False, and the last element of the path is a symbolic
15613 link, setxattr will modify the symbolic link itself instead of the file
15614 the link points to.
15615
15616[clinic start generated code]*/
15617
15618PyDoc_STRVAR(os_setxattr__doc__,
15619"setxattr($module, /, path, attribute, value, flags=0, *,\n"
15620" follow_symlinks=True)\n"
15621"--\n"
15622"\n"
15623"Set extended attribute attribute on path to value.\n"
15624"\n"
15625"path may be either a string or an open file descriptor.\n"
15626"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15627" link, setxattr will modify the symbolic link itself instead of the file\n"
15628" the link points to.");
15629
15630#define OS_SETXATTR_METHODDEF \
15631 {"setxattr", (PyCFunction)os_setxattr, METH_VARARGS|METH_KEYWORDS, os_setxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015632
15633static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015634os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks);
15635
15636static PyObject *
15637os_setxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015638{
Larry Hastings2f936352014-08-05 14:04:04 +100015639 PyObject *return_value = NULL;
15640 static char *_keywords[] = {"path", "attribute", "value", "flags", "follow_symlinks", NULL};
15641 path_t path = PATH_T_INITIALIZE("setxattr", "path", 0, 1);
15642 path_t attribute = PATH_T_INITIALIZE("setxattr", "attribute", 0, 0);
15643 Py_buffer value = {NULL, NULL};
Larry Hastings9cf065c2012-06-22 16:30:09 -070015644 int flags = 0;
15645 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015646
Larry Hastings2f936352014-08-05 14:04:04 +100015647 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15648 "O&O&y*|i$p:setxattr", _keywords,
15649 path_converter, &path, path_converter, &attribute, &value, &flags, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015650 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015651 return_value = os_setxattr_impl(module, &path, &attribute, &value, flags, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015652
Larry Hastings9cf065c2012-06-22 16:30:09 -070015653exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015654 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015655 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015656 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015657 path_cleanup(&attribute);
Larry Hastings2f936352014-08-05 14:04:04 +100015658 /* Cleanup for value */
15659 if (value.obj)
15660 PyBuffer_Release(&value);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015661
Larry Hastings9cf065c2012-06-22 16:30:09 -070015662 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015663}
15664
Benjamin Peterson799bd802011-08-31 22:15:17 -040015665static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015666os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks)
15667/*[clinic end generated code: output=2ff845d8e024b218 input=f0d26833992015c2]*/
Benjamin Peterson799bd802011-08-31 22:15:17 -040015668{
Larry Hastings2f936352014-08-05 14:04:04 +100015669 ssize_t result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015670
Larry Hastings2f936352014-08-05 14:04:04 +100015671 if (fd_and_follow_symlinks_invalid("setxattr", path->fd, follow_symlinks))
Benjamin Peterson799bd802011-08-31 22:15:17 -040015672 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015673
Benjamin Peterson799bd802011-08-31 22:15:17 -040015674 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015675 if (path->fd > -1)
15676 result = fsetxattr(path->fd, attribute->narrow,
15677 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015678 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015679 result = setxattr(path->narrow, attribute->narrow,
15680 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015681 else
Larry Hastings2f936352014-08-05 14:04:04 +100015682 result = lsetxattr(path->narrow, attribute->narrow,
15683 value->buf, value->len, flags);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015684 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015685
Larry Hastings9cf065c2012-06-22 16:30:09 -070015686 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100015687 path_error(path);
15688 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015689 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015690
Larry Hastings2f936352014-08-05 14:04:04 +100015691 Py_RETURN_NONE;
15692}
15693
15694
15695/*[clinic input]
15696os.removexattr
15697
15698 path: path_t(allow_fd=True)
15699 attribute: path_t
15700 *
15701 follow_symlinks: bool = True
15702
15703Remove extended attribute attribute on path.
15704
15705path may be either a string or an open file descriptor.
15706If follow_symlinks is False, and the last element of the path is a symbolic
15707 link, removexattr will modify the symbolic link itself instead of the file
15708 the link points to.
15709
15710[clinic start generated code]*/
15711
15712PyDoc_STRVAR(os_removexattr__doc__,
15713"removexattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15714"--\n"
15715"\n"
15716"Remove extended attribute attribute on path.\n"
15717"\n"
15718"path may be either a string or an open file descriptor.\n"
15719"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15720" link, removexattr will modify the symbolic link itself instead of the file\n"
15721" the link points to.");
15722
15723#define OS_REMOVEXATTR_METHODDEF \
15724 {"removexattr", (PyCFunction)os_removexattr, METH_VARARGS|METH_KEYWORDS, os_removexattr__doc__},
15725
15726static PyObject *
15727os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15728
15729static PyObject *
15730os_removexattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
15731{
15732 PyObject *return_value = NULL;
15733 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15734 path_t path = PATH_T_INITIALIZE("removexattr", "path", 0, 1);
15735 path_t attribute = PATH_T_INITIALIZE("removexattr", "attribute", 0, 0);
15736 int follow_symlinks = 1;
15737
15738 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15739 "O&O&|$p:removexattr", _keywords,
15740 path_converter, &path, path_converter, &attribute, &follow_symlinks))
15741 goto exit;
15742 return_value = os_removexattr_impl(module, &path, &attribute, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015743
Larry Hastings9cf065c2012-06-22 16:30:09 -070015744exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015745 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015746 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015747 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015748 path_cleanup(&attribute);
15749
15750 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015751}
15752
Larry Hastings2f936352014-08-05 14:04:04 +100015753static PyObject *
15754os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15755/*[clinic end generated code: output=8dfc715bf607c4cf input=cdb54834161e3329]*/
15756{
15757 ssize_t result;
15758
15759 if (fd_and_follow_symlinks_invalid("removexattr", path->fd, follow_symlinks))
15760 return NULL;
15761
15762 Py_BEGIN_ALLOW_THREADS;
15763 if (path->fd > -1)
15764 result = fremovexattr(path->fd, attribute->narrow);
15765 else if (follow_symlinks)
15766 result = removexattr(path->narrow, attribute->narrow);
15767 else
15768 result = lremovexattr(path->narrow, attribute->narrow);
15769 Py_END_ALLOW_THREADS;
15770
15771 if (result) {
15772 return path_error(path);
15773 }
15774
15775 Py_RETURN_NONE;
15776}
15777
15778
15779/*[clinic input]
15780os.listxattr
15781
15782 path: path_t(allow_fd=True, nullable=True) = None
15783 *
15784 follow_symlinks: bool = True
15785
15786Return a list of extended attributes on path.
15787
15788path may be either None, a string, or an open file descriptor.
15789if path is None, listxattr will examine the current directory.
15790If follow_symlinks is False, and the last element of the path is a symbolic
15791 link, listxattr will examine the symbolic link itself instead of the file
15792 the link points to.
15793[clinic start generated code]*/
15794
15795PyDoc_STRVAR(os_listxattr__doc__,
15796"listxattr($module, /, path=None, *, follow_symlinks=True)\n"
15797"--\n"
15798"\n"
15799"Return a list of extended attributes on path.\n"
15800"\n"
15801"path may be either None, a string, or an open file descriptor.\n"
15802"if path is None, listxattr will examine the current directory.\n"
15803"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15804" link, listxattr will examine the symbolic link itself instead of the file\n"
15805" the link points to.");
15806
15807#define OS_LISTXATTR_METHODDEF \
15808 {"listxattr", (PyCFunction)os_listxattr, METH_VARARGS|METH_KEYWORDS, os_listxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015809
15810static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015811os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks);
15812
15813static PyObject *
15814os_listxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015815{
Larry Hastings2f936352014-08-05 14:04:04 +100015816 PyObject *return_value = NULL;
15817 static char *_keywords[] = {"path", "follow_symlinks", NULL};
15818 path_t path = PATH_T_INITIALIZE("listxattr", "path", 1, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015819 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100015820
15821 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15822 "|O&$p:listxattr", _keywords,
15823 path_converter, &path, &follow_symlinks))
15824 goto exit;
15825 return_value = os_listxattr_impl(module, &path, follow_symlinks);
15826
15827exit:
15828 /* Cleanup for path */
15829 path_cleanup(&path);
15830
15831 return return_value;
15832}
15833
15834static PyObject *
15835os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks)
15836/*[clinic end generated code: output=3104cafda1a3d887 input=08cca53ac0b07c13]*/
15837{
Larry Hastings9cf065c2012-06-22 16:30:09 -070015838 Py_ssize_t i;
15839 PyObject *result = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100015840 const char *name;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015841 char *buffer = NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015842
Larry Hastings2f936352014-08-05 14:04:04 +100015843 if (fd_and_follow_symlinks_invalid("listxattr", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015844 goto exit;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015845
Larry Hastings2f936352014-08-05 14:04:04 +100015846 name = path->narrow ? path->narrow : ".";
15847
Larry Hastings9cf065c2012-06-22 16:30:09 -070015848 for (i = 0; ; i++) {
15849 char *start, *trace, *end;
15850 ssize_t length;
15851 static Py_ssize_t buffer_sizes[] = { 256, XATTR_LIST_MAX, 0 };
15852 Py_ssize_t buffer_size = buffer_sizes[i];
15853 if (!buffer_size) {
Christian Heimes3b9493b2012-09-23 16:11:15 +020015854 /* ERANGE */
Larry Hastings2f936352014-08-05 14:04:04 +100015855 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015856 break;
15857 }
15858 buffer = PyMem_MALLOC(buffer_size);
15859 if (!buffer) {
15860 PyErr_NoMemory();
15861 break;
15862 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015863
Larry Hastings9cf065c2012-06-22 16:30:09 -070015864 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015865 if (path->fd > -1)
15866 length = flistxattr(path->fd, buffer, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015867 else if (follow_symlinks)
15868 length = listxattr(name, buffer, buffer_size);
15869 else
15870 length = llistxattr(name, buffer, buffer_size);
15871 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015872
Larry Hastings9cf065c2012-06-22 16:30:09 -070015873 if (length < 0) {
Antoine Pitrou7f987392013-05-13 19:46:29 +020015874 if (errno == ERANGE) {
15875 PyMem_FREE(buffer);
Benjamin Petersondedac522013-05-13 19:55:40 -050015876 buffer = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015877 continue;
Antoine Pitrou7f987392013-05-13 19:46:29 +020015878 }
Larry Hastings2f936352014-08-05 14:04:04 +100015879 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015880 break;
15881 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015882
Larry Hastings9cf065c2012-06-22 16:30:09 -070015883 result = PyList_New(0);
15884 if (!result) {
15885 goto exit;
15886 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015887
Larry Hastings9cf065c2012-06-22 16:30:09 -070015888 end = buffer + length;
15889 for (trace = start = buffer; trace != end; trace++) {
15890 if (!*trace) {
15891 int error;
15892 PyObject *attribute = PyUnicode_DecodeFSDefaultAndSize(start,
15893 trace - start);
15894 if (!attribute) {
15895 Py_DECREF(result);
15896 result = NULL;
15897 goto exit;
15898 }
15899 error = PyList_Append(result, attribute);
15900 Py_DECREF(attribute);
15901 if (error) {
15902 Py_DECREF(result);
15903 result = NULL;
15904 goto exit;
15905 }
15906 start = trace + 1;
15907 }
15908 }
15909 break;
15910 }
15911exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070015912 if (buffer)
15913 PyMem_FREE(buffer);
15914 return result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015915}
Benjamin Peterson9428d532011-09-14 11:45:52 -040015916#endif /* USE_XATTRS */
Benjamin Peterson799bd802011-08-31 22:15:17 -040015917
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015918
Larry Hastings2f936352014-08-05 14:04:04 +100015919/*[clinic input]
15920os.urandom
15921
15922 size: Py_ssize_t
15923 /
15924
15925Return a bytes object containing random bytes suitable for cryptographic use.
15926[clinic start generated code]*/
15927
15928PyDoc_STRVAR(os_urandom__doc__,
15929"urandom($module, size, /)\n"
15930"--\n"
15931"\n"
15932"Return a bytes object containing random bytes suitable for cryptographic use.");
15933
15934#define OS_URANDOM_METHODDEF \
15935 {"urandom", (PyCFunction)os_urandom, METH_VARARGS, os_urandom__doc__},
Georg Brandl2fb477c2012-02-21 00:33:36 +010015936
15937static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015938os_urandom_impl(PyModuleDef *module, Py_ssize_t size);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015939
Larry Hastings2f936352014-08-05 14:04:04 +100015940static PyObject *
15941os_urandom(PyModuleDef *module, PyObject *args)
15942{
15943 PyObject *return_value = NULL;
15944 Py_ssize_t size;
15945
15946 if (!PyArg_ParseTuple(args,
15947 "n:urandom",
15948 &size))
15949 goto exit;
15950 return_value = os_urandom_impl(module, size);
15951
15952exit:
15953 return return_value;
15954}
15955
15956static PyObject *
15957os_urandom_impl(PyModuleDef *module, Py_ssize_t size)
15958/*[clinic end generated code: output=5dbff582cab94cb9 input=4067cdb1b6776c29]*/
15959{
15960 PyObject *bytes;
15961 int result;
15962
Georg Brandl2fb477c2012-02-21 00:33:36 +010015963 if (size < 0)
15964 return PyErr_Format(PyExc_ValueError,
15965 "negative argument not allowed");
Larry Hastings2f936352014-08-05 14:04:04 +100015966 bytes = PyBytes_FromStringAndSize(NULL, size);
15967 if (bytes == NULL)
Georg Brandl2fb477c2012-02-21 00:33:36 +010015968 return NULL;
15969
Larry Hastings2f936352014-08-05 14:04:04 +100015970 result = _PyOS_URandom(PyBytes_AS_STRING(bytes),
15971 PyBytes_GET_SIZE(bytes));
15972 if (result == -1) {
15973 Py_DECREF(bytes);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015974 return NULL;
15975 }
Larry Hastings2f936352014-08-05 14:04:04 +100015976 return bytes;
Georg Brandl2fb477c2012-02-21 00:33:36 +010015977}
15978
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015979/* Terminal size querying */
15980
15981static PyTypeObject TerminalSizeType;
15982
15983PyDoc_STRVAR(TerminalSize_docstring,
15984 "A tuple of (columns, lines) for holding terminal window size");
15985
15986static PyStructSequence_Field TerminalSize_fields[] = {
15987 {"columns", "width of the terminal window in characters"},
15988 {"lines", "height of the terminal window in characters"},
15989 {NULL, NULL}
15990};
15991
15992static PyStructSequence_Desc TerminalSize_desc = {
15993 "os.terminal_size",
15994 TerminalSize_docstring,
15995 TerminalSize_fields,
15996 2,
15997};
15998
15999#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
Larry Hastings2f936352014-08-05 14:04:04 +100016000/* AC 3.5: fd should accept None */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010016001PyDoc_STRVAR(termsize__doc__,
16002 "Return the size of the terminal window as (columns, lines).\n" \
16003 "\n" \
16004 "The optional argument fd (default standard output) specifies\n" \
16005 "which file descriptor should be queried.\n" \
16006 "\n" \
16007 "If the file descriptor is not connected to a terminal, an OSError\n" \
16008 "is thrown.\n" \
16009 "\n" \
16010 "This function will only be defined if an implementation is\n" \
16011 "available for this system.\n" \
16012 "\n" \
16013 "shutil.get_terminal_size is the high-level function which should \n" \
16014 "normally be used, os.get_terminal_size is the low-level implementation.");
16015
16016static PyObject*
16017get_terminal_size(PyObject *self, PyObject *args)
16018{
16019 int columns, lines;
16020 PyObject *termsize;
16021
16022 int fd = fileno(stdout);
16023 /* Under some conditions stdout may not be connected and
16024 * fileno(stdout) may point to an invalid file descriptor. For example
16025 * GUI apps don't have valid standard streams by default.
16026 *
16027 * If this happens, and the optional fd argument is not present,
16028 * the ioctl below will fail returning EBADF. This is what we want.
16029 */
16030
16031 if (!PyArg_ParseTuple(args, "|i", &fd))
16032 return NULL;
16033
16034#ifdef TERMSIZE_USE_IOCTL
16035 {
16036 struct winsize w;
16037 if (ioctl(fd, TIOCGWINSZ, &w))
16038 return PyErr_SetFromErrno(PyExc_OSError);
16039 columns = w.ws_col;
16040 lines = w.ws_row;
16041 }
16042#endif /* TERMSIZE_USE_IOCTL */
16043
16044#ifdef TERMSIZE_USE_CONIO
16045 {
16046 DWORD nhandle;
16047 HANDLE handle;
16048 CONSOLE_SCREEN_BUFFER_INFO csbi;
16049 switch (fd) {
16050 case 0: nhandle = STD_INPUT_HANDLE;
16051 break;
16052 case 1: nhandle = STD_OUTPUT_HANDLE;
16053 break;
16054 case 2: nhandle = STD_ERROR_HANDLE;
16055 break;
16056 default:
16057 return PyErr_Format(PyExc_ValueError, "bad file descriptor");
16058 }
16059 handle = GetStdHandle(nhandle);
16060 if (handle == NULL)
16061 return PyErr_Format(PyExc_OSError, "handle cannot be retrieved");
16062 if (handle == INVALID_HANDLE_VALUE)
16063 return PyErr_SetFromWindowsErr(0);
16064
16065 if (!GetConsoleScreenBufferInfo(handle, &csbi))
16066 return PyErr_SetFromWindowsErr(0);
16067
16068 columns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
16069 lines = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
16070 }
16071#endif /* TERMSIZE_USE_CONIO */
16072
16073 termsize = PyStructSequence_New(&TerminalSizeType);
16074 if (termsize == NULL)
16075 return NULL;
16076 PyStructSequence_SET_ITEM(termsize, 0, PyLong_FromLong(columns));
16077 PyStructSequence_SET_ITEM(termsize, 1, PyLong_FromLong(lines));
16078 if (PyErr_Occurred()) {
16079 Py_DECREF(termsize);
16080 return NULL;
16081 }
16082 return termsize;
16083}
16084#endif /* defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL) */
16085
Larry Hastings2f936352014-08-05 14:04:04 +100016086
16087/*[clinic input]
16088os.cpu_count
16089
16090Return the number of CPUs in the system; return None if indeterminable.
16091[clinic start generated code]*/
16092
16093PyDoc_STRVAR(os_cpu_count__doc__,
16094"cpu_count($module, /)\n"
16095"--\n"
16096"\n"
16097"Return the number of CPUs in the system; return None if indeterminable.");
16098
16099#define OS_CPU_COUNT_METHODDEF \
16100 {"cpu_count", (PyCFunction)os_cpu_count, METH_NOARGS, os_cpu_count__doc__},
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016101
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016102static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100016103os_cpu_count_impl(PyModuleDef *module);
16104
16105static PyObject *
16106os_cpu_count(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
16107{
16108 return os_cpu_count_impl(module);
16109}
16110
16111static PyObject *
16112os_cpu_count_impl(PyModuleDef *module)
16113/*[clinic end generated code: output=92e2a4a729eb7740 input=d55e2f8f3823a628]*/
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016114{
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016115 int ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016116#ifdef MS_WINDOWS
16117 SYSTEM_INFO sysinfo;
16118 GetSystemInfo(&sysinfo);
16119 ncpu = sysinfo.dwNumberOfProcessors;
16120#elif defined(__hpux)
16121 ncpu = mpctl(MPC_GETNUMSPUS, NULL, NULL);
16122#elif defined(HAVE_SYSCONF) && defined(_SC_NPROCESSORS_ONLN)
16123 ncpu = sysconf(_SC_NPROCESSORS_ONLN);
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016124#elif defined(__DragonFly__) || \
16125 defined(__OpenBSD__) || \
16126 defined(__FreeBSD__) || \
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016127 defined(__NetBSD__) || \
16128 defined(__APPLE__)
Charles-Francois Natali7c4f8da2013-05-20 17:40:32 +020016129 int mib[2];
16130 size_t len = sizeof(ncpu);
16131 mib[0] = CTL_HW;
16132 mib[1] = HW_NCPU;
16133 if (sysctl(mib, 2, &ncpu, &len, NULL, 0) != 0)
16134 ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016135#endif
16136 if (ncpu >= 1)
16137 return PyLong_FromLong(ncpu);
16138 else
16139 Py_RETURN_NONE;
16140}
16141
Victor Stinnerdaf45552013-08-28 00:53:59 +020016142
Larry Hastings2f936352014-08-05 14:04:04 +100016143/*[clinic input]
16144os.get_inheritable -> bool
16145
16146 fd: int
16147 /
16148
16149Get the close-on-exe flag of the specified file descriptor.
16150[clinic start generated code]*/
16151
16152PyDoc_STRVAR(os_get_inheritable__doc__,
16153"get_inheritable($module, fd, /)\n"
16154"--\n"
16155"\n"
16156"Get the close-on-exe flag of the specified file descriptor.");
16157
16158#define OS_GET_INHERITABLE_METHODDEF \
16159 {"get_inheritable", (PyCFunction)os_get_inheritable, METH_VARARGS, os_get_inheritable__doc__},
16160
16161static int
16162os_get_inheritable_impl(PyModuleDef *module, int fd);
16163
16164static PyObject *
16165os_get_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016166{
Larry Hastings2f936352014-08-05 14:04:04 +100016167 PyObject *return_value = NULL;
16168 int fd;
16169 int _return_value;
16170
16171 if (!PyArg_ParseTuple(args,
16172 "i:get_inheritable",
16173 &fd))
16174 goto exit;
16175 _return_value = os_get_inheritable_impl(module, fd);
16176 if ((_return_value == -1) && PyErr_Occurred())
16177 goto exit;
16178 return_value = PyBool_FromLong((long)_return_value);
16179
16180exit:
16181 return return_value;
16182}
16183
16184static int
16185os_get_inheritable_impl(PyModuleDef *module, int fd)
16186/*[clinic end generated code: output=261d1dd2b0dbdc35 input=89ac008dc9ab6b95]*/
16187{
16188 if (!_PyVerify_fd(fd)){
16189 posix_error();
16190 return -1;
16191 }
16192
16193 return _Py_get_inheritable(fd);
16194}
16195
16196
16197/*[clinic input]
16198os.set_inheritable
16199 fd: int
16200 inheritable: int
16201 /
16202
16203Set the inheritable flag of the specified file descriptor.
16204[clinic start generated code]*/
16205
16206PyDoc_STRVAR(os_set_inheritable__doc__,
16207"set_inheritable($module, fd, inheritable, /)\n"
16208"--\n"
16209"\n"
16210"Set the inheritable flag of the specified file descriptor.");
16211
16212#define OS_SET_INHERITABLE_METHODDEF \
16213 {"set_inheritable", (PyCFunction)os_set_inheritable, METH_VARARGS, os_set_inheritable__doc__},
16214
16215static PyObject *
16216os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable);
16217
16218static PyObject *
16219os_set_inheritable(PyModuleDef *module, PyObject *args)
16220{
16221 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016222 int fd;
16223 int inheritable;
16224
Larry Hastings2f936352014-08-05 14:04:04 +100016225 if (!PyArg_ParseTuple(args,
16226 "ii:set_inheritable",
16227 &fd, &inheritable))
16228 goto exit;
16229 return_value = os_set_inheritable_impl(module, fd, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016230
Larry Hastings2f936352014-08-05 14:04:04 +100016231exit:
16232 return return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016233}
16234
Larry Hastings2f936352014-08-05 14:04:04 +100016235static PyObject *
16236os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable)
16237/*[clinic end generated code: output=64dfe5e15c906539 input=9ceaead87a1e2402]*/
Victor Stinnerdaf45552013-08-28 00:53:59 +020016238{
Victor Stinnerdaf45552013-08-28 00:53:59 +020016239 if (!_PyVerify_fd(fd))
16240 return posix_error();
16241
16242 if (_Py_set_inheritable(fd, inheritable, NULL) < 0)
16243 return NULL;
16244 Py_RETURN_NONE;
16245}
16246
16247
16248#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100016249/*[clinic input]
16250os.get_handle_inheritable -> bool
16251 handle: Py_intptr_t
16252 /
Victor Stinnerdaf45552013-08-28 00:53:59 +020016253
Larry Hastings2f936352014-08-05 14:04:04 +100016254Get the close-on-exe flag of the specified file descriptor.
16255[clinic start generated code]*/
16256
16257PyDoc_STRVAR(os_get_handle_inheritable__doc__,
16258"get_handle_inheritable($module, handle, /)\n"
16259"--\n"
16260"\n"
16261"Get the close-on-exe flag of the specified file descriptor.");
16262
16263#define OS_GET_HANDLE_INHERITABLE_METHODDEF \
16264 {"get_handle_inheritable", (PyCFunction)os_get_handle_inheritable, METH_VARARGS, os_get_handle_inheritable__doc__},
16265
16266static int
16267os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle);
16268
16269static PyObject *
16270os_get_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016271{
Larry Hastings2f936352014-08-05 14:04:04 +100016272 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016273 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016274 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016275
Larry Hastings2f936352014-08-05 14:04:04 +100016276 if (!PyArg_ParseTuple(args,
16277 "" _Py_PARSE_INTPTR ":get_handle_inheritable",
16278 &handle))
16279 goto exit;
16280 _return_value = os_get_handle_inheritable_impl(module, handle);
16281 if ((_return_value == -1) && PyErr_Occurred())
16282 goto exit;
16283 return_value = PyBool_FromLong((long)_return_value);
16284
16285exit:
16286 return return_value;
16287}
16288
16289static int
16290os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle)
16291/*[clinic end generated code: output=d5bf9d86900bf457 input=5f7759443aae3dc5]*/
16292{
16293 DWORD flags;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016294
16295 if (!GetHandleInformation((HANDLE)handle, &flags)) {
16296 PyErr_SetFromWindowsErr(0);
Larry Hastings2f936352014-08-05 14:04:04 +100016297 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016298 }
16299
Larry Hastings2f936352014-08-05 14:04:04 +100016300 return flags & HANDLE_FLAG_INHERIT;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016301}
16302
Victor Stinnerdaf45552013-08-28 00:53:59 +020016303
Larry Hastings2f936352014-08-05 14:04:04 +100016304/*[clinic input]
16305os.set_handle_inheritable
16306 handle: Py_intptr_t
16307 inheritable: bool
16308 /
16309
16310Set the inheritable flag of the specified handle.
16311[clinic start generated code]*/
16312
16313PyDoc_STRVAR(os_set_handle_inheritable__doc__,
16314"set_handle_inheritable($module, handle, inheritable, /)\n"
16315"--\n"
16316"\n"
16317"Set the inheritable flag of the specified handle.");
16318
16319#define OS_SET_HANDLE_INHERITABLE_METHODDEF \
16320 {"set_handle_inheritable", (PyCFunction)os_set_handle_inheritable, METH_VARARGS, os_set_handle_inheritable__doc__},
16321
16322static PyObject *
16323os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable);
16324
16325static PyObject *
16326os_set_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016327{
Larry Hastings2f936352014-08-05 14:04:04 +100016328 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016329 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016330 int inheritable;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016331
Larry Hastings2f936352014-08-05 14:04:04 +100016332 if (!PyArg_ParseTuple(args,
16333 "" _Py_PARSE_INTPTR "p:set_handle_inheritable",
16334 &handle, &inheritable))
16335 goto exit;
16336 return_value = os_set_handle_inheritable_impl(module, handle, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016337
Larry Hastings2f936352014-08-05 14:04:04 +100016338exit:
16339 return return_value;
16340}
16341
16342static PyObject *
16343os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable)
16344/*[clinic end generated code: output=ee5fcc6d9f0d4f8b input=e64b2b2730469def]*/
16345{
16346 DWORD flags = inheritable ? HANDLE_FLAG_INHERIT : 0;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016347 if (!SetHandleInformation((HANDLE)handle, HANDLE_FLAG_INHERIT, flags)) {
16348 PyErr_SetFromWindowsErr(0);
16349 return NULL;
16350 }
16351 Py_RETURN_NONE;
16352}
Larry Hastings2f936352014-08-05 14:04:04 +100016353#endif /* MS_WINDOWS */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010016354
Victor Stinner1db9e7b2014-07-29 22:32:47 +020016355#ifndef MS_WINDOWS
16356PyDoc_STRVAR(get_blocking__doc__,
16357 "get_blocking(fd) -> bool\n" \
16358 "\n" \
16359 "Get the blocking mode of the file descriptor:\n" \
16360 "False if the O_NONBLOCK flag is set, True if the flag is cleared.");
16361
16362static PyObject*
16363posix_get_blocking(PyObject *self, PyObject *args)
16364{
16365 int fd;
16366 int blocking;
16367
16368 if (!PyArg_ParseTuple(args, "i:get_blocking", &fd))
16369 return NULL;
16370
16371 if (!_PyVerify_fd(fd))
16372 return posix_error();
16373
16374 blocking = _Py_get_blocking(fd);
16375 if (blocking < 0)
16376 return NULL;
16377 return PyBool_FromLong(blocking);
16378}
16379
16380PyDoc_STRVAR(set_blocking__doc__,
16381 "set_blocking(fd, blocking)\n" \
16382 "\n" \
16383 "Set the blocking mode of the specified file descriptor.\n" \
16384 "Set the O_NONBLOCK flag if blocking is False,\n" \
16385 "clear the O_NONBLOCK flag otherwise.");
16386
16387static PyObject*
16388posix_set_blocking(PyObject *self, PyObject *args)
16389{
16390 int fd, blocking;
16391
16392 if (!PyArg_ParseTuple(args, "ii:set_blocking", &fd, &blocking))
16393 return NULL;
16394
16395 if (!_PyVerify_fd(fd))
16396 return posix_error();
16397
16398 if (_Py_set_blocking(fd, blocking) < 0)
16399 return NULL;
16400 Py_RETURN_NONE;
16401}
16402#endif /* !MS_WINDOWS */
16403
16404
Larry Hastings7726ac92014-01-31 22:03:12 -080016405/*[clinic input]
16406dump buffer
16407[clinic start generated code]*/
16408
16409#ifndef OS_TTYNAME_METHODDEF
16410 #define OS_TTYNAME_METHODDEF
16411#endif /* !defined(OS_TTYNAME_METHODDEF) */
Larry Hastings2f936352014-08-05 14:04:04 +100016412
16413#ifndef OS_CTERMID_METHODDEF
16414 #define OS_CTERMID_METHODDEF
16415#endif /* !defined(OS_CTERMID_METHODDEF) */
16416
16417#ifndef OS_FCHDIR_METHODDEF
16418 #define OS_FCHDIR_METHODDEF
16419#endif /* !defined(OS_FCHDIR_METHODDEF) */
16420
16421#ifndef OS_FCHMOD_METHODDEF
16422 #define OS_FCHMOD_METHODDEF
16423#endif /* !defined(OS_FCHMOD_METHODDEF) */
16424
16425#ifndef OS_LCHMOD_METHODDEF
16426 #define OS_LCHMOD_METHODDEF
16427#endif /* !defined(OS_LCHMOD_METHODDEF) */
16428
16429#ifndef OS_CHFLAGS_METHODDEF
16430 #define OS_CHFLAGS_METHODDEF
16431#endif /* !defined(OS_CHFLAGS_METHODDEF) */
16432
16433#ifndef OS_LCHFLAGS_METHODDEF
16434 #define OS_LCHFLAGS_METHODDEF
16435#endif /* !defined(OS_LCHFLAGS_METHODDEF) */
16436
16437#ifndef OS_CHROOT_METHODDEF
16438 #define OS_CHROOT_METHODDEF
16439#endif /* !defined(OS_CHROOT_METHODDEF) */
16440
16441#ifndef OS_FSYNC_METHODDEF
16442 #define OS_FSYNC_METHODDEF
16443#endif /* !defined(OS_FSYNC_METHODDEF) */
16444
16445#ifndef OS_SYNC_METHODDEF
16446 #define OS_SYNC_METHODDEF
16447#endif /* !defined(OS_SYNC_METHODDEF) */
16448
16449#ifndef OS_FDATASYNC_METHODDEF
16450 #define OS_FDATASYNC_METHODDEF
16451#endif /* !defined(OS_FDATASYNC_METHODDEF) */
16452
16453#ifndef OS_CHOWN_METHODDEF
16454 #define OS_CHOWN_METHODDEF
16455#endif /* !defined(OS_CHOWN_METHODDEF) */
16456
16457#ifndef OS_FCHOWN_METHODDEF
16458 #define OS_FCHOWN_METHODDEF
16459#endif /* !defined(OS_FCHOWN_METHODDEF) */
16460
16461#ifndef OS_LCHOWN_METHODDEF
16462 #define OS_LCHOWN_METHODDEF
16463#endif /* !defined(OS_LCHOWN_METHODDEF) */
16464
16465#ifndef OS_LINK_METHODDEF
16466 #define OS_LINK_METHODDEF
16467#endif /* !defined(OS_LINK_METHODDEF) */
16468
16469#ifndef OS__GETFINALPATHNAME_METHODDEF
16470 #define OS__GETFINALPATHNAME_METHODDEF
16471#endif /* !defined(OS__GETFINALPATHNAME_METHODDEF) */
16472
16473#ifndef OS__GETVOLUMEPATHNAME_METHODDEF
16474 #define OS__GETVOLUMEPATHNAME_METHODDEF
16475#endif /* !defined(OS__GETVOLUMEPATHNAME_METHODDEF) */
16476
16477#ifndef OS_NICE_METHODDEF
16478 #define OS_NICE_METHODDEF
16479#endif /* !defined(OS_NICE_METHODDEF) */
16480
16481#ifndef OS_GETPRIORITY_METHODDEF
16482 #define OS_GETPRIORITY_METHODDEF
16483#endif /* !defined(OS_GETPRIORITY_METHODDEF) */
16484
16485#ifndef OS_SETPRIORITY_METHODDEF
16486 #define OS_SETPRIORITY_METHODDEF
16487#endif /* !defined(OS_SETPRIORITY_METHODDEF) */
16488
16489#ifndef OS_SYSTEM_METHODDEF
16490 #define OS_SYSTEM_METHODDEF
16491#endif /* !defined(OS_SYSTEM_METHODDEF) */
16492
16493#ifndef OS_SYSTEM_METHODDEF
16494 #define OS_SYSTEM_METHODDEF
16495#endif /* !defined(OS_SYSTEM_METHODDEF) */
16496
16497#ifndef OS_UNAME_METHODDEF
16498 #define OS_UNAME_METHODDEF
16499#endif /* !defined(OS_UNAME_METHODDEF) */
16500
16501#ifndef OS_EXECV_METHODDEF
16502 #define OS_EXECV_METHODDEF
16503#endif /* !defined(OS_EXECV_METHODDEF) */
16504
16505#ifndef OS_EXECVE_METHODDEF
16506 #define OS_EXECVE_METHODDEF
16507#endif /* !defined(OS_EXECVE_METHODDEF) */
16508
16509#ifndef OS_SPAWNV_METHODDEF
16510 #define OS_SPAWNV_METHODDEF
16511#endif /* !defined(OS_SPAWNV_METHODDEF) */
16512
16513#ifndef OS_SPAWNVE_METHODDEF
16514 #define OS_SPAWNVE_METHODDEF
16515#endif /* !defined(OS_SPAWNVE_METHODDEF) */
16516
16517#ifndef OS_FORK1_METHODDEF
16518 #define OS_FORK1_METHODDEF
16519#endif /* !defined(OS_FORK1_METHODDEF) */
16520
16521#ifndef OS_FORK_METHODDEF
16522 #define OS_FORK_METHODDEF
16523#endif /* !defined(OS_FORK_METHODDEF) */
16524
16525#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16526 #define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16527#endif /* !defined(OS_SCHED_GET_PRIORITY_MAX_METHODDEF) */
16528
16529#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16530 #define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16531#endif /* !defined(OS_SCHED_GET_PRIORITY_MIN_METHODDEF) */
16532
16533#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
16534 #define OS_SCHED_GETSCHEDULER_METHODDEF
16535#endif /* !defined(OS_SCHED_GETSCHEDULER_METHODDEF) */
16536
16537#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
16538 #define OS_SCHED_SETSCHEDULER_METHODDEF
16539#endif /* !defined(OS_SCHED_SETSCHEDULER_METHODDEF) */
16540
16541#ifndef OS_SCHED_GETPARAM_METHODDEF
16542 #define OS_SCHED_GETPARAM_METHODDEF
16543#endif /* !defined(OS_SCHED_GETPARAM_METHODDEF) */
16544
16545#ifndef OS_SCHED_SETPARAM_METHODDEF
16546 #define OS_SCHED_SETPARAM_METHODDEF
16547#endif /* !defined(OS_SCHED_SETPARAM_METHODDEF) */
16548
16549#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
16550 #define OS_SCHED_RR_GET_INTERVAL_METHODDEF
16551#endif /* !defined(OS_SCHED_RR_GET_INTERVAL_METHODDEF) */
16552
16553#ifndef OS_SCHED_YIELD_METHODDEF
16554 #define OS_SCHED_YIELD_METHODDEF
16555#endif /* !defined(OS_SCHED_YIELD_METHODDEF) */
16556
16557#ifndef OS_SCHED_SETAFFINITY_METHODDEF
16558 #define OS_SCHED_SETAFFINITY_METHODDEF
16559#endif /* !defined(OS_SCHED_SETAFFINITY_METHODDEF) */
16560
16561#ifndef OS_SCHED_GETAFFINITY_METHODDEF
16562 #define OS_SCHED_GETAFFINITY_METHODDEF
16563#endif /* !defined(OS_SCHED_GETAFFINITY_METHODDEF) */
16564
16565#ifndef OS_OPENPTY_METHODDEF
16566 #define OS_OPENPTY_METHODDEF
16567#endif /* !defined(OS_OPENPTY_METHODDEF) */
16568
16569#ifndef OS_FORKPTY_METHODDEF
16570 #define OS_FORKPTY_METHODDEF
16571#endif /* !defined(OS_FORKPTY_METHODDEF) */
16572
16573#ifndef OS_GETEGID_METHODDEF
16574 #define OS_GETEGID_METHODDEF
16575#endif /* !defined(OS_GETEGID_METHODDEF) */
16576
16577#ifndef OS_GETEUID_METHODDEF
16578 #define OS_GETEUID_METHODDEF
16579#endif /* !defined(OS_GETEUID_METHODDEF) */
16580
16581#ifndef OS_GETGID_METHODDEF
16582 #define OS_GETGID_METHODDEF
16583#endif /* !defined(OS_GETGID_METHODDEF) */
16584
16585#ifndef OS_GETGROUPS_METHODDEF
16586 #define OS_GETGROUPS_METHODDEF
16587#endif /* !defined(OS_GETGROUPS_METHODDEF) */
16588
16589#ifndef OS_GETPGID_METHODDEF
16590 #define OS_GETPGID_METHODDEF
16591#endif /* !defined(OS_GETPGID_METHODDEF) */
16592
16593#ifndef OS_GETPGRP_METHODDEF
16594 #define OS_GETPGRP_METHODDEF
16595#endif /* !defined(OS_GETPGRP_METHODDEF) */
16596
16597#ifndef OS_SETPGRP_METHODDEF
16598 #define OS_SETPGRP_METHODDEF
16599#endif /* !defined(OS_SETPGRP_METHODDEF) */
16600
16601#ifndef OS_GETPPID_METHODDEF
16602 #define OS_GETPPID_METHODDEF
16603#endif /* !defined(OS_GETPPID_METHODDEF) */
16604
16605#ifndef OS_GETLOGIN_METHODDEF
16606 #define OS_GETLOGIN_METHODDEF
16607#endif /* !defined(OS_GETLOGIN_METHODDEF) */
16608
16609#ifndef OS_GETUID_METHODDEF
16610 #define OS_GETUID_METHODDEF
16611#endif /* !defined(OS_GETUID_METHODDEF) */
16612
16613#ifndef OS_KILL_METHODDEF
16614 #define OS_KILL_METHODDEF
16615#endif /* !defined(OS_KILL_METHODDEF) */
16616
16617#ifndef OS_KILLPG_METHODDEF
16618 #define OS_KILLPG_METHODDEF
16619#endif /* !defined(OS_KILLPG_METHODDEF) */
16620
16621#ifndef OS_PLOCK_METHODDEF
16622 #define OS_PLOCK_METHODDEF
16623#endif /* !defined(OS_PLOCK_METHODDEF) */
16624
16625#ifndef OS_SETUID_METHODDEF
16626 #define OS_SETUID_METHODDEF
16627#endif /* !defined(OS_SETUID_METHODDEF) */
16628
16629#ifndef OS_SETEUID_METHODDEF
16630 #define OS_SETEUID_METHODDEF
16631#endif /* !defined(OS_SETEUID_METHODDEF) */
16632
16633#ifndef OS_SETEGID_METHODDEF
16634 #define OS_SETEGID_METHODDEF
16635#endif /* !defined(OS_SETEGID_METHODDEF) */
16636
16637#ifndef OS_SETREUID_METHODDEF
16638 #define OS_SETREUID_METHODDEF
16639#endif /* !defined(OS_SETREUID_METHODDEF) */
16640
16641#ifndef OS_SETREGID_METHODDEF
16642 #define OS_SETREGID_METHODDEF
16643#endif /* !defined(OS_SETREGID_METHODDEF) */
16644
16645#ifndef OS_SETGID_METHODDEF
16646 #define OS_SETGID_METHODDEF
16647#endif /* !defined(OS_SETGID_METHODDEF) */
16648
16649#ifndef OS_SETGROUPS_METHODDEF
16650 #define OS_SETGROUPS_METHODDEF
16651#endif /* !defined(OS_SETGROUPS_METHODDEF) */
16652
16653#ifndef OS_WAIT3_METHODDEF
16654 #define OS_WAIT3_METHODDEF
16655#endif /* !defined(OS_WAIT3_METHODDEF) */
16656
16657#ifndef OS_WAIT4_METHODDEF
16658 #define OS_WAIT4_METHODDEF
16659#endif /* !defined(OS_WAIT4_METHODDEF) */
16660
16661#ifndef OS_WAITID_METHODDEF
16662 #define OS_WAITID_METHODDEF
16663#endif /* !defined(OS_WAITID_METHODDEF) */
16664
16665#ifndef OS_WAITPID_METHODDEF
16666 #define OS_WAITPID_METHODDEF
16667#endif /* !defined(OS_WAITPID_METHODDEF) */
16668
16669#ifndef OS_WAITPID_METHODDEF
16670 #define OS_WAITPID_METHODDEF
16671#endif /* !defined(OS_WAITPID_METHODDEF) */
16672
16673#ifndef OS_WAIT_METHODDEF
16674 #define OS_WAIT_METHODDEF
16675#endif /* !defined(OS_WAIT_METHODDEF) */
16676
16677#ifndef OS_SYMLINK_METHODDEF
16678 #define OS_SYMLINK_METHODDEF
16679#endif /* !defined(OS_SYMLINK_METHODDEF) */
16680
16681#ifndef OS_TIMES_METHODDEF
16682 #define OS_TIMES_METHODDEF
16683#endif /* !defined(OS_TIMES_METHODDEF) */
16684
16685#ifndef OS_GETSID_METHODDEF
16686 #define OS_GETSID_METHODDEF
16687#endif /* !defined(OS_GETSID_METHODDEF) */
16688
16689#ifndef OS_SETSID_METHODDEF
16690 #define OS_SETSID_METHODDEF
16691#endif /* !defined(OS_SETSID_METHODDEF) */
16692
16693#ifndef OS_SETPGID_METHODDEF
16694 #define OS_SETPGID_METHODDEF
16695#endif /* !defined(OS_SETPGID_METHODDEF) */
16696
16697#ifndef OS_TCGETPGRP_METHODDEF
16698 #define OS_TCGETPGRP_METHODDEF
16699#endif /* !defined(OS_TCGETPGRP_METHODDEF) */
16700
16701#ifndef OS_TCSETPGRP_METHODDEF
16702 #define OS_TCSETPGRP_METHODDEF
16703#endif /* !defined(OS_TCSETPGRP_METHODDEF) */
16704
16705#ifndef OS_LOCKF_METHODDEF
16706 #define OS_LOCKF_METHODDEF
16707#endif /* !defined(OS_LOCKF_METHODDEF) */
16708
16709#ifndef OS_READV_METHODDEF
16710 #define OS_READV_METHODDEF
16711#endif /* !defined(OS_READV_METHODDEF) */
16712
16713#ifndef OS_PREAD_METHODDEF
16714 #define OS_PREAD_METHODDEF
16715#endif /* !defined(OS_PREAD_METHODDEF) */
16716
16717#ifndef OS_PIPE_METHODDEF
16718 #define OS_PIPE_METHODDEF
16719#endif /* !defined(OS_PIPE_METHODDEF) */
16720
16721#ifndef OS_PIPE2_METHODDEF
16722 #define OS_PIPE2_METHODDEF
16723#endif /* !defined(OS_PIPE2_METHODDEF) */
16724
16725#ifndef OS_WRITEV_METHODDEF
16726 #define OS_WRITEV_METHODDEF
16727#endif /* !defined(OS_WRITEV_METHODDEF) */
16728
16729#ifndef OS_PWRITE_METHODDEF
16730 #define OS_PWRITE_METHODDEF
16731#endif /* !defined(OS_PWRITE_METHODDEF) */
16732
16733#ifndef OS_MKFIFO_METHODDEF
16734 #define OS_MKFIFO_METHODDEF
16735#endif /* !defined(OS_MKFIFO_METHODDEF) */
16736
16737#ifndef OS_MKNOD_METHODDEF
16738 #define OS_MKNOD_METHODDEF
16739#endif /* !defined(OS_MKNOD_METHODDEF) */
16740
16741#ifndef OS_MAJOR_METHODDEF
16742 #define OS_MAJOR_METHODDEF
16743#endif /* !defined(OS_MAJOR_METHODDEF) */
16744
16745#ifndef OS_MINOR_METHODDEF
16746 #define OS_MINOR_METHODDEF
16747#endif /* !defined(OS_MINOR_METHODDEF) */
16748
16749#ifndef OS_MAKEDEV_METHODDEF
16750 #define OS_MAKEDEV_METHODDEF
16751#endif /* !defined(OS_MAKEDEV_METHODDEF) */
16752
16753#ifndef OS_FTRUNCATE_METHODDEF
16754 #define OS_FTRUNCATE_METHODDEF
16755#endif /* !defined(OS_FTRUNCATE_METHODDEF) */
16756
16757#ifndef OS_TRUNCATE_METHODDEF
16758 #define OS_TRUNCATE_METHODDEF
16759#endif /* !defined(OS_TRUNCATE_METHODDEF) */
16760
16761#ifndef OS_POSIX_FALLOCATE_METHODDEF
16762 #define OS_POSIX_FALLOCATE_METHODDEF
16763#endif /* !defined(OS_POSIX_FALLOCATE_METHODDEF) */
16764
16765#ifndef OS_POSIX_FADVISE_METHODDEF
16766 #define OS_POSIX_FADVISE_METHODDEF
16767#endif /* !defined(OS_POSIX_FADVISE_METHODDEF) */
16768
16769#ifndef OS_PUTENV_METHODDEF
16770 #define OS_PUTENV_METHODDEF
16771#endif /* !defined(OS_PUTENV_METHODDEF) */
16772
16773#ifndef OS_PUTENV_METHODDEF
16774 #define OS_PUTENV_METHODDEF
16775#endif /* !defined(OS_PUTENV_METHODDEF) */
16776
16777#ifndef OS_UNSETENV_METHODDEF
16778 #define OS_UNSETENV_METHODDEF
16779#endif /* !defined(OS_UNSETENV_METHODDEF) */
16780
16781#ifndef OS_WCOREDUMP_METHODDEF
16782 #define OS_WCOREDUMP_METHODDEF
16783#endif /* !defined(OS_WCOREDUMP_METHODDEF) */
16784
16785#ifndef OS_WIFCONTINUED_METHODDEF
16786 #define OS_WIFCONTINUED_METHODDEF
16787#endif /* !defined(OS_WIFCONTINUED_METHODDEF) */
16788
16789#ifndef OS_WIFSTOPPED_METHODDEF
16790 #define OS_WIFSTOPPED_METHODDEF
16791#endif /* !defined(OS_WIFSTOPPED_METHODDEF) */
16792
16793#ifndef OS_WIFSIGNALED_METHODDEF
16794 #define OS_WIFSIGNALED_METHODDEF
16795#endif /* !defined(OS_WIFSIGNALED_METHODDEF) */
16796
16797#ifndef OS_WIFEXITED_METHODDEF
16798 #define OS_WIFEXITED_METHODDEF
16799#endif /* !defined(OS_WIFEXITED_METHODDEF) */
16800
16801#ifndef OS_WEXITSTATUS_METHODDEF
16802 #define OS_WEXITSTATUS_METHODDEF
16803#endif /* !defined(OS_WEXITSTATUS_METHODDEF) */
16804
16805#ifndef OS_WTERMSIG_METHODDEF
16806 #define OS_WTERMSIG_METHODDEF
16807#endif /* !defined(OS_WTERMSIG_METHODDEF) */
16808
16809#ifndef OS_WSTOPSIG_METHODDEF
16810 #define OS_WSTOPSIG_METHODDEF
16811#endif /* !defined(OS_WSTOPSIG_METHODDEF) */
16812
16813#ifndef OS_FSTATVFS_METHODDEF
16814 #define OS_FSTATVFS_METHODDEF
16815#endif /* !defined(OS_FSTATVFS_METHODDEF) */
16816
16817#ifndef OS_STATVFS_METHODDEF
16818 #define OS_STATVFS_METHODDEF
16819#endif /* !defined(OS_STATVFS_METHODDEF) */
16820
16821#ifndef OS__GETDISKUSAGE_METHODDEF
16822 #define OS__GETDISKUSAGE_METHODDEF
16823#endif /* !defined(OS__GETDISKUSAGE_METHODDEF) */
16824
16825#ifndef OS_FPATHCONF_METHODDEF
16826 #define OS_FPATHCONF_METHODDEF
16827#endif /* !defined(OS_FPATHCONF_METHODDEF) */
16828
16829#ifndef OS_PATHCONF_METHODDEF
16830 #define OS_PATHCONF_METHODDEF
16831#endif /* !defined(OS_PATHCONF_METHODDEF) */
16832
16833#ifndef OS_CONFSTR_METHODDEF
16834 #define OS_CONFSTR_METHODDEF
16835#endif /* !defined(OS_CONFSTR_METHODDEF) */
16836
16837#ifndef OS_SYSCONF_METHODDEF
16838 #define OS_SYSCONF_METHODDEF
16839#endif /* !defined(OS_SYSCONF_METHODDEF) */
16840
16841#ifndef OS_GETLOADAVG_METHODDEF
16842 #define OS_GETLOADAVG_METHODDEF
16843#endif /* !defined(OS_GETLOADAVG_METHODDEF) */
16844
16845#ifndef OS_SETRESUID_METHODDEF
16846 #define OS_SETRESUID_METHODDEF
16847#endif /* !defined(OS_SETRESUID_METHODDEF) */
16848
16849#ifndef OS_SETRESGID_METHODDEF
16850 #define OS_SETRESGID_METHODDEF
16851#endif /* !defined(OS_SETRESGID_METHODDEF) */
16852
16853#ifndef OS_GETRESUID_METHODDEF
16854 #define OS_GETRESUID_METHODDEF
16855#endif /* !defined(OS_GETRESUID_METHODDEF) */
16856
16857#ifndef OS_GETRESGID_METHODDEF
16858 #define OS_GETRESGID_METHODDEF
16859#endif /* !defined(OS_GETRESGID_METHODDEF) */
16860
16861#ifndef OS_GETXATTR_METHODDEF
16862 #define OS_GETXATTR_METHODDEF
16863#endif /* !defined(OS_GETXATTR_METHODDEF) */
16864
16865#ifndef OS_SETXATTR_METHODDEF
16866 #define OS_SETXATTR_METHODDEF
16867#endif /* !defined(OS_SETXATTR_METHODDEF) */
16868
16869#ifndef OS_REMOVEXATTR_METHODDEF
16870 #define OS_REMOVEXATTR_METHODDEF
16871#endif /* !defined(OS_REMOVEXATTR_METHODDEF) */
16872
16873#ifndef OS_LISTXATTR_METHODDEF
16874 #define OS_LISTXATTR_METHODDEF
16875#endif /* !defined(OS_LISTXATTR_METHODDEF) */
16876
16877#ifndef OS_GET_HANDLE_INHERITABLE_METHODDEF
16878 #define OS_GET_HANDLE_INHERITABLE_METHODDEF
16879#endif /* !defined(OS_GET_HANDLE_INHERITABLE_METHODDEF) */
16880
16881#ifndef OS_SET_HANDLE_INHERITABLE_METHODDEF
16882 #define OS_SET_HANDLE_INHERITABLE_METHODDEF
16883#endif /* !defined(OS_SET_HANDLE_INHERITABLE_METHODDEF) */
16884/*[clinic end generated code: output=52a6140b0b052ce6 input=524ce2e021e4eba6]*/
Larry Hastings7726ac92014-01-31 22:03:12 -080016885
Larry Hastings31826802013-10-19 00:09:25 -070016886
Fred Drake5ab8eaf1999-12-09 21:13:07 +000016887static PyMethodDef posix_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -070016888
16889 OS_STAT_METHODDEF
16890 OS_ACCESS_METHODDEF
16891 OS_TTYNAME_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100016892 OS_CHDIR_METHODDEF
16893 OS_CHFLAGS_METHODDEF
16894 OS_CHMOD_METHODDEF
16895 OS_FCHMOD_METHODDEF
16896 OS_LCHMOD_METHODDEF
16897 OS_CHOWN_METHODDEF
16898 OS_FCHOWN_METHODDEF
16899 OS_LCHOWN_METHODDEF
16900 OS_LCHFLAGS_METHODDEF
16901 OS_CHROOT_METHODDEF
16902 OS_CTERMID_METHODDEF
16903 OS_GETCWD_METHODDEF
16904 OS_GETCWDB_METHODDEF
16905 OS_LINK_METHODDEF
16906 OS_LISTDIR_METHODDEF
16907 OS_LSTAT_METHODDEF
16908 OS_MKDIR_METHODDEF
16909 OS_NICE_METHODDEF
16910 OS_GETPRIORITY_METHODDEF
16911 OS_SETPRIORITY_METHODDEF
Guido van Rossumb6775db1994-08-01 11:34:53 +000016912#ifdef HAVE_READLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070016913 {"readlink", (PyCFunction)posix_readlink,
16914 METH_VARARGS | METH_KEYWORDS,
16915 readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000016916#endif /* HAVE_READLINK */
Brian Curtind40e6f72010-07-08 21:39:08 +000016917#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
Larry Hastings9cf065c2012-06-22 16:30:09 -070016918 {"readlink", (PyCFunction)win_readlink,
16919 METH_VARARGS | METH_KEYWORDS,
16920 readlink__doc__},
Brian Curtind40e6f72010-07-08 21:39:08 +000016921#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
Larry Hastings2f936352014-08-05 14:04:04 +100016922 OS_RENAME_METHODDEF
16923 OS_REPLACE_METHODDEF
16924 OS_RMDIR_METHODDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000016925 {"stat_float_times", stat_float_times, METH_VARARGS, stat_float_times__doc__},
Larry Hastings2f936352014-08-05 14:04:04 +100016926 OS_SYMLINK_METHODDEF
16927 OS_SYSTEM_METHODDEF
16928 OS_UMASK_METHODDEF
16929 OS_UNAME_METHODDEF
16930 OS_UNLINK_METHODDEF
16931 OS_REMOVE_METHODDEF
16932 OS_UTIME_METHODDEF
16933 OS_TIMES_METHODDEF
16934 OS__EXIT_METHODDEF
16935 OS_EXECV_METHODDEF
16936 OS_EXECVE_METHODDEF
16937 OS_SPAWNV_METHODDEF
16938 OS_SPAWNVE_METHODDEF
16939 OS_FORK1_METHODDEF
16940 OS_FORK_METHODDEF
16941 OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16942 OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16943 OS_SCHED_GETPARAM_METHODDEF
16944 OS_SCHED_GETSCHEDULER_METHODDEF
16945 OS_SCHED_RR_GET_INTERVAL_METHODDEF
16946 OS_SCHED_SETPARAM_METHODDEF
16947 OS_SCHED_SETSCHEDULER_METHODDEF
16948 OS_SCHED_YIELD_METHODDEF
16949 OS_SCHED_SETAFFINITY_METHODDEF
16950 OS_SCHED_GETAFFINITY_METHODDEF
16951 OS_OPENPTY_METHODDEF
16952 OS_FORKPTY_METHODDEF
16953 OS_GETEGID_METHODDEF
16954 OS_GETEUID_METHODDEF
16955 OS_GETGID_METHODDEF
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +020016956#ifdef HAVE_GETGROUPLIST
16957 {"getgrouplist", posix_getgrouplist, METH_VARARGS, posix_getgrouplist__doc__},
16958#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016959 OS_GETGROUPS_METHODDEF
16960 OS_GETPID_METHODDEF
16961 OS_GETPGRP_METHODDEF
16962 OS_GETPPID_METHODDEF
16963 OS_GETUID_METHODDEF
16964 OS_GETLOGIN_METHODDEF
16965 OS_KILL_METHODDEF
16966 OS_KILLPG_METHODDEF
16967 OS_PLOCK_METHODDEF
Thomas Heller8b7a9572007-08-31 06:44:36 +000016968#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000016969 {"startfile", win32_startfile, METH_VARARGS, win32_startfile__doc__},
Thomas Heller8b7a9572007-08-31 06:44:36 +000016970#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016971 OS_SETUID_METHODDEF
16972 OS_SETEUID_METHODDEF
16973 OS_SETREUID_METHODDEF
16974 OS_SETGID_METHODDEF
16975 OS_SETEGID_METHODDEF
16976 OS_SETREGID_METHODDEF
16977 OS_SETGROUPS_METHODDEF
Antoine Pitroub7572f02009-12-02 20:46:48 +000016978#ifdef HAVE_INITGROUPS
Victor Stinner8c62be82010-05-06 00:08:46 +000016979 {"initgroups", posix_initgroups, METH_VARARGS, posix_initgroups__doc__},
Antoine Pitroub7572f02009-12-02 20:46:48 +000016980#endif /* HAVE_INITGROUPS */
Larry Hastings2f936352014-08-05 14:04:04 +100016981 OS_GETPGID_METHODDEF
16982 OS_SETPGRP_METHODDEF
16983 OS_WAIT_METHODDEF
16984 OS_WAIT3_METHODDEF
16985 OS_WAIT4_METHODDEF
16986 OS_WAITID_METHODDEF
16987 OS_WAITPID_METHODDEF
16988 OS_GETSID_METHODDEF
16989 OS_SETSID_METHODDEF
16990 OS_SETPGID_METHODDEF
16991 OS_TCGETPGRP_METHODDEF
16992 OS_TCSETPGRP_METHODDEF
16993 OS_OPEN_METHODDEF
16994 OS_CLOSE_METHODDEF
16995 OS_CLOSERANGE_METHODDEF
16996 OS_DEVICE_ENCODING_METHODDEF
16997 OS_DUP_METHODDEF
16998 OS_DUP2_METHODDEF
16999 OS_LOCKF_METHODDEF
17000 OS_LSEEK_METHODDEF
17001 OS_READ_METHODDEF
17002 OS_READV_METHODDEF
17003 OS_PREAD_METHODDEF
17004 OS_WRITE_METHODDEF
17005 OS_WRITEV_METHODDEF
17006 OS_PWRITE_METHODDEF
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017007#ifdef HAVE_SENDFILE
17008 {"sendfile", (PyCFunction)posix_sendfile, METH_VARARGS | METH_KEYWORDS,
17009 posix_sendfile__doc__},
17010#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017011 OS_FSTAT_METHODDEF
17012 OS_ISATTY_METHODDEF
17013 OS_PIPE_METHODDEF
17014 OS_PIPE2_METHODDEF
17015 OS_MKFIFO_METHODDEF
17016 OS_MKNOD_METHODDEF
17017 OS_MAJOR_METHODDEF
17018 OS_MINOR_METHODDEF
17019 OS_MAKEDEV_METHODDEF
17020 OS_FTRUNCATE_METHODDEF
17021 OS_TRUNCATE_METHODDEF
17022 OS_POSIX_FALLOCATE_METHODDEF
17023 OS_POSIX_FADVISE_METHODDEF
17024 OS_PUTENV_METHODDEF
17025 OS_UNSETENV_METHODDEF
17026 OS_STRERROR_METHODDEF
17027 OS_FCHDIR_METHODDEF
17028 OS_FSYNC_METHODDEF
17029 OS_SYNC_METHODDEF
17030 OS_FDATASYNC_METHODDEF
17031 OS_WCOREDUMP_METHODDEF
17032 OS_WIFCONTINUED_METHODDEF
17033 OS_WIFSTOPPED_METHODDEF
17034 OS_WIFSIGNALED_METHODDEF
17035 OS_WIFEXITED_METHODDEF
17036 OS_WEXITSTATUS_METHODDEF
17037 OS_WTERMSIG_METHODDEF
17038 OS_WSTOPSIG_METHODDEF
17039 OS_FSTATVFS_METHODDEF
17040 OS_STATVFS_METHODDEF
17041 OS_CONFSTR_METHODDEF
17042 OS_SYSCONF_METHODDEF
17043 OS_FPATHCONF_METHODDEF
17044 OS_PATHCONF_METHODDEF
17045 OS_ABORT_METHODDEF
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000017046#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000017047 {"_getfullpathname", posix__getfullpathname, METH_VARARGS, NULL},
Brian Curtin95d028f2011-06-09 09:10:38 -050017048 {"_isdir", posix__isdir, METH_VARARGS, posix__isdir__doc__},
Mark Hammondef8b6542001-05-13 08:04:26 +000017049#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017050 OS__GETDISKUSAGE_METHODDEF
17051 OS__GETFINALPATHNAME_METHODDEF
17052 OS__GETVOLUMEPATHNAME_METHODDEF
17053 OS_GETLOADAVG_METHODDEF
17054 OS_URANDOM_METHODDEF
17055 OS_SETRESUID_METHODDEF
17056 OS_SETRESGID_METHODDEF
17057 OS_GETRESUID_METHODDEF
17058 OS_GETRESGID_METHODDEF
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000017059
Larry Hastings2f936352014-08-05 14:04:04 +100017060 OS_GETXATTR_METHODDEF
17061 OS_SETXATTR_METHODDEF
17062 OS_REMOVEXATTR_METHODDEF
17063 OS_LISTXATTR_METHODDEF
17064
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017065#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
17066 {"get_terminal_size", get_terminal_size, METH_VARARGS, termsize__doc__},
17067#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017068 OS_CPU_COUNT_METHODDEF
17069 OS_GET_INHERITABLE_METHODDEF
17070 OS_SET_INHERITABLE_METHODDEF
17071 OS_GET_HANDLE_INHERITABLE_METHODDEF
17072 OS_SET_HANDLE_INHERITABLE_METHODDEF
Victor Stinner1db9e7b2014-07-29 22:32:47 +020017073#ifndef MS_WINDOWS
17074 {"get_blocking", posix_get_blocking, METH_VARARGS, get_blocking__doc__},
17075 {"set_blocking", posix_set_blocking, METH_VARARGS, set_blocking__doc__},
17076#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017077 {NULL, NULL} /* Sentinel */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000017078};
17079
17080
Brian Curtin52173d42010-12-02 18:29:18 +000017081#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017082static int
Brian Curtin52173d42010-12-02 18:29:18 +000017083enable_symlink()
17084{
17085 HANDLE tok;
17086 TOKEN_PRIVILEGES tok_priv;
17087 LUID luid;
17088 int meth_idx = 0;
17089
17090 if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &tok))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017091 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017092
17093 if (!LookupPrivilegeValue(NULL, SE_CREATE_SYMBOLIC_LINK_NAME, &luid))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017094 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017095
17096 tok_priv.PrivilegeCount = 1;
17097 tok_priv.Privileges[0].Luid = luid;
17098 tok_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
17099
17100 if (!AdjustTokenPrivileges(tok, FALSE, &tok_priv,
17101 sizeof(TOKEN_PRIVILEGES),
17102 (PTOKEN_PRIVILEGES) NULL, (PDWORD) NULL))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017103 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017104
Brian Curtin3b4499c2010-12-28 14:31:47 +000017105 /* ERROR_NOT_ALL_ASSIGNED returned when the privilege can't be assigned. */
17106 return GetLastError() == ERROR_NOT_ALL_ASSIGNED ? 0 : 1;
Brian Curtin52173d42010-12-02 18:29:18 +000017107}
17108#endif /* defined(HAVE_SYMLINK) && defined(MS_WINDOWS) */
17109
Barry Warsaw4a342091996-12-19 23:50:02 +000017110static int
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017111all_ins(PyObject *m)
Barry Warsaw4a342091996-12-19 23:50:02 +000017112{
Guido van Rossum94f6f721999-01-06 18:42:14 +000017113#ifdef F_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017114 if (PyModule_AddIntMacro(m, F_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017115#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017116#ifdef R_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017117 if (PyModule_AddIntMacro(m, R_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017118#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017119#ifdef W_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017120 if (PyModule_AddIntMacro(m, W_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017121#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017122#ifdef X_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017123 if (PyModule_AddIntMacro(m, X_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017124#endif
Fred Drakec9680921999-12-13 16:37:25 +000017125#ifdef NGROUPS_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017126 if (PyModule_AddIntMacro(m, NGROUPS_MAX)) return -1;
Fred Drakec9680921999-12-13 16:37:25 +000017127#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017128#ifdef TMP_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017129 if (PyModule_AddIntMacro(m, TMP_MAX)) return -1;
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017130#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017131#ifdef WCONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017132 if (PyModule_AddIntMacro(m, WCONTINUED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017133#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017134#ifdef WNOHANG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017135 if (PyModule_AddIntMacro(m, WNOHANG)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017136#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017137#ifdef WUNTRACED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017138 if (PyModule_AddIntMacro(m, WUNTRACED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017139#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017140#ifdef O_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017141 if (PyModule_AddIntMacro(m, O_RDONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017142#endif
17143#ifdef O_WRONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017144 if (PyModule_AddIntMacro(m, O_WRONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017145#endif
17146#ifdef O_RDWR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017147 if (PyModule_AddIntMacro(m, O_RDWR)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017148#endif
17149#ifdef O_NDELAY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017150 if (PyModule_AddIntMacro(m, O_NDELAY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017151#endif
17152#ifdef O_NONBLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017153 if (PyModule_AddIntMacro(m, O_NONBLOCK)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017154#endif
17155#ifdef O_APPEND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017156 if (PyModule_AddIntMacro(m, O_APPEND)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017157#endif
17158#ifdef O_DSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017159 if (PyModule_AddIntMacro(m, O_DSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017160#endif
17161#ifdef O_RSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017162 if (PyModule_AddIntMacro(m, O_RSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017163#endif
17164#ifdef O_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017165 if (PyModule_AddIntMacro(m, O_SYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017166#endif
17167#ifdef O_NOCTTY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017168 if (PyModule_AddIntMacro(m, O_NOCTTY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017169#endif
17170#ifdef O_CREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017171 if (PyModule_AddIntMacro(m, O_CREAT)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017172#endif
17173#ifdef O_EXCL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017174 if (PyModule_AddIntMacro(m, O_EXCL)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017175#endif
17176#ifdef O_TRUNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017177 if (PyModule_AddIntMacro(m, O_TRUNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017178#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +000017179#ifdef O_BINARY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017180 if (PyModule_AddIntMacro(m, O_BINARY)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017181#endif
17182#ifdef O_TEXT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017183 if (PyModule_AddIntMacro(m, O_TEXT)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017184#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017185#ifdef O_XATTR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017186 if (PyModule_AddIntMacro(m, O_XATTR)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017187#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017188#ifdef O_LARGEFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017189 if (PyModule_AddIntMacro(m, O_LARGEFILE)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017190#endif
Skip Montanaro5ff14922005-05-16 02:42:22 +000017191#ifdef O_SHLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017192 if (PyModule_AddIntMacro(m, O_SHLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017193#endif
17194#ifdef O_EXLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017195 if (PyModule_AddIntMacro(m, O_EXLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017196#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017197#ifdef O_EXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017198 if (PyModule_AddIntMacro(m, O_EXEC)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017199#endif
17200#ifdef O_SEARCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017201 if (PyModule_AddIntMacro(m, O_SEARCH)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017202#endif
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017203#ifdef O_PATH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017204 if (PyModule_AddIntMacro(m, O_PATH)) return -1;
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017205#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017206#ifdef O_TTY_INIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017207 if (PyModule_AddIntMacro(m, O_TTY_INIT)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017208#endif
Christian Heimes177b3f92013-08-16 14:35:09 +020017209#ifdef O_TMPFILE
17210 if (PyModule_AddIntMacro(m, O_TMPFILE)) return -1;
17211#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017212#ifdef PRIO_PROCESS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017213 if (PyModule_AddIntMacro(m, PRIO_PROCESS)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017214#endif
17215#ifdef PRIO_PGRP
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017216 if (PyModule_AddIntMacro(m, PRIO_PGRP)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017217#endif
17218#ifdef PRIO_USER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017219 if (PyModule_AddIntMacro(m, PRIO_USER)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017220#endif
Charles-François Natali1e045b12011-05-22 20:42:32 +020017221#ifdef O_CLOEXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017222 if (PyModule_AddIntMacro(m, O_CLOEXEC)) return -1;
Charles-François Natali1e045b12011-05-22 20:42:32 +020017223#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017224#ifdef O_ACCMODE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017225 if (PyModule_AddIntMacro(m, O_ACCMODE)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017226#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017227
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017228
Jesus Cea94363612012-06-22 18:32:07 +020017229#ifdef SEEK_HOLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017230 if (PyModule_AddIntMacro(m, SEEK_HOLE)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017231#endif
17232#ifdef SEEK_DATA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017233 if (PyModule_AddIntMacro(m, SEEK_DATA)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017234#endif
17235
Tim Peters5aa91602002-01-30 05:46:57 +000017236/* MS Windows */
17237#ifdef O_NOINHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000017238 /* Don't inherit in child processes. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017239 if (PyModule_AddIntMacro(m, O_NOINHERIT)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017240#endif
17241#ifdef _O_SHORT_LIVED
Victor Stinner8c62be82010-05-06 00:08:46 +000017242 /* Optimize for short life (keep in memory). */
17243 /* MS forgot to define this one with a non-underscore form too. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017244 if (PyModule_AddIntConstant(m, "O_SHORT_LIVED", _O_SHORT_LIVED)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017245#endif
17246#ifdef O_TEMPORARY
Victor Stinner8c62be82010-05-06 00:08:46 +000017247 /* Automatically delete when last handle is closed. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017248 if (PyModule_AddIntMacro(m, O_TEMPORARY)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017249#endif
17250#ifdef O_RANDOM
Victor Stinner8c62be82010-05-06 00:08:46 +000017251 /* Optimize for random access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017252 if (PyModule_AddIntMacro(m, O_RANDOM)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017253#endif
17254#ifdef O_SEQUENTIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000017255 /* Optimize for sequential access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017256 if (PyModule_AddIntMacro(m, O_SEQUENTIAL)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017257#endif
17258
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017259/* GNU extensions. */
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017260#ifdef O_ASYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000017261 /* Send a SIGIO signal whenever input or output
17262 becomes available on file descriptor */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017263 if (PyModule_AddIntMacro(m, O_ASYNC)) return -1;
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017264#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017265#ifdef O_DIRECT
Victor Stinner8c62be82010-05-06 00:08:46 +000017266 /* Direct disk access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017267 if (PyModule_AddIntMacro(m, O_DIRECT)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017268#endif
17269#ifdef O_DIRECTORY
Victor Stinner8c62be82010-05-06 00:08:46 +000017270 /* Must be a directory. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017271 if (PyModule_AddIntMacro(m, O_DIRECTORY)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017272#endif
17273#ifdef O_NOFOLLOW
Victor Stinner8c62be82010-05-06 00:08:46 +000017274 /* Do not follow links. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017275 if (PyModule_AddIntMacro(m, O_NOFOLLOW)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017276#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017277#ifdef O_NOLINKS
17278 /* Fails if link count of the named file is greater than 1 */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017279 if (PyModule_AddIntMacro(m, O_NOLINKS)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017280#endif
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017281#ifdef O_NOATIME
Victor Stinner8c62be82010-05-06 00:08:46 +000017282 /* Do not update the access time. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017283 if (PyModule_AddIntMacro(m, O_NOATIME)) return -1;
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017284#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +000017285
Victor Stinner8c62be82010-05-06 00:08:46 +000017286 /* These come from sysexits.h */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017287#ifdef EX_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017288 if (PyModule_AddIntMacro(m, EX_OK)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017289#endif /* EX_OK */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017290#ifdef EX_USAGE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017291 if (PyModule_AddIntMacro(m, EX_USAGE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017292#endif /* EX_USAGE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017293#ifdef EX_DATAERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017294 if (PyModule_AddIntMacro(m, EX_DATAERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017295#endif /* EX_DATAERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017296#ifdef EX_NOINPUT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017297 if (PyModule_AddIntMacro(m, EX_NOINPUT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017298#endif /* EX_NOINPUT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017299#ifdef EX_NOUSER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017300 if (PyModule_AddIntMacro(m, EX_NOUSER)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017301#endif /* EX_NOUSER */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017302#ifdef EX_NOHOST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017303 if (PyModule_AddIntMacro(m, EX_NOHOST)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017304#endif /* EX_NOHOST */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017305#ifdef EX_UNAVAILABLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017306 if (PyModule_AddIntMacro(m, EX_UNAVAILABLE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017307#endif /* EX_UNAVAILABLE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017308#ifdef EX_SOFTWARE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017309 if (PyModule_AddIntMacro(m, EX_SOFTWARE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017310#endif /* EX_SOFTWARE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017311#ifdef EX_OSERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017312 if (PyModule_AddIntMacro(m, EX_OSERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017313#endif /* EX_OSERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017314#ifdef EX_OSFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017315 if (PyModule_AddIntMacro(m, EX_OSFILE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017316#endif /* EX_OSFILE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017317#ifdef EX_CANTCREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017318 if (PyModule_AddIntMacro(m, EX_CANTCREAT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017319#endif /* EX_CANTCREAT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017320#ifdef EX_IOERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017321 if (PyModule_AddIntMacro(m, EX_IOERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017322#endif /* EX_IOERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017323#ifdef EX_TEMPFAIL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017324 if (PyModule_AddIntMacro(m, EX_TEMPFAIL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017325#endif /* EX_TEMPFAIL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017326#ifdef EX_PROTOCOL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017327 if (PyModule_AddIntMacro(m, EX_PROTOCOL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017328#endif /* EX_PROTOCOL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017329#ifdef EX_NOPERM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017330 if (PyModule_AddIntMacro(m, EX_NOPERM)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017331#endif /* EX_NOPERM */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017332#ifdef EX_CONFIG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017333 if (PyModule_AddIntMacro(m, EX_CONFIG)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017334#endif /* EX_CONFIG */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017335#ifdef EX_NOTFOUND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017336 if (PyModule_AddIntMacro(m, EX_NOTFOUND)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017337#endif /* EX_NOTFOUND */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017338
Amaury Forgeot d'Arc66d00ad2010-09-10 18:11:45 +000017339 /* statvfs */
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017340#ifdef ST_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017341 if (PyModule_AddIntMacro(m, ST_RDONLY)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017342#endif /* ST_RDONLY */
17343#ifdef ST_NOSUID
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017344 if (PyModule_AddIntMacro(m, ST_NOSUID)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017345#endif /* ST_NOSUID */
17346
doko@ubuntu.comca616a22013-12-08 15:23:07 +010017347 /* GNU extensions */
17348#ifdef ST_NODEV
17349 if (PyModule_AddIntMacro(m, ST_NODEV)) return -1;
17350#endif /* ST_NODEV */
17351#ifdef ST_NOEXEC
17352 if (PyModule_AddIntMacro(m, ST_NOEXEC)) return -1;
17353#endif /* ST_NOEXEC */
17354#ifdef ST_SYNCHRONOUS
17355 if (PyModule_AddIntMacro(m, ST_SYNCHRONOUS)) return -1;
17356#endif /* ST_SYNCHRONOUS */
17357#ifdef ST_MANDLOCK
17358 if (PyModule_AddIntMacro(m, ST_MANDLOCK)) return -1;
17359#endif /* ST_MANDLOCK */
17360#ifdef ST_WRITE
17361 if (PyModule_AddIntMacro(m, ST_WRITE)) return -1;
17362#endif /* ST_WRITE */
17363#ifdef ST_APPEND
17364 if (PyModule_AddIntMacro(m, ST_APPEND)) return -1;
17365#endif /* ST_APPEND */
17366#ifdef ST_NOATIME
17367 if (PyModule_AddIntMacro(m, ST_NOATIME)) return -1;
17368#endif /* ST_NOATIME */
17369#ifdef ST_NODIRATIME
17370 if (PyModule_AddIntMacro(m, ST_NODIRATIME)) return -1;
17371#endif /* ST_NODIRATIME */
17372#ifdef ST_RELATIME
17373 if (PyModule_AddIntMacro(m, ST_RELATIME)) return -1;
17374#endif /* ST_RELATIME */
17375
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017376 /* FreeBSD sendfile() constants */
17377#ifdef SF_NODISKIO
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017378 if (PyModule_AddIntMacro(m, SF_NODISKIO)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017379#endif
17380#ifdef SF_MNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017381 if (PyModule_AddIntMacro(m, SF_MNOWAIT)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017382#endif
17383#ifdef SF_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017384 if (PyModule_AddIntMacro(m, SF_SYNC)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017385#endif
17386
Ross Lagerwall7807c352011-03-17 20:20:30 +020017387 /* constants for posix_fadvise */
17388#ifdef POSIX_FADV_NORMAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017389 if (PyModule_AddIntMacro(m, POSIX_FADV_NORMAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017390#endif
17391#ifdef POSIX_FADV_SEQUENTIAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017392 if (PyModule_AddIntMacro(m, POSIX_FADV_SEQUENTIAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017393#endif
17394#ifdef POSIX_FADV_RANDOM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017395 if (PyModule_AddIntMacro(m, POSIX_FADV_RANDOM)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017396#endif
17397#ifdef POSIX_FADV_NOREUSE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017398 if (PyModule_AddIntMacro(m, POSIX_FADV_NOREUSE)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017399#endif
17400#ifdef POSIX_FADV_WILLNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017401 if (PyModule_AddIntMacro(m, POSIX_FADV_WILLNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017402#endif
17403#ifdef POSIX_FADV_DONTNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017404 if (PyModule_AddIntMacro(m, POSIX_FADV_DONTNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017405#endif
17406
17407 /* constants for waitid */
17408#if defined(HAVE_SYS_WAIT_H) && defined(HAVE_WAITID)
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017409 if (PyModule_AddIntMacro(m, P_PID)) return -1;
17410 if (PyModule_AddIntMacro(m, P_PGID)) return -1;
17411 if (PyModule_AddIntMacro(m, P_ALL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017412#endif
17413#ifdef WEXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017414 if (PyModule_AddIntMacro(m, WEXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017415#endif
17416#ifdef WNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017417 if (PyModule_AddIntMacro(m, WNOWAIT)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017418#endif
17419#ifdef WSTOPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017420 if (PyModule_AddIntMacro(m, WSTOPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017421#endif
17422#ifdef CLD_EXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017423 if (PyModule_AddIntMacro(m, CLD_EXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017424#endif
17425#ifdef CLD_DUMPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017426 if (PyModule_AddIntMacro(m, CLD_DUMPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017427#endif
17428#ifdef CLD_TRAPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017429 if (PyModule_AddIntMacro(m, CLD_TRAPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017430#endif
17431#ifdef CLD_CONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017432 if (PyModule_AddIntMacro(m, CLD_CONTINUED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017433#endif
17434
17435 /* constants for lockf */
17436#ifdef F_LOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017437 if (PyModule_AddIntMacro(m, F_LOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017438#endif
17439#ifdef F_TLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017440 if (PyModule_AddIntMacro(m, F_TLOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017441#endif
17442#ifdef F_ULOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017443 if (PyModule_AddIntMacro(m, F_ULOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017444#endif
17445#ifdef F_TEST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017446 if (PyModule_AddIntMacro(m, F_TEST)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017447#endif
17448
Guido van Rossum246bc171999-02-01 23:54:31 +000017449#ifdef HAVE_SPAWNV
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017450 if (PyModule_AddIntConstant(m, "P_WAIT", _P_WAIT)) return -1;
17451 if (PyModule_AddIntConstant(m, "P_NOWAIT", _P_NOWAIT)) return -1;
17452 if (PyModule_AddIntConstant(m, "P_OVERLAY", _OLD_P_OVERLAY)) return -1;
17453 if (PyModule_AddIntConstant(m, "P_NOWAITO", _P_NOWAITO)) return -1;
17454 if (PyModule_AddIntConstant(m, "P_DETACH", _P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +000017455#endif
17456
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017457#ifdef HAVE_SCHED_H
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017458 if (PyModule_AddIntMacro(m, SCHED_OTHER)) return -1;
17459 if (PyModule_AddIntMacro(m, SCHED_FIFO)) return -1;
17460 if (PyModule_AddIntMacro(m, SCHED_RR)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017461#ifdef SCHED_SPORADIC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017462 if (PyModule_AddIntMacro(m, SCHED_SPORADIC) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017463#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017464#ifdef SCHED_BATCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017465 if (PyModule_AddIntMacro(m, SCHED_BATCH)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017466#endif
17467#ifdef SCHED_IDLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017468 if (PyModule_AddIntMacro(m, SCHED_IDLE)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017469#endif
17470#ifdef SCHED_RESET_ON_FORK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017471 if (PyModule_AddIntMacro(m, SCHED_RESET_ON_FORK)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017472#endif
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017473#ifdef SCHED_SYS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017474 if (PyModule_AddIntMacro(m, SCHED_SYS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017475#endif
17476#ifdef SCHED_IA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017477 if (PyModule_AddIntMacro(m, SCHED_IA)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017478#endif
17479#ifdef SCHED_FSS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017480 if (PyModule_AddIntMacro(m, SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017481#endif
17482#ifdef SCHED_FX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017483 if (PyModule_AddIntConstant(m, "SCHED_FX", SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017484#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017485#endif
17486
Benjamin Peterson9428d532011-09-14 11:45:52 -040017487#ifdef USE_XATTRS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017488 if (PyModule_AddIntMacro(m, XATTR_CREATE)) return -1;
17489 if (PyModule_AddIntMacro(m, XATTR_REPLACE)) return -1;
17490 if (PyModule_AddIntMacro(m, XATTR_SIZE_MAX)) return -1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040017491#endif
17492
Victor Stinner8b905bd2011-10-25 13:34:04 +020017493#ifdef RTLD_LAZY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017494 if (PyModule_AddIntMacro(m, RTLD_LAZY)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017495#endif
17496#ifdef RTLD_NOW
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017497 if (PyModule_AddIntMacro(m, RTLD_NOW)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017498#endif
17499#ifdef RTLD_GLOBAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017500 if (PyModule_AddIntMacro(m, RTLD_GLOBAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017501#endif
17502#ifdef RTLD_LOCAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017503 if (PyModule_AddIntMacro(m, RTLD_LOCAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017504#endif
17505#ifdef RTLD_NODELETE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017506 if (PyModule_AddIntMacro(m, RTLD_NODELETE)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017507#endif
17508#ifdef RTLD_NOLOAD
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017509 if (PyModule_AddIntMacro(m, RTLD_NOLOAD)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017510#endif
17511#ifdef RTLD_DEEPBIND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017512 if (PyModule_AddIntMacro(m, RTLD_DEEPBIND)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017513#endif
17514
Victor Stinner8c62be82010-05-06 00:08:46 +000017515 return 0;
Barry Warsaw4a342091996-12-19 23:50:02 +000017516}
17517
17518
Victor Stinnerd42c4282014-10-10 00:09:47 +020017519#ifdef MS_WINDOWS
Martin v. Löwis1a214512008-06-11 05:26:20 +000017520#define INITFUNC PyInit_nt
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017521#define MODNAME "nt"
Tim Peters58e0a8c2001-05-14 22:32:33 +000017522
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000017523#else
Martin v. Löwis1a214512008-06-11 05:26:20 +000017524#define INITFUNC PyInit_posix
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017525#define MODNAME "posix"
17526#endif
17527
Martin v. Löwis1a214512008-06-11 05:26:20 +000017528static struct PyModuleDef posixmodule = {
Victor Stinner8c62be82010-05-06 00:08:46 +000017529 PyModuleDef_HEAD_INIT,
17530 MODNAME,
17531 posix__doc__,
17532 -1,
17533 posix_methods,
17534 NULL,
17535 NULL,
17536 NULL,
17537 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +000017538};
17539
17540
Larry Hastings9cf065c2012-06-22 16:30:09 -070017541static char *have_functions[] = {
17542
17543#ifdef HAVE_FACCESSAT
17544 "HAVE_FACCESSAT",
17545#endif
17546
17547#ifdef HAVE_FCHDIR
17548 "HAVE_FCHDIR",
17549#endif
17550
17551#ifdef HAVE_FCHMOD
17552 "HAVE_FCHMOD",
17553#endif
17554
17555#ifdef HAVE_FCHMODAT
17556 "HAVE_FCHMODAT",
17557#endif
17558
17559#ifdef HAVE_FCHOWN
17560 "HAVE_FCHOWN",
17561#endif
17562
Larry Hastings00964ed2013-08-12 13:49:30 -040017563#ifdef HAVE_FCHOWNAT
17564 "HAVE_FCHOWNAT",
17565#endif
17566
Larry Hastings9cf065c2012-06-22 16:30:09 -070017567#ifdef HAVE_FEXECVE
17568 "HAVE_FEXECVE",
17569#endif
17570
17571#ifdef HAVE_FDOPENDIR
17572 "HAVE_FDOPENDIR",
17573#endif
17574
Georg Brandl306336b2012-06-24 12:55:33 +020017575#ifdef HAVE_FPATHCONF
17576 "HAVE_FPATHCONF",
17577#endif
17578
Larry Hastings9cf065c2012-06-22 16:30:09 -070017579#ifdef HAVE_FSTATAT
17580 "HAVE_FSTATAT",
17581#endif
17582
17583#ifdef HAVE_FSTATVFS
17584 "HAVE_FSTATVFS",
17585#endif
17586
Georg Brandl306336b2012-06-24 12:55:33 +020017587#ifdef HAVE_FTRUNCATE
17588 "HAVE_FTRUNCATE",
17589#endif
17590
Larry Hastings9cf065c2012-06-22 16:30:09 -070017591#ifdef HAVE_FUTIMENS
17592 "HAVE_FUTIMENS",
17593#endif
17594
17595#ifdef HAVE_FUTIMES
17596 "HAVE_FUTIMES",
17597#endif
17598
17599#ifdef HAVE_FUTIMESAT
17600 "HAVE_FUTIMESAT",
17601#endif
17602
17603#ifdef HAVE_LINKAT
17604 "HAVE_LINKAT",
17605#endif
17606
17607#ifdef HAVE_LCHFLAGS
17608 "HAVE_LCHFLAGS",
17609#endif
17610
17611#ifdef HAVE_LCHMOD
17612 "HAVE_LCHMOD",
17613#endif
17614
17615#ifdef HAVE_LCHOWN
17616 "HAVE_LCHOWN",
17617#endif
17618
17619#ifdef HAVE_LSTAT
17620 "HAVE_LSTAT",
17621#endif
17622
17623#ifdef HAVE_LUTIMES
17624 "HAVE_LUTIMES",
17625#endif
17626
17627#ifdef HAVE_MKDIRAT
17628 "HAVE_MKDIRAT",
17629#endif
17630
17631#ifdef HAVE_MKFIFOAT
17632 "HAVE_MKFIFOAT",
17633#endif
17634
17635#ifdef HAVE_MKNODAT
17636 "HAVE_MKNODAT",
17637#endif
17638
17639#ifdef HAVE_OPENAT
17640 "HAVE_OPENAT",
17641#endif
17642
17643#ifdef HAVE_READLINKAT
17644 "HAVE_READLINKAT",
17645#endif
17646
17647#ifdef HAVE_RENAMEAT
17648 "HAVE_RENAMEAT",
17649#endif
17650
17651#ifdef HAVE_SYMLINKAT
17652 "HAVE_SYMLINKAT",
17653#endif
17654
17655#ifdef HAVE_UNLINKAT
17656 "HAVE_UNLINKAT",
17657#endif
17658
17659#ifdef HAVE_UTIMENSAT
17660 "HAVE_UTIMENSAT",
17661#endif
17662
17663#ifdef MS_WINDOWS
17664 "MS_WINDOWS",
17665#endif
17666
17667 NULL
17668};
17669
17670
Mark Hammondfe51c6d2002-08-02 02:27:13 +000017671PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +000017672INITFUNC(void)
Guido van Rossumb6775db1994-08-01 11:34:53 +000017673{
Victor Stinner8c62be82010-05-06 00:08:46 +000017674 PyObject *m, *v;
Larry Hastings9cf065c2012-06-22 16:30:09 -070017675 PyObject *list;
17676 char **trace;
Tim Peters5aa91602002-01-30 05:46:57 +000017677
Brian Curtin52173d42010-12-02 18:29:18 +000017678#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017679 win32_can_symlink = enable_symlink();
Brian Curtin52173d42010-12-02 18:29:18 +000017680#endif
17681
Victor Stinner8c62be82010-05-06 00:08:46 +000017682 m = PyModule_Create(&posixmodule);
17683 if (m == NULL)
17684 return NULL;
Tim Peters5aa91602002-01-30 05:46:57 +000017685
Victor Stinner8c62be82010-05-06 00:08:46 +000017686 /* Initialize environ dictionary */
17687 v = convertenviron();
17688 Py_XINCREF(v);
17689 if (v == NULL || PyModule_AddObject(m, "environ", v) != 0)
17690 return NULL;
17691 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +000017692
Victor Stinner8c62be82010-05-06 00:08:46 +000017693 if (all_ins(m))
17694 return NULL;
Barry Warsaw4a342091996-12-19 23:50:02 +000017695
Victor Stinner8c62be82010-05-06 00:08:46 +000017696 if (setup_confname_tables(m))
17697 return NULL;
Fred Drakebec628d1999-12-15 18:31:10 +000017698
Victor Stinner8c62be82010-05-06 00:08:46 +000017699 Py_INCREF(PyExc_OSError);
17700 PyModule_AddObject(m, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +000017701
Guido van Rossumb3d39562000-01-31 18:41:26 +000017702#ifdef HAVE_PUTENV
Victor Stinner8c62be82010-05-06 00:08:46 +000017703 if (posix_putenv_garbage == NULL)
17704 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +000017705#endif
Guido van Rossum98bf58f2001-10-18 20:34:25 +000017706
Victor Stinner8c62be82010-05-06 00:08:46 +000017707 if (!initialized) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020017708#if defined(HAVE_WAITID) && !defined(__APPLE__)
17709 waitid_result_desc.name = MODNAME ".waitid_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017710 if (PyStructSequence_InitType2(&WaitidResultType, &waitid_result_desc) < 0)
17711 return NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017712#endif
17713
Christian Heimes25827622013-10-12 01:27:08 +020017714 stat_result_desc.name = "os.stat_result"; /* see issue #19209 */
Victor Stinner8c62be82010-05-06 00:08:46 +000017715 stat_result_desc.fields[7].name = PyStructSequence_UnnamedField;
17716 stat_result_desc.fields[8].name = PyStructSequence_UnnamedField;
17717 stat_result_desc.fields[9].name = PyStructSequence_UnnamedField;
Victor Stinner1c8f0592013-07-22 22:24:54 +020017718 if (PyStructSequence_InitType2(&StatResultType, &stat_result_desc) < 0)
17719 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017720 structseq_new = StatResultType.tp_new;
17721 StatResultType.tp_new = statresult_new;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017722
Christian Heimes25827622013-10-12 01:27:08 +020017723 statvfs_result_desc.name = "os.statvfs_result"; /* see issue #19209 */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017724 if (PyStructSequence_InitType2(&StatVFSResultType,
17725 &statvfs_result_desc) < 0)
17726 return NULL;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017727#ifdef NEED_TICKS_PER_SECOND
17728# if defined(HAVE_SYSCONF) && defined(_SC_CLK_TCK)
Victor Stinner8c62be82010-05-06 00:08:46 +000017729 ticks_per_second = sysconf(_SC_CLK_TCK);
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017730# elif defined(HZ)
Victor Stinner8c62be82010-05-06 00:08:46 +000017731 ticks_per_second = HZ;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017732# else
Victor Stinner8c62be82010-05-06 00:08:46 +000017733 ticks_per_second = 60; /* magic fallback value; may be bogus */
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017734# endif
17735#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017736
Benjamin Peterson0163c9a2011-08-02 18:11:38 -050017737#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017738 sched_param_desc.name = MODNAME ".sched_param";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017739 if (PyStructSequence_InitType2(&SchedParamType, &sched_param_desc) < 0)
17740 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100017741 SchedParamType.tp_new = os_sched_param;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017742#endif
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017743
17744 /* initialize TerminalSize_info */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017745 if (PyStructSequence_InitType2(&TerminalSizeType,
17746 &TerminalSize_desc) < 0)
17747 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017748 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020017749#if defined(HAVE_WAITID) && !defined(__APPLE__)
17750 Py_INCREF((PyObject*) &WaitidResultType);
17751 PyModule_AddObject(m, "waitid_result", (PyObject*) &WaitidResultType);
17752#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017753 Py_INCREF((PyObject*) &StatResultType);
17754 PyModule_AddObject(m, "stat_result", (PyObject*) &StatResultType);
17755 Py_INCREF((PyObject*) &StatVFSResultType);
17756 PyModule_AddObject(m, "statvfs_result",
17757 (PyObject*) &StatVFSResultType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017758
17759#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017760 Py_INCREF(&SchedParamType);
17761 PyModule_AddObject(m, "sched_param", (PyObject *)&SchedParamType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017762#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +000017763
Larry Hastings605a62d2012-06-24 04:33:36 -070017764 times_result_desc.name = MODNAME ".times_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017765 if (PyStructSequence_InitType2(&TimesResultType, &times_result_desc) < 0)
17766 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017767 PyModule_AddObject(m, "times_result", (PyObject *)&TimesResultType);
17768
17769 uname_result_desc.name = MODNAME ".uname_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017770 if (PyStructSequence_InitType2(&UnameResultType, &uname_result_desc) < 0)
17771 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017772 PyModule_AddObject(m, "uname_result", (PyObject *)&UnameResultType);
17773
Thomas Wouters477c8d52006-05-27 19:21:47 +000017774#ifdef __APPLE__
Victor Stinner8c62be82010-05-06 00:08:46 +000017775 /*
17776 * Step 2 of weak-linking support on Mac OS X.
17777 *
17778 * The code below removes functions that are not available on the
17779 * currently active platform.
17780 *
17781 * This block allow one to use a python binary that was build on
Larry Hastings9cf065c2012-06-22 16:30:09 -070017782 * OSX 10.4 on OSX 10.3, without losing access to new APIs on
Victor Stinner8c62be82010-05-06 00:08:46 +000017783 * OSX 10.4.
17784 */
Thomas Wouters477c8d52006-05-27 19:21:47 +000017785#ifdef HAVE_FSTATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017786 if (fstatvfs == NULL) {
17787 if (PyObject_DelAttrString(m, "fstatvfs") == -1) {
17788 return NULL;
17789 }
17790 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017791#endif /* HAVE_FSTATVFS */
17792
17793#ifdef HAVE_STATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017794 if (statvfs == NULL) {
17795 if (PyObject_DelAttrString(m, "statvfs") == -1) {
17796 return NULL;
17797 }
17798 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017799#endif /* HAVE_STATVFS */
17800
17801# ifdef HAVE_LCHOWN
Victor Stinner8c62be82010-05-06 00:08:46 +000017802 if (lchown == NULL) {
17803 if (PyObject_DelAttrString(m, "lchown") == -1) {
17804 return NULL;
17805 }
17806 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017807#endif /* HAVE_LCHOWN */
17808
17809
17810#endif /* __APPLE__ */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017811
Antoine Pitrou9d20e0e2012-09-12 18:01:36 +020017812 Py_INCREF(&TerminalSizeType);
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017813 PyModule_AddObject(m, "terminal_size", (PyObject*) &TerminalSizeType);
17814
Larry Hastings6fe20b32012-04-19 15:07:49 -070017815 billion = PyLong_FromLong(1000000000);
17816 if (!billion)
17817 return NULL;
17818
Larry Hastings9cf065c2012-06-22 16:30:09 -070017819 /* suppress "function not used" warnings */
17820 {
17821 int ignored;
17822 fd_specified("", -1);
17823 follow_symlinks_specified("", 1);
17824 dir_fd_and_follow_symlinks_invalid("chmod", DEFAULT_DIR_FD, 1);
17825 dir_fd_converter(Py_None, &ignored);
17826 dir_fd_unavailable(Py_None, &ignored);
17827 }
17828
17829 /*
17830 * provide list of locally available functions
17831 * so os.py can populate support_* lists
17832 */
17833 list = PyList_New(0);
17834 if (!list)
17835 return NULL;
17836 for (trace = have_functions; *trace; trace++) {
17837 PyObject *unicode = PyUnicode_DecodeASCII(*trace, strlen(*trace), NULL);
17838 if (!unicode)
17839 return NULL;
17840 if (PyList_Append(list, unicode))
17841 return NULL;
17842 Py_DECREF(unicode);
17843 }
17844 PyModule_AddObject(m, "_have_functions", list);
17845
17846 initialized = 1;
17847
Victor Stinner8c62be82010-05-06 00:08:46 +000017848 return m;
Guido van Rossumb6775db1994-08-01 11:34:53 +000017849}
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017850
17851#ifdef __cplusplus
17852}
17853#endif