blob: 0f0f1c3efe36b90fce4adbe3134438706d4cbee4 [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
Larry Hastings9cf065c2012-06-22 16:30:09 -0700620#ifdef AT_FDCWD
Trent Nelson9a461052012-09-18 21:50:06 -0400621/*
622 * Why the (int) cast? Solaris 10 defines AT_FDCWD as 0xffd19553 (-3041965);
623 * without the int cast, the value gets interpreted as uint (4291925331),
624 * which doesn't play nicely with all the initializer lines in this file that
625 * look like this:
626 * int dir_fd = DEFAULT_DIR_FD;
627 */
628#define DEFAULT_DIR_FD (int)AT_FDCWD
Larry Hastings9cf065c2012-06-22 16:30:09 -0700629#else
630#define DEFAULT_DIR_FD (-100)
631#endif
632
633static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200634_fd_converter(PyObject *o, int *p, const char *allowed)
635{
636 int overflow;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700637 long long_value;
638
639 PyObject *index = PyNumber_Index(o);
640 if (index == NULL) {
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200641 PyErr_Format(PyExc_TypeError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700642 "argument should be %s, not %.200s",
643 allowed, Py_TYPE(o)->tp_name);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700644 return 0;
645 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700646
647 long_value = PyLong_AsLongAndOverflow(index, &overflow);
648 Py_DECREF(index);
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200649 if (overflow > 0 || long_value > INT_MAX) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700650 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700651 "fd is greater than maximum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700652 return 0;
653 }
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200654 if (overflow < 0 || long_value < INT_MIN) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700655 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700656 "fd is less than minimum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700657 return 0;
658 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700659
Larry Hastings9cf065c2012-06-22 16:30:09 -0700660 *p = (int)long_value;
661 return 1;
662}
663
664static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200665dir_fd_converter(PyObject *o, void *p)
666{
667 if (o == Py_None) {
668 *(int *)p = DEFAULT_DIR_FD;
669 return 1;
670 }
671 return _fd_converter(o, (int *)p, "integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700672}
673
674
Larry Hastings9cf065c2012-06-22 16:30:09 -0700675/*
676 * A PyArg_ParseTuple "converter" function
677 * that handles filesystem paths in the manner
678 * preferred by the os module.
679 *
680 * path_converter accepts (Unicode) strings and their
681 * subclasses, and bytes and their subclasses. What
682 * it does with the argument depends on the platform:
683 *
684 * * On Windows, if we get a (Unicode) string we
685 * extract the wchar_t * and return it; if we get
686 * bytes we extract the char * and return that.
687 *
688 * * On all other platforms, strings are encoded
689 * to bytes using PyUnicode_FSConverter, then we
690 * extract the char * from the bytes object and
691 * return that.
692 *
693 * path_converter also optionally accepts signed
694 * integers (representing open file descriptors) instead
695 * of path strings.
696 *
697 * Input fields:
698 * path.nullable
699 * If nonzero, the path is permitted to be None.
700 * path.allow_fd
701 * If nonzero, the path is permitted to be a file handle
702 * (a signed int) instead of a string.
703 * path.function_name
704 * If non-NULL, path_converter will use that as the name
705 * of the function in error messages.
Larry Hastings31826802013-10-19 00:09:25 -0700706 * (If path.function_name is NULL it omits the function name.)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700707 * path.argument_name
708 * If non-NULL, path_converter will use that as the name
709 * of the parameter in error messages.
710 * (If path.argument_name is NULL it uses "path".)
711 *
712 * Output fields:
713 * path.wide
714 * Points to the path if it was expressed as Unicode
715 * and was not encoded. (Only used on Windows.)
716 * path.narrow
717 * Points to the path if it was expressed as bytes,
718 * or it was Unicode and was encoded to bytes.
719 * path.fd
720 * Contains a file descriptor if path.accept_fd was true
721 * and the caller provided a signed integer instead of any
722 * sort of string.
723 *
724 * WARNING: if your "path" parameter is optional, and is
725 * unspecified, path_converter will never get called.
726 * So if you set allow_fd, you *MUST* initialize path.fd = -1
727 * yourself!
728 * path.length
729 * The length of the path in characters, if specified as
730 * a string.
731 * path.object
732 * The original object passed in.
733 * path.cleanup
734 * For internal use only. May point to a temporary object.
735 * (Pay no attention to the man behind the curtain.)
736 *
737 * At most one of path.wide or path.narrow will be non-NULL.
738 * If path was None and path.nullable was set,
739 * or if path was an integer and path.allow_fd was set,
740 * both path.wide and path.narrow will be NULL
741 * and path.length will be 0.
Georg Brandlf7875592012-06-24 13:58:31 +0200742 *
Larry Hastings9cf065c2012-06-22 16:30:09 -0700743 * path_converter takes care to not write to the path_t
744 * unless it's successful. However it must reset the
745 * "cleanup" field each time it's called.
746 *
747 * Use as follows:
748 * path_t path;
749 * memset(&path, 0, sizeof(path));
750 * PyArg_ParseTuple(args, "O&", path_converter, &path);
751 * // ... use values from path ...
752 * path_cleanup(&path);
753 *
754 * (Note that if PyArg_Parse fails you don't need to call
755 * path_cleanup(). However it is safe to do so.)
756 */
757typedef struct {
Victor Stinner292c8352012-10-30 02:17:38 +0100758 const char *function_name;
759 const char *argument_name;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700760 int nullable;
761 int allow_fd;
762 wchar_t *wide;
763 char *narrow;
764 int fd;
765 Py_ssize_t length;
766 PyObject *object;
767 PyObject *cleanup;
768} path_t;
769
Larry Hastings2f936352014-08-05 14:04:04 +1000770#define PATH_T_INITIALIZE(function_name, argument_name, nullable, allow_fd) \
771 {function_name, argument_name, nullable, allow_fd, NULL, NULL, -1, 0, NULL, NULL}
Larry Hastings31826802013-10-19 00:09:25 -0700772
Larry Hastings9cf065c2012-06-22 16:30:09 -0700773static void
774path_cleanup(path_t *path) {
775 if (path->cleanup) {
Serhiy Storchaka505ff752014-02-09 13:33:53 +0200776 Py_CLEAR(path->cleanup);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700777 }
778}
779
780static int
781path_converter(PyObject *o, void *p) {
782 path_t *path = (path_t *)p;
783 PyObject *unicode, *bytes;
784 Py_ssize_t length;
785 char *narrow;
786
787#define FORMAT_EXCEPTION(exc, fmt) \
788 PyErr_Format(exc, "%s%s" fmt, \
789 path->function_name ? path->function_name : "", \
790 path->function_name ? ": " : "", \
791 path->argument_name ? path->argument_name : "path")
792
793 /* Py_CLEANUP_SUPPORTED support */
794 if (o == NULL) {
795 path_cleanup(path);
796 return 1;
797 }
798
799 /* ensure it's always safe to call path_cleanup() */
800 path->cleanup = NULL;
801
802 if (o == Py_None) {
803 if (!path->nullable) {
804 FORMAT_EXCEPTION(PyExc_TypeError,
805 "can't specify None for %s argument");
806 return 0;
807 }
808 path->wide = NULL;
809 path->narrow = NULL;
810 path->length = 0;
811 path->object = o;
812 path->fd = -1;
813 return 1;
814 }
815
816 unicode = PyUnicode_FromObject(o);
817 if (unicode) {
818#ifdef MS_WINDOWS
819 wchar_t *wide;
Victor Stinner59799a82013-11-13 14:17:30 +0100820
821 wide = PyUnicode_AsUnicodeAndSize(unicode, &length);
822 if (!wide) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700823 Py_DECREF(unicode);
824 return 0;
825 }
Victor Stinner59799a82013-11-13 14:17:30 +0100826 if (length > 32767) {
827 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700828 Py_DECREF(unicode);
829 return 0;
830 }
831
832 path->wide = wide;
833 path->narrow = NULL;
834 path->length = length;
835 path->object = o;
836 path->fd = -1;
837 path->cleanup = unicode;
838 return Py_CLEANUP_SUPPORTED;
839#else
840 int converted = PyUnicode_FSConverter(unicode, &bytes);
841 Py_DECREF(unicode);
842 if (!converted)
843 bytes = NULL;
844#endif
845 }
846 else {
847 PyErr_Clear();
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200848 if (PyObject_CheckBuffer(o))
849 bytes = PyBytes_FromObject(o);
850 else
851 bytes = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700852 if (!bytes) {
853 PyErr_Clear();
854 if (path->allow_fd) {
855 int fd;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200856 int result = _fd_converter(o, &fd,
857 "string, bytes or integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700858 if (result) {
859 path->wide = NULL;
860 path->narrow = NULL;
861 path->length = 0;
862 path->object = o;
863 path->fd = fd;
864 return result;
865 }
866 }
867 }
868 }
869
870 if (!bytes) {
871 if (!PyErr_Occurred())
872 FORMAT_EXCEPTION(PyExc_TypeError, "illegal type for %s parameter");
873 return 0;
874 }
875
876#ifdef MS_WINDOWS
877 if (win32_warn_bytes_api()) {
878 Py_DECREF(bytes);
879 return 0;
880 }
881#endif
882
883 length = PyBytes_GET_SIZE(bytes);
884#ifdef MS_WINDOWS
Victor Stinner75875072013-11-24 19:23:25 +0100885 if (length > MAX_PATH-1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700886 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
887 Py_DECREF(bytes);
888 return 0;
889 }
890#endif
891
892 narrow = PyBytes_AS_STRING(bytes);
Victor Stinner706768c2014-08-16 01:03:39 +0200893 if ((size_t)length != strlen(narrow)) {
Serhiy Storchakad8a14472014-09-06 20:07:17 +0300894 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700895 Py_DECREF(bytes);
896 return 0;
897 }
898
899 path->wide = NULL;
900 path->narrow = narrow;
901 path->length = length;
902 path->object = o;
903 path->fd = -1;
904 path->cleanup = bytes;
905 return Py_CLEANUP_SUPPORTED;
906}
907
908static void
909argument_unavailable_error(char *function_name, char *argument_name) {
910 PyErr_Format(PyExc_NotImplementedError,
911 "%s%s%s unavailable on this platform",
912 (function_name != NULL) ? function_name : "",
913 (function_name != NULL) ? ": ": "",
914 argument_name);
915}
916
917static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200918dir_fd_unavailable(PyObject *o, void *p)
919{
920 int dir_fd;
921 if (!dir_fd_converter(o, &dir_fd))
Larry Hastings9cf065c2012-06-22 16:30:09 -0700922 return 0;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200923 if (dir_fd != DEFAULT_DIR_FD) {
924 argument_unavailable_error(NULL, "dir_fd");
925 return 0;
926 }
927 *(int *)p = dir_fd;
928 return 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700929}
930
931static int
932fd_specified(char *function_name, int fd) {
933 if (fd == -1)
934 return 0;
935
936 argument_unavailable_error(function_name, "fd");
937 return 1;
938}
939
940static int
941follow_symlinks_specified(char *function_name, int follow_symlinks) {
942 if (follow_symlinks)
943 return 0;
944
945 argument_unavailable_error(function_name, "follow_symlinks");
946 return 1;
947}
948
949static int
950path_and_dir_fd_invalid(char *function_name, path_t *path, int dir_fd) {
951 if (!path->narrow && !path->wide && (dir_fd != DEFAULT_DIR_FD)) {
952 PyErr_Format(PyExc_ValueError,
953 "%s: can't specify dir_fd without matching path",
954 function_name);
955 return 1;
956 }
957 return 0;
958}
959
960static int
961dir_fd_and_fd_invalid(char *function_name, int dir_fd, int fd) {
962 if ((dir_fd != DEFAULT_DIR_FD) && (fd != -1)) {
963 PyErr_Format(PyExc_ValueError,
964 "%s: can't specify both dir_fd and fd",
965 function_name);
966 return 1;
967 }
968 return 0;
969}
970
971static int
972fd_and_follow_symlinks_invalid(char *function_name, int fd,
973 int follow_symlinks) {
974 if ((fd > 0) && (!follow_symlinks)) {
975 PyErr_Format(PyExc_ValueError,
976 "%s: cannot use fd and follow_symlinks together",
977 function_name);
978 return 1;
979 }
980 return 0;
981}
982
983static int
984dir_fd_and_follow_symlinks_invalid(char *function_name, int dir_fd,
985 int follow_symlinks) {
986 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
987 PyErr_Format(PyExc_ValueError,
988 "%s: cannot use dir_fd and follow_symlinks together",
989 function_name);
990 return 1;
991 }
992 return 0;
993}
994
Larry Hastings2f936352014-08-05 14:04:04 +1000995#ifdef MS_WINDOWS
996 typedef PY_LONG_LONG Py_off_t;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000997#else
Larry Hastings2f936352014-08-05 14:04:04 +1000998 typedef off_t Py_off_t;
999#endif
1000
1001static int
1002Py_off_t_converter(PyObject *arg, void *addr)
1003{
1004#ifdef HAVE_LARGEFILE_SUPPORT
1005 *((Py_off_t *)addr) = PyLong_AsLongLong(arg);
1006#else
1007 *((Py_off_t *)addr) = PyLong_AsLong(arg);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001008#endif
1009 if (PyErr_Occurred())
1010 return 0;
1011 return 1;
1012}
Larry Hastings2f936352014-08-05 14:04:04 +10001013
1014static PyObject *
1015PyLong_FromPy_off_t(Py_off_t offset)
1016{
1017#ifdef HAVE_LARGEFILE_SUPPORT
1018 return PyLong_FromLongLong(offset);
1019#else
1020 return PyLong_FromLong(offset);
Ross Lagerwallb1e5d592011-09-19 08:30:43 +02001021#endif
Larry Hastings2f936352014-08-05 14:04:04 +10001022}
1023
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001024
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001025#if defined _MSC_VER && _MSC_VER >= 1400
1026/* Microsoft CRT in VS2005 and higher will verify that a filehandle is
Andrew Svetlov737fb892012-12-18 21:14:22 +02001027 * valid and raise an assertion if it isn't.
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001028 * Normally, an invalid fd is likely to be a C program error and therefore
1029 * an assertion can be useful, but it does contradict the POSIX standard
1030 * which for write(2) states:
1031 * "Otherwise, -1 shall be returned and errno set to indicate the error."
1032 * "[EBADF] The fildes argument is not a valid file descriptor open for
1033 * writing."
1034 * Furthermore, python allows the user to enter any old integer
1035 * as a fd and should merely raise a python exception on error.
1036 * The Microsoft CRT doesn't provide an official way to check for the
1037 * validity of a file descriptor, but we can emulate its internal behaviour
Victor Stinner8c62be82010-05-06 00:08:46 +00001038 * by using the exported __pinfo data member and knowledge of the
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001039 * internal structures involved.
1040 * The structures below must be updated for each version of visual studio
1041 * according to the file internal.h in the CRT source, until MS comes
1042 * up with a less hacky way to do this.
1043 * (all of this is to avoid globally modifying the CRT behaviour using
1044 * _set_invalid_parameter_handler() and _CrtSetReportMode())
1045 */
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001046/* The actual size of the structure is determined at runtime.
1047 * Only the first items must be present.
1048 */
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001049typedef struct {
Victor Stinner8c62be82010-05-06 00:08:46 +00001050 intptr_t osfhnd;
1051 char osfile;
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001052} my_ioinfo;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001053
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001054extern __declspec(dllimport) char * __pioinfo[];
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001055#define IOINFO_L2E 5
1056#define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
1057#define IOINFO_ARRAYS 64
1058#define _NHANDLE_ (IOINFO_ARRAYS * IOINFO_ARRAY_ELTS)
1059#define FOPEN 0x01
1060#define _NO_CONSOLE_FILENO (intptr_t)-2
1061
1062/* This function emulates what the windows CRT does to validate file handles */
1063int
1064_PyVerify_fd(int fd)
1065{
Victor Stinner8c62be82010-05-06 00:08:46 +00001066 const int i1 = fd >> IOINFO_L2E;
1067 const int i2 = fd & ((1 << IOINFO_L2E) - 1);
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001068
Antoine Pitrou22e41552010-08-15 18:07:50 +00001069 static size_t sizeof_ioinfo = 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001070
Victor Stinner8c62be82010-05-06 00:08:46 +00001071 /* Determine the actual size of the ioinfo structure,
1072 * as used by the CRT loaded in memory
1073 */
1074 if (sizeof_ioinfo == 0 && __pioinfo[0] != NULL) {
1075 sizeof_ioinfo = _msize(__pioinfo[0]) / IOINFO_ARRAY_ELTS;
1076 }
1077 if (sizeof_ioinfo == 0) {
1078 /* This should not happen... */
1079 goto fail;
1080 }
1081
1082 /* See that it isn't a special CLEAR fileno */
1083 if (fd != _NO_CONSOLE_FILENO) {
1084 /* Microsoft CRT would check that 0<=fd<_nhandle but we can't do that. Instead
1085 * we check pointer validity and other info
1086 */
1087 if (0 <= i1 && i1 < IOINFO_ARRAYS && __pioinfo[i1] != NULL) {
1088 /* finally, check that the file is open */
1089 my_ioinfo* info = (my_ioinfo*)(__pioinfo[i1] + i2 * sizeof_ioinfo);
1090 if (info->osfile & FOPEN) {
1091 return 1;
1092 }
1093 }
1094 }
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +00001095 fail:
Victor Stinner8c62be82010-05-06 00:08:46 +00001096 errno = EBADF;
1097 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001098}
1099
1100/* the special case of checking dup2. The target fd must be in a sensible range */
1101static int
1102_PyVerify_fd_dup2(int fd1, int fd2)
1103{
Victor Stinner8c62be82010-05-06 00:08:46 +00001104 if (!_PyVerify_fd(fd1))
1105 return 0;
1106 if (fd2 == _NO_CONSOLE_FILENO)
1107 return 0;
1108 if ((unsigned)fd2 < _NHANDLE_)
1109 return 1;
1110 else
1111 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001112}
1113#else
1114/* dummy version. _PyVerify_fd() is already defined in fileobject.h */
1115#define _PyVerify_fd_dup2(A, B) (1)
1116#endif
1117
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001118#ifdef MS_WINDOWS
Brian Curtinf5e76d02010-11-24 13:14:05 +00001119
1120static int
Brian Curtind25aef52011-06-13 15:16:04 -05001121win32_get_reparse_tag(HANDLE reparse_point_handle, ULONG *reparse_tag)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001122{
1123 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
1124 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
1125 DWORD n_bytes_returned;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001126
1127 if (0 == DeviceIoControl(
1128 reparse_point_handle,
1129 FSCTL_GET_REPARSE_POINT,
1130 NULL, 0, /* in buffer */
1131 target_buffer, sizeof(target_buffer),
1132 &n_bytes_returned,
1133 NULL)) /* we're not using OVERLAPPED_IO */
Brian Curtind25aef52011-06-13 15:16:04 -05001134 return FALSE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001135
1136 if (reparse_tag)
1137 *reparse_tag = rdb->ReparseTag;
1138
Brian Curtind25aef52011-06-13 15:16:04 -05001139 return TRUE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001140}
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001141
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001142#endif /* MS_WINDOWS */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001143
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001144/* Return a dictionary corresponding to the POSIX environment table */
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001145#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Jack Jansenea0c3822002-08-01 21:57:49 +00001146/* On Darwin/MacOSX a shared library or framework has no access to
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001147** environ directly, we must obtain it with _NSGetEnviron(). See also
1148** man environ(7).
Jack Jansenea0c3822002-08-01 21:57:49 +00001149*/
1150#include <crt_externs.h>
1151static char **environ;
1152#elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001153extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001154#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001155
Barry Warsaw53699e91996-12-10 23:23:01 +00001156static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001157convertenviron(void)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001158{
Victor Stinner8c62be82010-05-06 00:08:46 +00001159 PyObject *d;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001160#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00001161 wchar_t **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001162#else
Victor Stinner8c62be82010-05-06 00:08:46 +00001163 char **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001164#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00001165
Victor Stinner8c62be82010-05-06 00:08:46 +00001166 d = PyDict_New();
1167 if (d == NULL)
1168 return NULL;
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001169#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Victor Stinner8c62be82010-05-06 00:08:46 +00001170 if (environ == NULL)
1171 environ = *_NSGetEnviron();
1172#endif
1173#ifdef MS_WINDOWS
1174 /* _wenviron must be initialized in this way if the program is started
1175 through main() instead of wmain(). */
1176 _wgetenv(L"");
1177 if (_wenviron == NULL)
1178 return d;
1179 /* This part ignores errors */
1180 for (e = _wenviron; *e != NULL; e++) {
1181 PyObject *k;
1182 PyObject *v;
1183 wchar_t *p = wcschr(*e, L'=');
1184 if (p == NULL)
1185 continue;
1186 k = PyUnicode_FromWideChar(*e, (Py_ssize_t)(p-*e));
1187 if (k == NULL) {
1188 PyErr_Clear();
1189 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001190 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001191 v = PyUnicode_FromWideChar(p+1, wcslen(p+1));
1192 if (v == NULL) {
1193 PyErr_Clear();
1194 Py_DECREF(k);
1195 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001196 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001197 if (PyDict_GetItem(d, k) == NULL) {
1198 if (PyDict_SetItem(d, k, v) != 0)
1199 PyErr_Clear();
1200 }
1201 Py_DECREF(k);
1202 Py_DECREF(v);
1203 }
1204#else
1205 if (environ == NULL)
1206 return d;
1207 /* This part ignores errors */
1208 for (e = environ; *e != NULL; e++) {
1209 PyObject *k;
1210 PyObject *v;
1211 char *p = strchr(*e, '=');
1212 if (p == NULL)
1213 continue;
Victor Stinner84ae1182010-05-06 22:05:07 +00001214 k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
Victor Stinner8c62be82010-05-06 00:08:46 +00001215 if (k == NULL) {
1216 PyErr_Clear();
1217 continue;
1218 }
Victor Stinner84ae1182010-05-06 22:05:07 +00001219 v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
Victor Stinner8c62be82010-05-06 00:08:46 +00001220 if (v == NULL) {
1221 PyErr_Clear();
1222 Py_DECREF(k);
1223 continue;
1224 }
1225 if (PyDict_GetItem(d, k) == NULL) {
1226 if (PyDict_SetItem(d, k, v) != 0)
1227 PyErr_Clear();
1228 }
1229 Py_DECREF(k);
1230 Py_DECREF(v);
Guido van Rossumd48f2521997-12-05 22:19:34 +00001231 }
1232#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001233 return d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001234}
1235
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001236/* Set a POSIX-specific error from errno, and return NULL */
1237
Barry Warsawd58d7641998-07-23 16:14:40 +00001238static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001239posix_error(void)
Guido van Rossumad0ee831995-03-01 10:34:45 +00001240{
Victor Stinner8c62be82010-05-06 00:08:46 +00001241 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001242}
Mark Hammondef8b6542001-05-13 08:04:26 +00001243
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00001244#ifdef MS_WINDOWS
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001245static PyObject *
Brian Curtind40e6f72010-07-08 21:39:08 +00001246win32_error(char* function, const char* filename)
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001247{
Victor Stinner8c62be82010-05-06 00:08:46 +00001248 /* XXX We should pass the function name along in the future.
1249 (winreg.c also wants to pass the function name.)
1250 This would however require an additional param to the
1251 Windows error object, which is non-trivial.
1252 */
1253 errno = GetLastError();
1254 if (filename)
1255 return PyErr_SetFromWindowsErrWithFilename(errno, filename);
1256 else
1257 return PyErr_SetFromWindowsErr(errno);
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001258}
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001259
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001260static PyObject *
Victor Stinnereb5657a2011-09-30 01:44:27 +02001261win32_error_object(char* function, PyObject* filename)
1262{
1263 /* XXX - see win32_error for comments on 'function' */
1264 errno = GetLastError();
1265 if (filename)
1266 return PyErr_SetExcFromWindowsErrWithFilenameObject(
Andrew Svetlov2606a6f2012-12-19 14:33:35 +02001267 PyExc_OSError,
Victor Stinnereb5657a2011-09-30 01:44:27 +02001268 errno,
1269 filename);
1270 else
1271 return PyErr_SetFromWindowsErr(errno);
1272}
1273
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001274#endif /* MS_WINDOWS */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001275
Larry Hastings9cf065c2012-06-22 16:30:09 -07001276static PyObject *
Victor Stinner292c8352012-10-30 02:17:38 +01001277path_error(path_t *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001278{
1279#ifdef MS_WINDOWS
Victor Stinner292c8352012-10-30 02:17:38 +01001280 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
1281 0, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001282#else
Victor Stinner292c8352012-10-30 02:17:38 +01001283 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001284#endif
1285}
1286
Larry Hastings31826802013-10-19 00:09:25 -07001287
Larry Hastingsb0827312014-02-09 22:05:19 -08001288static PyObject *
1289path_error2(path_t *path, path_t *path2)
1290{
1291#ifdef MS_WINDOWS
1292 return PyErr_SetExcFromWindowsErrWithFilenameObjects(PyExc_OSError,
1293 0, path->object, path2->object);
1294#else
1295 return PyErr_SetFromErrnoWithFilenameObjects(PyExc_OSError,
1296 path->object, path2->object);
1297#endif
1298}
1299
1300
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001301/* POSIX generic methods */
1302
Larry Hastings2f936352014-08-05 14:04:04 +10001303static int
1304fildes_converter(PyObject *o, void *p)
Fred Drake4d1e64b2002-04-15 19:40:07 +00001305{
Victor Stinner8c62be82010-05-06 00:08:46 +00001306 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +10001307 int *pointer = (int *)p;
1308 fd = PyObject_AsFileDescriptor(o);
Victor Stinner8c62be82010-05-06 00:08:46 +00001309 if (fd < 0)
Larry Hastings2f936352014-08-05 14:04:04 +10001310 return 0;
1311 if (!_PyVerify_fd(fd)) {
1312 posix_error();
1313 return 0;
1314 }
1315 *pointer = fd;
1316 return 1;
1317}
1318
1319static PyObject *
1320posix_fildes_fd(int fd, int (*func)(int))
1321{
1322 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00001323 Py_BEGIN_ALLOW_THREADS
1324 res = (*func)(fd);
1325 Py_END_ALLOW_THREADS
1326 if (res < 0)
1327 return posix_error();
1328 Py_INCREF(Py_None);
1329 return Py_None;
Fred Drake4d1e64b2002-04-15 19:40:07 +00001330}
Guido van Rossum21142a01999-01-08 21:05:37 +00001331
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001332
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001333#ifdef MS_WINDOWS
Thomas Wouters477c8d52006-05-27 19:21:47 +00001334/* This is a reimplementation of the C library's chdir function,
1335 but one that produces Win32 errors instead of DOS error codes.
1336 chdir is essentially a wrapper around SetCurrentDirectory; however,
1337 it also needs to set "magic" environment variables indicating
1338 the per-drive current directory, which are of the form =<drive>: */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001339static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001340win32_chdir(LPCSTR path)
1341{
Victor Stinner75875072013-11-24 19:23:25 +01001342 char new_path[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00001343 int result;
1344 char env[4] = "=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001345
Victor Stinner8c62be82010-05-06 00:08:46 +00001346 if(!SetCurrentDirectoryA(path))
1347 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001348 result = GetCurrentDirectoryA(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001349 if (!result)
1350 return FALSE;
1351 /* In the ANSI API, there should not be any paths longer
Victor Stinner75875072013-11-24 19:23:25 +01001352 than MAX_PATH-1 (not including the final null character). */
1353 assert(result < Py_ARRAY_LENGTH(new_path));
Victor Stinner8c62be82010-05-06 00:08:46 +00001354 if (strncmp(new_path, "\\\\", 2) == 0 ||
1355 strncmp(new_path, "//", 2) == 0)
1356 /* UNC path, nothing to do. */
1357 return TRUE;
1358 env[1] = new_path[0];
1359 return SetEnvironmentVariableA(env, new_path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001360}
1361
1362/* The Unicode version differs from the ANSI version
1363 since the current directory might exceed MAX_PATH characters */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001364static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001365win32_wchdir(LPCWSTR path)
1366{
Victor Stinner75875072013-11-24 19:23:25 +01001367 wchar_t _new_path[MAX_PATH], *new_path = _new_path;
Victor Stinner8c62be82010-05-06 00:08:46 +00001368 int result;
1369 wchar_t env[4] = L"=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001370
Victor Stinner8c62be82010-05-06 00:08:46 +00001371 if(!SetCurrentDirectoryW(path))
1372 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001373 result = GetCurrentDirectoryW(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001374 if (!result)
1375 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001376 if (result > Py_ARRAY_LENGTH(new_path)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001377 new_path = PyMem_RawMalloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00001378 if (!new_path) {
1379 SetLastError(ERROR_OUTOFMEMORY);
1380 return FALSE;
1381 }
1382 result = GetCurrentDirectoryW(result, new_path);
1383 if (!result) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001384 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001385 return FALSE;
1386 }
1387 }
1388 if (wcsncmp(new_path, L"\\\\", 2) == 0 ||
1389 wcsncmp(new_path, L"//", 2) == 0)
1390 /* UNC path, nothing to do. */
1391 return TRUE;
1392 env[1] = new_path[0];
1393 result = SetEnvironmentVariableW(env, new_path);
1394 if (new_path != _new_path)
Victor Stinnerb6404912013-07-07 16:21:41 +02001395 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001396 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001397}
1398#endif
1399
Martin v. Löwis14694662006-02-03 12:54:16 +00001400#ifdef MS_WINDOWS
1401/* The CRT of Windows has a number of flaws wrt. its stat() implementation:
1402 - time stamps are restricted to second resolution
1403 - file modification times suffer from forth-and-back conversions between
1404 UTC and local time
1405 Therefore, we implement our own stat, based on the Win32 API directly.
1406*/
Victor Stinner8c62be82010-05-06 00:08:46 +00001407#define HAVE_STAT_NSEC 1
Zachary Ware63f277b2014-06-19 09:46:37 -05001408#define HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES 1
Martin v. Löwis14694662006-02-03 12:54:16 +00001409
1410struct win32_stat{
Brian Curtin87e63a22012-12-31 11:59:48 -06001411 unsigned long st_dev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001412 __int64 st_ino;
1413 unsigned short st_mode;
1414 int st_nlink;
1415 int st_uid;
1416 int st_gid;
Brian Curtin87e63a22012-12-31 11:59:48 -06001417 unsigned long st_rdev;
Martin v. Löwis14694662006-02-03 12:54:16 +00001418 __int64 st_size;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001419 time_t st_atime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001420 int st_atime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001421 time_t st_mtime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001422 int st_mtime_nsec;
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001423 time_t st_ctime;
Martin v. Löwis14694662006-02-03 12:54:16 +00001424 int st_ctime_nsec;
Zachary Ware63f277b2014-06-19 09:46:37 -05001425 unsigned long st_file_attributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001426};
1427
1428static __int64 secs_between_epochs = 11644473600; /* Seconds between 1.1.1601 and 1.1.1970 */
1429
1430static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001431FILE_TIME_to_time_t_nsec(FILETIME *in_ptr, time_t *time_out, int* nsec_out)
Martin v. Löwis14694662006-02-03 12:54:16 +00001432{
Victor Stinner8c62be82010-05-06 00:08:46 +00001433 /* XXX endianness. Shouldn't matter, as all Windows implementations are little-endian */
1434 /* Cannot simply cast and dereference in_ptr,
1435 since it might not be aligned properly */
1436 __int64 in;
1437 memcpy(&in, in_ptr, sizeof(in));
1438 *nsec_out = (int)(in % 10000000) * 100; /* FILETIME is in units of 100 nsec. */
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001439 *time_out = Py_SAFE_DOWNCAST((in / 10000000) - secs_between_epochs, __int64, time_t);
Martin v. Löwis14694662006-02-03 12:54:16 +00001440}
1441
Thomas Wouters477c8d52006-05-27 19:21:47 +00001442static void
Amaury Forgeot d'Arca251a852011-01-03 00:19:11 +00001443time_t_to_FILE_TIME(time_t time_in, int nsec_in, FILETIME *out_ptr)
Thomas Wouters477c8d52006-05-27 19:21:47 +00001444{
Victor Stinner8c62be82010-05-06 00:08:46 +00001445 /* XXX endianness */
1446 __int64 out;
1447 out = time_in + secs_between_epochs;
1448 out = out * 10000000 + nsec_in / 100;
1449 memcpy(out_ptr, &out, sizeof(out));
Thomas Wouters477c8d52006-05-27 19:21:47 +00001450}
1451
Martin v. Löwis14694662006-02-03 12:54:16 +00001452/* Below, we *know* that ugo+r is 0444 */
1453#if _S_IREAD != 0400
1454#error Unsupported C library
1455#endif
1456static int
1457attributes_to_mode(DWORD attr)
1458{
Victor Stinner8c62be82010-05-06 00:08:46 +00001459 int m = 0;
1460 if (attr & FILE_ATTRIBUTE_DIRECTORY)
1461 m |= _S_IFDIR | 0111; /* IFEXEC for user,group,other */
1462 else
1463 m |= _S_IFREG;
1464 if (attr & FILE_ATTRIBUTE_READONLY)
1465 m |= 0444;
1466 else
1467 m |= 0666;
1468 return m;
Martin v. Löwis14694662006-02-03 12:54:16 +00001469}
1470
1471static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001472attribute_data_to_stat(BY_HANDLE_FILE_INFORMATION *info, ULONG reparse_tag, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001473{
Victor Stinner8c62be82010-05-06 00:08:46 +00001474 memset(result, 0, sizeof(*result));
1475 result->st_mode = attributes_to_mode(info->dwFileAttributes);
1476 result->st_size = (((__int64)info->nFileSizeHigh)<<32) + info->nFileSizeLow;
Brian Curtin490b32a2012-12-26 07:03:03 -06001477 result->st_dev = info->dwVolumeSerialNumber;
1478 result->st_rdev = result->st_dev;
Victor Stinner8c62be82010-05-06 00:08:46 +00001479 FILE_TIME_to_time_t_nsec(&info->ftCreationTime, &result->st_ctime, &result->st_ctime_nsec);
1480 FILE_TIME_to_time_t_nsec(&info->ftLastWriteTime, &result->st_mtime, &result->st_mtime_nsec);
1481 FILE_TIME_to_time_t_nsec(&info->ftLastAccessTime, &result->st_atime, &result->st_atime_nsec);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001482 result->st_nlink = info->nNumberOfLinks;
Brian Curtin1b9df392010-11-24 20:24:31 +00001483 result->st_ino = (((__int64)info->nFileIndexHigh)<<32) + info->nFileIndexLow;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001484 if (reparse_tag == IO_REPARSE_TAG_SYMLINK) {
1485 /* first clear the S_IFMT bits */
Christian Heimes99d61352013-06-23 23:56:05 +02001486 result->st_mode ^= (result->st_mode & S_IFMT);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001487 /* now set the bits that make this a symlink */
Christian Heimes99d61352013-06-23 23:56:05 +02001488 result->st_mode |= S_IFLNK;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001489 }
Zachary Ware63f277b2014-06-19 09:46:37 -05001490 result->st_file_attributes = info->dwFileAttributes;
Martin v. Löwis14694662006-02-03 12:54:16 +00001491
Victor Stinner8c62be82010-05-06 00:08:46 +00001492 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001493}
1494
Guido van Rossumd8faa362007-04-27 19:54:29 +00001495static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001496attributes_from_dir(LPCSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001497{
Victor Stinner8c62be82010-05-06 00:08:46 +00001498 HANDLE hFindFile;
1499 WIN32_FIND_DATAA FileData;
1500 hFindFile = FindFirstFileA(pszFile, &FileData);
1501 if (hFindFile == INVALID_HANDLE_VALUE)
1502 return FALSE;
1503 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001504 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001505 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001506 info->dwFileAttributes = FileData.dwFileAttributes;
1507 info->ftCreationTime = FileData.ftCreationTime;
1508 info->ftLastAccessTime = FileData.ftLastAccessTime;
1509 info->ftLastWriteTime = FileData.ftLastWriteTime;
1510 info->nFileSizeHigh = FileData.nFileSizeHigh;
1511 info->nFileSizeLow = FileData.nFileSizeLow;
1512/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001513 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1514 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001515 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001516}
1517
1518static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001519attributes_from_dir_w(LPCWSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001520{
Victor Stinner8c62be82010-05-06 00:08:46 +00001521 HANDLE hFindFile;
1522 WIN32_FIND_DATAW FileData;
1523 hFindFile = FindFirstFileW(pszFile, &FileData);
1524 if (hFindFile == INVALID_HANDLE_VALUE)
1525 return FALSE;
1526 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001527 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001528 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001529 info->dwFileAttributes = FileData.dwFileAttributes;
1530 info->ftCreationTime = FileData.ftCreationTime;
1531 info->ftLastAccessTime = FileData.ftLastAccessTime;
1532 info->ftLastWriteTime = FileData.ftLastWriteTime;
1533 info->nFileSizeHigh = FileData.nFileSizeHigh;
1534 info->nFileSizeLow = FileData.nFileSizeLow;
1535/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001536 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1537 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001538 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001539}
1540
Brian Curtind25aef52011-06-13 15:16:04 -05001541/* Grab GetFinalPathNameByHandle dynamically from kernel32 */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001542static int has_GetFinalPathNameByHandle = -1;
Brian Curtind25aef52011-06-13 15:16:04 -05001543static DWORD (CALLBACK *Py_GetFinalPathNameByHandleW)(HANDLE, LPWSTR, DWORD,
1544 DWORD);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001545static int
Brian Curtind25aef52011-06-13 15:16:04 -05001546check_GetFinalPathNameByHandle()
Brian Curtinf5e76d02010-11-24 13:14:05 +00001547{
Brian Curtind25aef52011-06-13 15:16:04 -05001548 HINSTANCE hKernel32;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001549 DWORD (CALLBACK *Py_GetFinalPathNameByHandleA)(HANDLE, LPSTR, DWORD,
1550 DWORD);
1551
Brian Curtind25aef52011-06-13 15:16:04 -05001552 /* only recheck */
Antoine Pitrou06eecea2012-10-21 16:33:33 +02001553 if (-1 == has_GetFinalPathNameByHandle)
Brian Curtind25aef52011-06-13 15:16:04 -05001554 {
Martin v. Löwis50590f12012-01-14 17:54:09 +01001555 hKernel32 = GetModuleHandleW(L"KERNEL32");
Brian Curtind25aef52011-06-13 15:16:04 -05001556 *(FARPROC*)&Py_GetFinalPathNameByHandleA = GetProcAddress(hKernel32,
1557 "GetFinalPathNameByHandleA");
1558 *(FARPROC*)&Py_GetFinalPathNameByHandleW = GetProcAddress(hKernel32,
1559 "GetFinalPathNameByHandleW");
1560 has_GetFinalPathNameByHandle = Py_GetFinalPathNameByHandleA &&
1561 Py_GetFinalPathNameByHandleW;
1562 }
1563 return has_GetFinalPathNameByHandle;
1564}
1565
1566static BOOL
1567get_target_path(HANDLE hdl, wchar_t **target_path)
1568{
1569 int buf_size, result_length;
1570 wchar_t *buf;
1571
1572 /* We have a good handle to the target, use it to determine
1573 the target path name (then we'll call lstat on it). */
1574 buf_size = Py_GetFinalPathNameByHandleW(hdl, 0, 0,
1575 VOLUME_NAME_DOS);
1576 if(!buf_size)
1577 return FALSE;
1578
Victor Stinnerb6404912013-07-07 16:21:41 +02001579 buf = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtinc8be8402011-06-14 09:52:50 -05001580 if (!buf) {
1581 SetLastError(ERROR_OUTOFMEMORY);
1582 return FALSE;
1583 }
1584
Brian Curtind25aef52011-06-13 15:16:04 -05001585 result_length = Py_GetFinalPathNameByHandleW(hdl,
1586 buf, buf_size, VOLUME_NAME_DOS);
1587
1588 if(!result_length) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001589 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001590 return FALSE;
1591 }
1592
1593 if(!CloseHandle(hdl)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001594 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001595 return FALSE;
1596 }
1597
1598 buf[result_length] = 0;
1599
1600 *target_path = buf;
1601 return TRUE;
1602}
1603
1604static int
1605win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1606 BOOL traverse);
1607static int
1608win32_xstat_impl(const char *path, struct win32_stat *result,
1609 BOOL traverse)
1610{
Victor Stinner26de69d2011-06-17 15:15:38 +02001611 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001612 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001613 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001614 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001615 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001616 const char *dot;
1617
Brian Curtind25aef52011-06-13 15:16:04 -05001618 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001619 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1620 traverse reparse point. */
1621 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001622 }
1623
Brian Curtinf5e76d02010-11-24 13:14:05 +00001624 hFile = CreateFileA(
1625 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001626 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001627 0, /* share mode */
1628 NULL, /* security attributes */
1629 OPEN_EXISTING,
1630 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001631 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1632 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001633 the symlink path again and not the actual final path. */
Brian Curtind25aef52011-06-13 15:16:04 -05001634 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
1635 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001636 NULL);
1637
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001638 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001639 /* Either the target doesn't exist, or we don't have access to
1640 get a handle to it. If the former, we need to return an error.
1641 If the latter, we can use attributes_from_dir. */
1642 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001643 return -1;
1644 /* Could not get attributes on open file. Fall back to
1645 reading the directory. */
1646 if (!attributes_from_dir(path, &info, &reparse_tag))
1647 /* Very strange. This should not fail now */
1648 return -1;
1649 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1650 if (traverse) {
1651 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001652 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001653 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001654 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001655 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001656 } else {
1657 if (!GetFileInformationByHandle(hFile, &info)) {
1658 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001659 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001660 }
1661 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001662 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1663 return -1;
1664
1665 /* Close the outer open file handle now that we're about to
1666 reopen it with different flags. */
1667 if (!CloseHandle(hFile))
1668 return -1;
1669
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001670 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001671 /* In order to call GetFinalPathNameByHandle we need to open
1672 the file without the reparse handling flag set. */
1673 hFile2 = CreateFileA(
1674 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1675 NULL, OPEN_EXISTING,
1676 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1677 NULL);
1678 if (hFile2 == INVALID_HANDLE_VALUE)
1679 return -1;
1680
1681 if (!get_target_path(hFile2, &target_path))
1682 return -1;
1683
1684 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001685 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001686 return code;
1687 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001688 } else
1689 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001690 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001691 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001692
1693 /* Set S_IEXEC if it is an .exe, .bat, ... */
1694 dot = strrchr(path, '.');
1695 if (dot) {
1696 if (stricmp(dot, ".bat") == 0 || stricmp(dot, ".cmd") == 0 ||
1697 stricmp(dot, ".exe") == 0 || stricmp(dot, ".com") == 0)
1698 result->st_mode |= 0111;
1699 }
1700 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001701}
1702
1703static int
Brian Curtind25aef52011-06-13 15:16:04 -05001704win32_xstat_impl_w(const wchar_t *path, struct win32_stat *result,
1705 BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001706{
1707 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001708 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001709 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001710 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001711 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001712 const wchar_t *dot;
1713
Brian Curtind25aef52011-06-13 15:16:04 -05001714 if(!check_GetFinalPathNameByHandle()) {
Brian Curtinc8be8402011-06-14 09:52:50 -05001715 /* If the OS doesn't have GetFinalPathNameByHandle, don't
1716 traverse reparse point. */
1717 traverse = FALSE;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001718 }
1719
Brian Curtinf5e76d02010-11-24 13:14:05 +00001720 hFile = CreateFileW(
1721 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001722 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001723 0, /* share mode */
1724 NULL, /* security attributes */
1725 OPEN_EXISTING,
1726 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001727 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1728 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001729 the symlink path again and not the actual final path. */
Victor Stinner26de69d2011-06-17 15:15:38 +02001730 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
Brian Curtind25aef52011-06-13 15:16:04 -05001731 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001732 NULL);
1733
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001734 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001735 /* Either the target doesn't exist, or we don't have access to
1736 get a handle to it. If the former, we need to return an error.
1737 If the latter, we can use attributes_from_dir. */
1738 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001739 return -1;
1740 /* Could not get attributes on open file. Fall back to
1741 reading the directory. */
1742 if (!attributes_from_dir_w(path, &info, &reparse_tag))
1743 /* Very strange. This should not fail now */
1744 return -1;
1745 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1746 if (traverse) {
1747 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001748 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001749 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001750 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001751 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001752 } else {
1753 if (!GetFileInformationByHandle(hFile, &info)) {
1754 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001755 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001756 }
1757 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001758 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1759 return -1;
1760
1761 /* Close the outer open file handle now that we're about to
1762 reopen it with different flags. */
1763 if (!CloseHandle(hFile))
1764 return -1;
1765
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001766 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001767 /* In order to call GetFinalPathNameByHandle we need to open
1768 the file without the reparse handling flag set. */
1769 hFile2 = CreateFileW(
1770 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1771 NULL, OPEN_EXISTING,
1772 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1773 NULL);
1774 if (hFile2 == INVALID_HANDLE_VALUE)
1775 return -1;
1776
1777 if (!get_target_path(hFile2, &target_path))
1778 return -1;
1779
1780 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001781 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001782 return code;
1783 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001784 } else
1785 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001786 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001787 attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001788
1789 /* Set S_IEXEC if it is an .exe, .bat, ... */
1790 dot = wcsrchr(path, '.');
1791 if (dot) {
1792 if (_wcsicmp(dot, L".bat") == 0 || _wcsicmp(dot, L".cmd") == 0 ||
1793 _wcsicmp(dot, L".exe") == 0 || _wcsicmp(dot, L".com") == 0)
1794 result->st_mode |= 0111;
1795 }
1796 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001797}
1798
1799static int
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001800win32_xstat(const char *path, struct win32_stat *result, BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001801{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001802 /* Protocol violation: we explicitly clear errno, instead of
1803 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001804 int code = win32_xstat_impl(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001805 errno = 0;
1806 return code;
1807}
Brian Curtinf5e76d02010-11-24 13:14:05 +00001808
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001809static int
1810win32_xstat_w(const wchar_t *path, struct win32_stat *result, BOOL traverse)
1811{
1812 /* Protocol violation: we explicitly clear errno, instead of
1813 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001814 int code = win32_xstat_impl_w(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001815 errno = 0;
1816 return code;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001817}
Brian Curtind25aef52011-06-13 15:16:04 -05001818/* About the following functions: win32_lstat_w, win32_stat, win32_stat_w
Brian Curtind40e6f72010-07-08 21:39:08 +00001819
1820 In Posix, stat automatically traverses symlinks and returns the stat
1821 structure for the target. In Windows, the equivalent GetFileAttributes by
1822 default does not traverse symlinks and instead returns attributes for
1823 the symlink.
1824
1825 Therefore, win32_lstat will get the attributes traditionally, and
1826 win32_stat will first explicitly resolve the symlink target and then will
1827 call win32_lstat on that result.
1828
Ezio Melotti4969f702011-03-15 05:59:46 +02001829 The _w represent Unicode equivalents of the aforementioned ANSI functions. */
Brian Curtind40e6f72010-07-08 21:39:08 +00001830
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001831static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001832win32_lstat(const char* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001833{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001834 return win32_xstat(path, result, FALSE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001835}
1836
Victor Stinner8c62be82010-05-06 00:08:46 +00001837static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001838win32_lstat_w(const wchar_t* path, struct win32_stat *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001839{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001840 return win32_xstat_w(path, result, FALSE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001841}
1842
1843static int
1844win32_stat(const char* path, struct win32_stat *result)
1845{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001846 return win32_xstat(path, result, TRUE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001847}
1848
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001849static int
Brian Curtind40e6f72010-07-08 21:39:08 +00001850win32_stat_w(const wchar_t* path, struct win32_stat *result)
1851{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001852 return win32_xstat_w(path, result, TRUE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001853}
1854
1855static int
1856win32_fstat(int file_number, struct win32_stat *result)
1857{
Victor Stinner8c62be82010-05-06 00:08:46 +00001858 BY_HANDLE_FILE_INFORMATION info;
1859 HANDLE h;
1860 int type;
Martin v. Löwis14694662006-02-03 12:54:16 +00001861
Richard Oudkerk2240ac12012-07-06 12:05:32 +01001862 if (!_PyVerify_fd(file_number))
1863 h = INVALID_HANDLE_VALUE;
1864 else
1865 h = (HANDLE)_get_osfhandle(file_number);
Martin v. Löwis14694662006-02-03 12:54:16 +00001866
Victor Stinner8c62be82010-05-06 00:08:46 +00001867 /* Protocol violation: we explicitly clear errno, instead of
1868 setting it to a POSIX error. Callers should use GetLastError. */
1869 errno = 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001870
Victor Stinner8c62be82010-05-06 00:08:46 +00001871 if (h == INVALID_HANDLE_VALUE) {
1872 /* This is really a C library error (invalid file handle).
1873 We set the Win32 error to the closes one matching. */
1874 SetLastError(ERROR_INVALID_HANDLE);
1875 return -1;
1876 }
1877 memset(result, 0, sizeof(*result));
Martin v. Löwis14694662006-02-03 12:54:16 +00001878
Victor Stinner8c62be82010-05-06 00:08:46 +00001879 type = GetFileType(h);
1880 if (type == FILE_TYPE_UNKNOWN) {
1881 DWORD error = GetLastError();
1882 if (error != 0) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001883 return -1;
Victor Stinner8c62be82010-05-06 00:08:46 +00001884 }
1885 /* else: valid but unknown file */
1886 }
Martin v. Löwis14694662006-02-03 12:54:16 +00001887
Victor Stinner8c62be82010-05-06 00:08:46 +00001888 if (type != FILE_TYPE_DISK) {
1889 if (type == FILE_TYPE_CHAR)
1890 result->st_mode = _S_IFCHR;
1891 else if (type == FILE_TYPE_PIPE)
1892 result->st_mode = _S_IFIFO;
1893 return 0;
1894 }
1895
1896 if (!GetFileInformationByHandle(h, &info)) {
1897 return -1;
1898 }
1899
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001900 attribute_data_to_stat(&info, 0, result);
Victor Stinner8c62be82010-05-06 00:08:46 +00001901 /* specific to fstat() */
Victor Stinner8c62be82010-05-06 00:08:46 +00001902 result->st_ino = (((__int64)info.nFileIndexHigh)<<32) + info.nFileIndexLow;
1903 return 0;
Martin v. Löwis14694662006-02-03 12:54:16 +00001904}
1905
1906#endif /* MS_WINDOWS */
1907
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001908PyDoc_STRVAR(stat_result__doc__,
Larry Hastings9cf065c2012-06-22 16:30:09 -07001909"stat_result: Result from stat, fstat, or lstat.\n\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001910This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001911 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001912or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
1913\n\
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001914Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
1915or st_flags, they are available as attributes only.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001916\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001917See os.stat for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001918
1919static PyStructSequence_Field stat_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001920 {"st_mode", "protection bits"},
1921 {"st_ino", "inode"},
1922 {"st_dev", "device"},
1923 {"st_nlink", "number of hard links"},
1924 {"st_uid", "user ID of owner"},
1925 {"st_gid", "group ID of owner"},
1926 {"st_size", "total size, in bytes"},
1927 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
1928 {NULL, "integer time of last access"},
1929 {NULL, "integer time of last modification"},
1930 {NULL, "integer time of last change"},
1931 {"st_atime", "time of last access"},
1932 {"st_mtime", "time of last modification"},
1933 {"st_ctime", "time of last change"},
Larry Hastings6fe20b32012-04-19 15:07:49 -07001934 {"st_atime_ns", "time of last access in nanoseconds"},
1935 {"st_mtime_ns", "time of last modification in nanoseconds"},
1936 {"st_ctime_ns", "time of last change in nanoseconds"},
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001937#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00001938 {"st_blksize", "blocksize for filesystem I/O"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001939#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001940#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00001941 {"st_blocks", "number of blocks allocated"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001942#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001943#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00001944 {"st_rdev", "device type (if inode device)"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001945#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001946#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00001947 {"st_flags", "user defined flags for file"},
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001948#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001949#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00001950 {"st_gen", "generation number"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001951#endif
1952#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00001953 {"st_birthtime", "time of creation"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001954#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05001955#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1956 {"st_file_attributes", "Windows file attribute bits"},
1957#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001958 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001959};
1960
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001961#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Larry Hastings6fe20b32012-04-19 15:07:49 -07001962#define ST_BLKSIZE_IDX 16
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001963#else
Larry Hastings6fe20b32012-04-19 15:07:49 -07001964#define ST_BLKSIZE_IDX 15
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001965#endif
1966
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001967#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001968#define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
1969#else
1970#define ST_BLOCKS_IDX ST_BLKSIZE_IDX
1971#endif
1972
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001973#ifdef HAVE_STRUCT_STAT_ST_RDEV
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001974#define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
1975#else
1976#define ST_RDEV_IDX ST_BLOCKS_IDX
1977#endif
1978
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001979#ifdef HAVE_STRUCT_STAT_ST_FLAGS
1980#define ST_FLAGS_IDX (ST_RDEV_IDX+1)
1981#else
1982#define ST_FLAGS_IDX ST_RDEV_IDX
1983#endif
1984
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001985#ifdef HAVE_STRUCT_STAT_ST_GEN
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001986#define ST_GEN_IDX (ST_FLAGS_IDX+1)
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001987#else
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001988#define ST_GEN_IDX ST_FLAGS_IDX
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001989#endif
1990
1991#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
1992#define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
1993#else
1994#define ST_BIRTHTIME_IDX ST_GEN_IDX
1995#endif
1996
Zachary Ware63f277b2014-06-19 09:46:37 -05001997#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1998#define ST_FILE_ATTRIBUTES_IDX (ST_BIRTHTIME_IDX+1)
1999#else
2000#define ST_FILE_ATTRIBUTES_IDX ST_BIRTHTIME_IDX
2001#endif
2002
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002003static PyStructSequence_Desc stat_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002004 "stat_result", /* name */
2005 stat_result__doc__, /* doc */
2006 stat_result_fields,
2007 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002008};
2009
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002010PyDoc_STRVAR(statvfs_result__doc__,
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002011"statvfs_result: Result from statvfs or fstatvfs.\n\n\
2012This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00002013 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
Guido van Rossuma4dc73e2001-10-18 20:53:15 +00002014or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002015\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00002016See os.statvfs for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002017
2018static PyStructSequence_Field statvfs_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002019 {"f_bsize", },
2020 {"f_frsize", },
2021 {"f_blocks", },
2022 {"f_bfree", },
2023 {"f_bavail", },
2024 {"f_files", },
2025 {"f_ffree", },
2026 {"f_favail", },
2027 {"f_flag", },
2028 {"f_namemax",},
2029 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002030};
2031
2032static PyStructSequence_Desc statvfs_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00002033 "statvfs_result", /* name */
2034 statvfs_result__doc__, /* doc */
2035 statvfs_result_fields,
2036 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002037};
2038
Ross Lagerwall7807c352011-03-17 20:20:30 +02002039#if defined(HAVE_WAITID) && !defined(__APPLE__)
2040PyDoc_STRVAR(waitid_result__doc__,
2041"waitid_result: Result from waitid.\n\n\
2042This object may be accessed either as a tuple of\n\
2043 (si_pid, si_uid, si_signo, si_status, si_code),\n\
2044or via the attributes si_pid, si_uid, and so on.\n\
2045\n\
2046See os.waitid for more information.");
2047
2048static PyStructSequence_Field waitid_result_fields[] = {
2049 {"si_pid", },
2050 {"si_uid", },
2051 {"si_signo", },
2052 {"si_status", },
2053 {"si_code", },
2054 {0}
2055};
2056
2057static PyStructSequence_Desc waitid_result_desc = {
2058 "waitid_result", /* name */
2059 waitid_result__doc__, /* doc */
2060 waitid_result_fields,
2061 5
2062};
2063static PyTypeObject WaitidResultType;
2064#endif
2065
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00002066static int initialized;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002067static PyTypeObject StatResultType;
2068static PyTypeObject StatVFSResultType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002069#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05002070static PyTypeObject SchedParamType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05002071#endif
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002072static newfunc structseq_new;
2073
2074static PyObject *
2075statresult_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
2076{
Victor Stinner8c62be82010-05-06 00:08:46 +00002077 PyStructSequence *result;
2078 int i;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002079
Victor Stinner8c62be82010-05-06 00:08:46 +00002080 result = (PyStructSequence*)structseq_new(type, args, kwds);
2081 if (!result)
2082 return NULL;
2083 /* If we have been initialized from a tuple,
2084 st_?time might be set to None. Initialize it
2085 from the int slots. */
2086 for (i = 7; i <= 9; i++) {
2087 if (result->ob_item[i+3] == Py_None) {
2088 Py_DECREF(Py_None);
2089 Py_INCREF(result->ob_item[i]);
2090 result->ob_item[i+3] = result->ob_item[i];
2091 }
2092 }
2093 return (PyObject*)result;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002094}
2095
2096
2097
2098/* If true, st_?time is float. */
Martin v. Löwisfe33d0b2005-01-16 08:57:39 +00002099static int _stat_float_times = 1;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002100
2101PyDoc_STRVAR(stat_float_times__doc__,
2102"stat_float_times([newval]) -> oldval\n\n\
2103Determine whether os.[lf]stat represents time stamps as float objects.\n\
Larry Hastings2f936352014-08-05 14:04:04 +10002104\n\
2105If value is True, future calls to stat() return floats; if it is False,\n\
2106future calls return ints.\n\
2107If value is omitted, return the current setting.\n");
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002108
Larry Hastings2f936352014-08-05 14:04:04 +10002109/* AC 3.5: the public default value should be None, not ready for that yet */
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002110static PyObject*
2111stat_float_times(PyObject* self, PyObject *args)
2112{
Victor Stinner8c62be82010-05-06 00:08:46 +00002113 int newval = -1;
2114 if (!PyArg_ParseTuple(args, "|i:stat_float_times", &newval))
2115 return NULL;
Victor Stinner034d0aa2012-06-05 01:22:15 +02002116 if (PyErr_WarnEx(PyExc_DeprecationWarning,
2117 "stat_float_times() is deprecated",
2118 1))
2119 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00002120 if (newval == -1)
2121 /* Return old value */
2122 return PyBool_FromLong(_stat_float_times);
2123 _stat_float_times = newval;
2124 Py_INCREF(Py_None);
2125 return Py_None;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00002126}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002127
Larry Hastings6fe20b32012-04-19 15:07:49 -07002128static PyObject *billion = NULL;
2129
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002130static void
Victor Stinner4195b5c2012-02-08 23:03:19 +01002131fill_time(PyObject *v, int index, time_t sec, unsigned long nsec)
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002132{
Larry Hastings6fe20b32012-04-19 15:07:49 -07002133 PyObject *s = _PyLong_FromTime_t(sec);
2134 PyObject *ns_fractional = PyLong_FromUnsignedLong(nsec);
2135 PyObject *s_in_ns = NULL;
2136 PyObject *ns_total = NULL;
2137 PyObject *float_s = NULL;
2138
2139 if (!(s && ns_fractional))
2140 goto exit;
2141
2142 s_in_ns = PyNumber_Multiply(s, billion);
2143 if (!s_in_ns)
2144 goto exit;
2145
2146 ns_total = PyNumber_Add(s_in_ns, ns_fractional);
2147 if (!ns_total)
2148 goto exit;
2149
Victor Stinner4195b5c2012-02-08 23:03:19 +01002150 if (_stat_float_times) {
Larry Hastings6fe20b32012-04-19 15:07:49 -07002151 float_s = PyFloat_FromDouble(sec + 1e-9*nsec);
2152 if (!float_s)
2153 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00002154 }
Larry Hastings6fe20b32012-04-19 15:07:49 -07002155 else {
2156 float_s = s;
2157 Py_INCREF(float_s);
2158 }
2159
2160 PyStructSequence_SET_ITEM(v, index, s);
2161 PyStructSequence_SET_ITEM(v, index+3, float_s);
2162 PyStructSequence_SET_ITEM(v, index+6, ns_total);
2163 s = NULL;
2164 float_s = NULL;
2165 ns_total = NULL;
2166exit:
2167 Py_XDECREF(s);
2168 Py_XDECREF(ns_fractional);
2169 Py_XDECREF(s_in_ns);
2170 Py_XDECREF(ns_total);
2171 Py_XDECREF(float_s);
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002172}
2173
Tim Peters5aa91602002-01-30 05:46:57 +00002174/* pack a system stat C structure into the Python stat tuple
Fred Drake699f3522000-06-29 21:12:41 +00002175 (used by posix_stat() and posix_fstat()) */
2176static PyObject*
Victor Stinner4195b5c2012-02-08 23:03:19 +01002177_pystat_fromstructstat(STRUCT_STAT *st)
Fred Drake699f3522000-06-29 21:12:41 +00002178{
Victor Stinner8c62be82010-05-06 00:08:46 +00002179 unsigned long ansec, mnsec, cnsec;
2180 PyObject *v = PyStructSequence_New(&StatResultType);
2181 if (v == NULL)
2182 return NULL;
Fred Drake699f3522000-06-29 21:12:41 +00002183
Victor Stinner8c62be82010-05-06 00:08:46 +00002184 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long)st->st_mode));
Fred Drake699f3522000-06-29 21:12:41 +00002185#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002186 PyStructSequence_SET_ITEM(v, 1,
2187 PyLong_FromLongLong((PY_LONG_LONG)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002188#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002189 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002190#endif
Serhiy Storchaka404fa922013-01-02 18:22:23 +02002191#ifdef MS_WINDOWS
2192 PyStructSequence_SET_ITEM(v, 2, PyLong_FromUnsignedLong(st->st_dev));
2193#elif defined(HAVE_LONG_LONG)
Victor Stinner8c62be82010-05-06 00:08:46 +00002194 PyStructSequence_SET_ITEM(v, 2,
2195 PyLong_FromLongLong((PY_LONG_LONG)st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002196#else
Brian Curtin9cc43212013-01-01 12:31:06 -06002197 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long)st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002198#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002199 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long)st->st_nlink));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02002200#if defined(MS_WINDOWS)
2201 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong(0));
2202 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong(0));
2203#else
2204 PyStructSequence_SET_ITEM(v, 4, _PyLong_FromUid(st->st_uid));
2205 PyStructSequence_SET_ITEM(v, 5, _PyLong_FromGid(st->st_gid));
2206#endif
Fred Drake699f3522000-06-29 21:12:41 +00002207#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002208 PyStructSequence_SET_ITEM(v, 6,
2209 PyLong_FromLongLong((PY_LONG_LONG)st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002210#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002211 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong(st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002212#endif
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002213
Martin v. Löwis14694662006-02-03 12:54:16 +00002214#if defined(HAVE_STAT_TV_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002215 ansec = st->st_atim.tv_nsec;
2216 mnsec = st->st_mtim.tv_nsec;
2217 cnsec = st->st_ctim.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002218#elif defined(HAVE_STAT_TV_NSEC2)
Victor Stinner8c62be82010-05-06 00:08:46 +00002219 ansec = st->st_atimespec.tv_nsec;
2220 mnsec = st->st_mtimespec.tv_nsec;
2221 cnsec = st->st_ctimespec.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002222#elif defined(HAVE_STAT_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002223 ansec = st->st_atime_nsec;
2224 mnsec = st->st_mtime_nsec;
2225 cnsec = st->st_ctime_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002226#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002227 ansec = mnsec = cnsec = 0;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002228#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002229 fill_time(v, 7, st->st_atime, ansec);
2230 fill_time(v, 8, st->st_mtime, mnsec);
2231 fill_time(v, 9, st->st_ctime, cnsec);
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002232
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002233#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00002234 PyStructSequence_SET_ITEM(v, ST_BLKSIZE_IDX,
2235 PyLong_FromLong((long)st->st_blksize));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002236#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002237#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00002238 PyStructSequence_SET_ITEM(v, ST_BLOCKS_IDX,
2239 PyLong_FromLong((long)st->st_blocks));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002240#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002241#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00002242 PyStructSequence_SET_ITEM(v, ST_RDEV_IDX,
2243 PyLong_FromLong((long)st->st_rdev));
Fred Drake699f3522000-06-29 21:12:41 +00002244#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002245#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00002246 PyStructSequence_SET_ITEM(v, ST_GEN_IDX,
2247 PyLong_FromLong((long)st->st_gen));
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002248#endif
2249#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00002250 {
Victor Stinner4195b5c2012-02-08 23:03:19 +01002251 PyObject *val;
2252 unsigned long bsec,bnsec;
2253 bsec = (long)st->st_birthtime;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002254#ifdef HAVE_STAT_TV_NSEC2
Victor Stinner4195b5c2012-02-08 23:03:19 +01002255 bnsec = st->st_birthtimespec.tv_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002256#else
Victor Stinner4195b5c2012-02-08 23:03:19 +01002257 bnsec = 0;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002258#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002259 if (_stat_float_times) {
2260 val = PyFloat_FromDouble(bsec + 1e-9*bnsec);
2261 } else {
2262 val = PyLong_FromLong((long)bsec);
2263 }
2264 PyStructSequence_SET_ITEM(v, ST_BIRTHTIME_IDX,
2265 val);
Victor Stinner8c62be82010-05-06 00:08:46 +00002266 }
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002267#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002268#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00002269 PyStructSequence_SET_ITEM(v, ST_FLAGS_IDX,
2270 PyLong_FromLong((long)st->st_flags));
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002271#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05002272#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2273 PyStructSequence_SET_ITEM(v, ST_FILE_ATTRIBUTES_IDX,
2274 PyLong_FromUnsignedLong(st->st_file_attributes));
2275#endif
Fred Drake699f3522000-06-29 21:12:41 +00002276
Victor Stinner8c62be82010-05-06 00:08:46 +00002277 if (PyErr_Occurred()) {
2278 Py_DECREF(v);
2279 return NULL;
2280 }
Fred Drake699f3522000-06-29 21:12:41 +00002281
Victor Stinner8c62be82010-05-06 00:08:46 +00002282 return v;
Fred Drake699f3522000-06-29 21:12:41 +00002283}
2284
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002285/* POSIX methods */
2286
Guido van Rossum94f6f721999-01-06 18:42:14 +00002287
2288static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07002289posix_do_stat(char *function_name, path_t *path,
2290 int dir_fd, int follow_symlinks)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002291{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002292 STRUCT_STAT st;
2293 int result;
2294
2295#if !defined(MS_WINDOWS) && !defined(HAVE_FSTATAT) && !defined(HAVE_LSTAT)
2296 if (follow_symlinks_specified(function_name, follow_symlinks))
2297 return NULL;
2298#endif
2299
2300 if (path_and_dir_fd_invalid("stat", path, dir_fd) ||
2301 dir_fd_and_fd_invalid("stat", dir_fd, path->fd) ||
2302 fd_and_follow_symlinks_invalid("stat", path->fd, follow_symlinks))
2303 return NULL;
2304
2305 Py_BEGIN_ALLOW_THREADS
2306 if (path->fd != -1)
2307 result = FSTAT(path->fd, &st);
2308 else
2309#ifdef MS_WINDOWS
2310 if (path->wide) {
2311 if (follow_symlinks)
2312 result = win32_stat_w(path->wide, &st);
2313 else
2314 result = win32_lstat_w(path->wide, &st);
2315 }
2316 else
2317#endif
2318#if defined(HAVE_LSTAT) || defined(MS_WINDOWS)
2319 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
2320 result = LSTAT(path->narrow, &st);
2321 else
2322#endif
2323#ifdef HAVE_FSTATAT
2324 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks)
2325 result = fstatat(dir_fd, path->narrow, &st,
2326 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2327 else
2328#endif
2329 result = STAT(path->narrow, &st);
2330 Py_END_ALLOW_THREADS
2331
Victor Stinner292c8352012-10-30 02:17:38 +01002332 if (result != 0) {
2333 return path_error(path);
2334 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07002335
2336 return _pystat_fromstructstat(&st);
2337}
2338
Larry Hastings2f936352014-08-05 14:04:04 +10002339/*[python input]
2340
2341for s in """
2342
2343FACCESSAT
2344FCHMODAT
2345FCHOWNAT
2346FSTATAT
2347LINKAT
2348MKDIRAT
2349MKFIFOAT
2350MKNODAT
2351OPENAT
2352READLINKAT
2353SYMLINKAT
2354UNLINKAT
2355
2356""".strip().split():
2357 s = s.strip()
2358 print("""
2359#ifdef HAVE_{s}
2360 #define {s}_DIR_FD_CONVERTER dir_fd_converter
Larry Hastings31826802013-10-19 00:09:25 -07002361#else
Larry Hastings2f936352014-08-05 14:04:04 +10002362 #define {s}_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings31826802013-10-19 00:09:25 -07002363#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002364""".rstrip().format(s=s))
2365
2366for s in """
2367
2368FCHDIR
2369FCHMOD
2370FCHOWN
2371FDOPENDIR
2372FEXECVE
2373FPATHCONF
2374FSTATVFS
2375FTRUNCATE
2376
2377""".strip().split():
2378 s = s.strip()
2379 print("""
2380#ifdef HAVE_{s}
2381 #define PATH_HAVE_{s} 1
2382#else
2383 #define PATH_HAVE_{s} 0
2384#endif
2385
2386""".rstrip().format(s=s))
2387[python start generated code]*/
2388
2389#ifdef HAVE_FACCESSAT
2390 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_converter
2391#else
2392 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_unavailable
2393#endif
2394
2395#ifdef HAVE_FCHMODAT
2396 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_converter
2397#else
2398 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_unavailable
2399#endif
2400
2401#ifdef HAVE_FCHOWNAT
2402 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_converter
2403#else
2404 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_unavailable
2405#endif
2406
2407#ifdef HAVE_FSTATAT
2408 #define FSTATAT_DIR_FD_CONVERTER dir_fd_converter
2409#else
2410 #define FSTATAT_DIR_FD_CONVERTER dir_fd_unavailable
2411#endif
2412
2413#ifdef HAVE_LINKAT
2414 #define LINKAT_DIR_FD_CONVERTER dir_fd_converter
2415#else
2416 #define LINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2417#endif
2418
2419#ifdef HAVE_MKDIRAT
2420 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_converter
2421#else
2422 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_unavailable
2423#endif
2424
2425#ifdef HAVE_MKFIFOAT
2426 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_converter
2427#else
2428 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_unavailable
2429#endif
2430
2431#ifdef HAVE_MKNODAT
2432 #define MKNODAT_DIR_FD_CONVERTER dir_fd_converter
2433#else
2434 #define MKNODAT_DIR_FD_CONVERTER dir_fd_unavailable
2435#endif
2436
2437#ifdef HAVE_OPENAT
2438 #define OPENAT_DIR_FD_CONVERTER dir_fd_converter
2439#else
2440 #define OPENAT_DIR_FD_CONVERTER dir_fd_unavailable
2441#endif
2442
2443#ifdef HAVE_READLINKAT
2444 #define READLINKAT_DIR_FD_CONVERTER dir_fd_converter
2445#else
2446 #define READLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2447#endif
2448
2449#ifdef HAVE_SYMLINKAT
2450 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_converter
2451#else
2452 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2453#endif
2454
2455#ifdef HAVE_UNLINKAT
2456 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_converter
2457#else
2458 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2459#endif
2460
2461#ifdef HAVE_FCHDIR
2462 #define PATH_HAVE_FCHDIR 1
2463#else
2464 #define PATH_HAVE_FCHDIR 0
2465#endif
2466
2467#ifdef HAVE_FCHMOD
2468 #define PATH_HAVE_FCHMOD 1
2469#else
2470 #define PATH_HAVE_FCHMOD 0
2471#endif
2472
2473#ifdef HAVE_FCHOWN
2474 #define PATH_HAVE_FCHOWN 1
2475#else
2476 #define PATH_HAVE_FCHOWN 0
2477#endif
2478
2479#ifdef HAVE_FDOPENDIR
2480 #define PATH_HAVE_FDOPENDIR 1
2481#else
2482 #define PATH_HAVE_FDOPENDIR 0
2483#endif
2484
2485#ifdef HAVE_FEXECVE
2486 #define PATH_HAVE_FEXECVE 1
2487#else
2488 #define PATH_HAVE_FEXECVE 0
2489#endif
2490
2491#ifdef HAVE_FPATHCONF
2492 #define PATH_HAVE_FPATHCONF 1
2493#else
2494 #define PATH_HAVE_FPATHCONF 0
2495#endif
2496
2497#ifdef HAVE_FSTATVFS
2498 #define PATH_HAVE_FSTATVFS 1
2499#else
2500 #define PATH_HAVE_FSTATVFS 0
2501#endif
2502
2503#ifdef HAVE_FTRUNCATE
2504 #define PATH_HAVE_FTRUNCATE 1
2505#else
2506 #define PATH_HAVE_FTRUNCATE 0
2507#endif
2508/*[python end generated code: output=4bd4f6f7d41267f1 input=80b4c890b6774ea5]*/
Larry Hastings31826802013-10-19 00:09:25 -07002509
2510
Larry Hastings61272b72014-01-07 12:41:53 -08002511/*[python input]
Larry Hastings31826802013-10-19 00:09:25 -07002512
2513class path_t_converter(CConverter):
2514
2515 type = "path_t"
2516 impl_by_reference = True
2517 parse_by_reference = True
2518
2519 converter = 'path_converter'
2520
2521 def converter_init(self, *, allow_fd=False, nullable=False):
Larry Hastings31826802013-10-19 00:09:25 -07002522 # right now path_t doesn't support default values.
2523 # to support a default value, you'll need to override initialize().
Larry Hastings2f936352014-08-05 14:04:04 +10002524 if self.default not in (unspecified, None):
Larry Hastings7726ac92014-01-31 22:03:12 -08002525 fail("Can't specify a default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002526
Larry Hastings2f936352014-08-05 14:04:04 +10002527 if self.c_default not in (None, 'Py_None'):
2528 raise RuntimeError("Can't specify a c_default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002529
2530 self.nullable = nullable
2531 self.allow_fd = allow_fd
2532
Larry Hastings7726ac92014-01-31 22:03:12 -08002533 def pre_render(self):
2534 def strify(value):
Larry Hastings2f936352014-08-05 14:04:04 +10002535 if isinstance(value, str):
2536 return value
Larry Hastings7726ac92014-01-31 22:03:12 -08002537 return str(int(bool(value)))
2538
2539 # add self.py_name here when merging with posixmodule conversion
Larry Hastings2f936352014-08-05 14:04:04 +10002540 self.c_default = 'PATH_T_INITIALIZE("{}", "{}", {}, {})'.format(
Larry Hastings31826802013-10-19 00:09:25 -07002541 self.function.name,
Larry Hastings2f936352014-08-05 14:04:04 +10002542 self.name,
Larry Hastings7726ac92014-01-31 22:03:12 -08002543 strify(self.nullable),
2544 strify(self.allow_fd),
Larry Hastings31826802013-10-19 00:09:25 -07002545 )
2546
2547 def cleanup(self):
2548 return "path_cleanup(&" + self.name + ");\n"
2549
2550
2551class dir_fd_converter(CConverter):
2552 type = 'int'
Larry Hastings31826802013-10-19 00:09:25 -07002553
Larry Hastings2f936352014-08-05 14:04:04 +10002554 def converter_init(self, requires=None):
Larry Hastings31826802013-10-19 00:09:25 -07002555 if self.default in (unspecified, None):
2556 self.c_default = 'DEFAULT_DIR_FD'
Larry Hastings2f936352014-08-05 14:04:04 +10002557 if isinstance(requires, str):
2558 self.converter = requires.upper() + '_DIR_FD_CONVERTER'
2559 else:
2560 self.converter = 'dir_fd_converter'
Larry Hastings31826802013-10-19 00:09:25 -07002561
Larry Hastings2f936352014-08-05 14:04:04 +10002562class fildes_converter(CConverter):
2563 type = 'int'
2564 converter = 'fildes_converter'
2565
2566class uid_t_converter(CConverter):
2567 type = "uid_t"
2568 converter = '_Py_Uid_Converter'
2569
2570class gid_t_converter(CConverter):
2571 type = "gid_t"
2572 converter = '_Py_Gid_Converter'
2573
2574class FSConverter_converter(CConverter):
2575 type = 'PyObject *'
2576 converter = 'PyUnicode_FSConverter'
2577 def converter_init(self):
2578 if self.default is not unspecified:
2579 fail("FSConverter_converter does not support default values")
2580 self.c_default = 'NULL'
2581
2582 def cleanup(self):
2583 return "Py_XDECREF(" + self.name + ");\n"
2584
2585class pid_t_converter(CConverter):
2586 type = 'pid_t'
2587 format_unit = '" _Py_PARSE_PID "'
2588
2589class idtype_t_converter(int_converter):
2590 type = 'idtype_t'
2591
2592class id_t_converter(CConverter):
2593 type = 'id_t'
2594 format_unit = '" _Py_PARSE_PID "'
2595
2596class Py_intptr_t_converter(CConverter):
2597 type = 'Py_intptr_t'
2598 format_unit = '" _Py_PARSE_INTPTR "'
2599
2600class Py_off_t_converter(CConverter):
2601 type = 'Py_off_t'
2602 converter = 'Py_off_t_converter'
2603
2604class Py_off_t_return_converter(long_return_converter):
2605 type = 'Py_off_t'
2606 conversion_fn = 'PyLong_FromPy_off_t'
2607
2608class path_confname_converter(CConverter):
2609 type="int"
2610 converter="conv_path_confname"
2611
2612class confstr_confname_converter(path_confname_converter):
2613 converter='conv_confstr_confname'
2614
2615class sysconf_confname_converter(path_confname_converter):
2616 converter="conv_sysconf_confname"
2617
2618class sched_param_converter(CConverter):
2619 type = 'struct sched_param'
2620 converter = 'convert_sched_param'
2621 impl_by_reference = True;
Larry Hastings31826802013-10-19 00:09:25 -07002622
Larry Hastings61272b72014-01-07 12:41:53 -08002623[python start generated code]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002624/*[python end generated code: output=da39a3ee5e6b4b0d input=147ba8f52a05aca4]*/
Larry Hastings31826802013-10-19 00:09:25 -07002625
Larry Hastings61272b72014-01-07 12:41:53 -08002626/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002627
Larry Hastings2a727912014-01-16 11:32:01 -08002628os.stat
Larry Hastings31826802013-10-19 00:09:25 -07002629
2630 path : path_t(allow_fd=True)
2631 Path to be examined; can be string, bytes, or open-file-descriptor int.
2632
2633 *
2634
Larry Hastings2f936352014-08-05 14:04:04 +10002635 dir_fd : dir_fd(requires='fstatat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002636 If not None, it should be a file descriptor open to a directory,
2637 and path should be a relative string; path will then be relative to
2638 that directory.
2639
2640 follow_symlinks: bool = True
2641 If False, and the last element of the path is a symbolic link,
2642 stat will examine the symbolic link itself instead of the file
2643 the link points to.
2644
2645Perform a stat system call on the given path.
2646
2647dir_fd and follow_symlinks may not be implemented
2648 on your platform. If they are unavailable, using them will raise a
2649 NotImplementedError.
2650
2651It's an error to use dir_fd or follow_symlinks when specifying path as
2652 an open file descriptor.
2653
Larry Hastings61272b72014-01-07 12:41:53 -08002654[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002655
2656PyDoc_STRVAR(os_stat__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002657"stat($module, /, path, *, dir_fd=None, follow_symlinks=True)\n"
2658"--\n"
2659"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002660"Perform a stat system call on the given path.\n"
2661"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002662" path\n"
2663" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
2664" dir_fd\n"
2665" If not None, it should be a file descriptor open to a directory,\n"
2666" and path should be a relative string; path will then be relative to\n"
2667" that directory.\n"
2668" follow_symlinks\n"
2669" If False, and the last element of the path is a symbolic link,\n"
2670" stat will examine the symbolic link itself instead of the file\n"
2671" the link points to.\n"
2672"\n"
2673"dir_fd and follow_symlinks may not be implemented\n"
2674" on your platform. If they are unavailable, using them will raise a\n"
2675" NotImplementedError.\n"
2676"\n"
2677"It\'s an error to use dir_fd or follow_symlinks when specifying path as\n"
2678" an open file descriptor.");
2679
2680#define OS_STAT_METHODDEF \
2681 {"stat", (PyCFunction)os_stat, METH_VARARGS|METH_KEYWORDS, os_stat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002682
2683static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002684os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002685
2686static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002687os_stat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002688{
Larry Hastings31826802013-10-19 00:09:25 -07002689 PyObject *return_value = NULL;
2690 static char *_keywords[] = {"path", "dir_fd", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002691 path_t path = PATH_T_INITIALIZE("stat", "path", 0, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002692 int dir_fd = DEFAULT_DIR_FD;
2693 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002694
Larry Hastings31826802013-10-19 00:09:25 -07002695 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2696 "O&|$O&p:stat", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002697 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002698 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08002699 return_value = os_stat_impl(module, &path, dir_fd, follow_symlinks);
Larry Hastings31826802013-10-19 00:09:25 -07002700
2701exit:
2702 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002703 path_cleanup(&path);
Larry Hastings31826802013-10-19 00:09:25 -07002704
Larry Hastings9cf065c2012-06-22 16:30:09 -07002705 return return_value;
2706}
2707
Larry Hastings31826802013-10-19 00:09:25 -07002708static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002709os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd, int follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002710/*[clinic end generated code: output=0e9f9508fa0c0607 input=099d356c306fa24a]*/
Larry Hastings31826802013-10-19 00:09:25 -07002711{
2712 return posix_do_stat("stat", path, dir_fd, follow_symlinks);
2713}
2714
Larry Hastings2f936352014-08-05 14:04:04 +10002715
2716/*[clinic input]
2717os.lstat
2718
2719 path : path_t
2720
2721 *
2722
2723 dir_fd : dir_fd(requires='fstatat') = None
2724
2725Perform a stat system call on the given path, without following symbolic links.
2726
2727Like stat(), but do not follow symbolic links.
2728Equivalent to stat(path, follow_symlinks=False).
2729[clinic start generated code]*/
2730
2731PyDoc_STRVAR(os_lstat__doc__,
2732"lstat($module, /, path, *, dir_fd=None)\n"
2733"--\n"
2734"\n"
2735"Perform a stat system call on the given path, without following symbolic links.\n"
2736"\n"
2737"Like stat(), but do not follow symbolic links.\n"
2738"Equivalent to stat(path, follow_symlinks=False).");
2739
2740#define OS_LSTAT_METHODDEF \
2741 {"lstat", (PyCFunction)os_lstat, METH_VARARGS|METH_KEYWORDS, os_lstat__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002742
2743static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10002744os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002745
Larry Hastings2f936352014-08-05 14:04:04 +10002746static PyObject *
2747os_lstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
2748{
2749 PyObject *return_value = NULL;
2750 static char *_keywords[] = {"path", "dir_fd", NULL};
2751 path_t path = PATH_T_INITIALIZE("lstat", "path", 0, 0);
2752 int dir_fd = DEFAULT_DIR_FD;
2753
2754 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2755 "O&|$O&:lstat", _keywords,
2756 path_converter, &path, FSTATAT_DIR_FD_CONVERTER, &dir_fd))
2757 goto exit;
2758 return_value = os_lstat_impl(module, &path, dir_fd);
2759
2760exit:
2761 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002762 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10002763
Larry Hastings9cf065c2012-06-22 16:30:09 -07002764 return return_value;
2765}
2766
Larry Hastings2f936352014-08-05 14:04:04 +10002767static PyObject *
2768os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd)
2769/*[clinic end generated code: output=85702247224a2b1c input=0b7474765927b925]*/
2770{
2771 int follow_symlinks = 0;
2772 return posix_do_stat("lstat", path, dir_fd, follow_symlinks);
2773}
Larry Hastings31826802013-10-19 00:09:25 -07002774
Larry Hastings2f936352014-08-05 14:04:04 +10002775
Larry Hastings61272b72014-01-07 12:41:53 -08002776/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +10002777os.access -> bool
Larry Hastings31826802013-10-19 00:09:25 -07002778
2779 path: path_t(allow_fd=True)
2780 Path to be tested; can be string, bytes, or open-file-descriptor int.
2781
2782 mode: int
2783 Operating-system mode bitfield. Can be F_OK to test existence,
2784 or the inclusive-OR of R_OK, W_OK, and X_OK.
2785
2786 *
2787
Larry Hastings2f936352014-08-05 14:04:04 +10002788 dir_fd : dir_fd(requires='faccessat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002789 If not None, it should be a file descriptor open to a directory,
2790 and path should be relative; path will then be relative to that
2791 directory.
2792
2793 effective_ids: bool = False
2794 If True, access will use the effective uid/gid instead of
2795 the real uid/gid.
2796
2797 follow_symlinks: bool = True
2798 If False, and the last element of the path is a symbolic link,
2799 access will examine the symbolic link itself instead of the file
2800 the link points to.
2801
2802Use the real uid/gid to test for access to a path.
2803
2804{parameters}
2805dir_fd, effective_ids, and follow_symlinks may not be implemented
2806 on your platform. If they are unavailable, using them will raise a
2807 NotImplementedError.
2808
2809Note that most operations will use the effective uid/gid, therefore this
2810 routine can be used in a suid/sgid environment to test if the invoking user
2811 has the specified access to the path.
2812
Larry Hastings61272b72014-01-07 12:41:53 -08002813[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002814
2815PyDoc_STRVAR(os_access__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002816"access($module, /, path, mode, *, dir_fd=None, effective_ids=False,\n"
2817" follow_symlinks=True)\n"
2818"--\n"
2819"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002820"Use the real uid/gid to test for access to a path.\n"
2821"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002822" path\n"
2823" Path to be tested; can be string, bytes, or open-file-descriptor int.\n"
2824" mode\n"
2825" Operating-system mode bitfield. Can be F_OK to test existence,\n"
2826" or the inclusive-OR of R_OK, W_OK, and X_OK.\n"
2827" dir_fd\n"
2828" If not None, it should be a file descriptor open to a directory,\n"
2829" and path should be relative; path will then be relative to that\n"
2830" directory.\n"
2831" effective_ids\n"
2832" If True, access will use the effective uid/gid instead of\n"
2833" the real uid/gid.\n"
2834" follow_symlinks\n"
2835" If False, and the last element of the path is a symbolic link,\n"
2836" access will examine the symbolic link itself instead of the file\n"
2837" the link points to.\n"
2838"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002839"dir_fd, effective_ids, and follow_symlinks may not be implemented\n"
2840" on your platform. If they are unavailable, using them will raise a\n"
2841" NotImplementedError.\n"
2842"\n"
2843"Note that most operations will use the effective uid/gid, therefore this\n"
2844" routine can be used in a suid/sgid environment to test if the invoking user\n"
2845" has the specified access to the path.");
2846
2847#define OS_ACCESS_METHODDEF \
2848 {"access", (PyCFunction)os_access, METH_VARARGS|METH_KEYWORDS, os_access__doc__},
Larry Hastings9cf065c2012-06-22 16:30:09 -07002849
Larry Hastings2f936352014-08-05 14:04:04 +10002850static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002851os_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 -07002852
2853static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002854os_access(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002855{
Larry Hastings31826802013-10-19 00:09:25 -07002856 PyObject *return_value = NULL;
2857 static char *_keywords[] = {"path", "mode", "dir_fd", "effective_ids", "follow_symlinks", NULL};
Larry Hastings2f936352014-08-05 14:04:04 +10002858 path_t path = PATH_T_INITIALIZE("access", "path", 0, 1);
Victor Stinner8c62be82010-05-06 00:08:46 +00002859 int mode;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002860 int dir_fd = DEFAULT_DIR_FD;
2861 int effective_ids = 0;
2862 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10002863 int _return_value;
Larry Hastings31826802013-10-19 00:09:25 -07002864
2865 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
2866 "O&i|$O&pp:access", _keywords,
Larry Hastings2f936352014-08-05 14:04:04 +10002867 path_converter, &path, &mode, FACCESSAT_DIR_FD_CONVERTER, &dir_fd, &effective_ids, &follow_symlinks))
Larry Hastings31826802013-10-19 00:09:25 -07002868 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +10002869 _return_value = os_access_impl(module, &path, mode, dir_fd, effective_ids, follow_symlinks);
2870 if ((_return_value == -1) && PyErr_Occurred())
2871 goto exit;
2872 return_value = PyBool_FromLong((long)_return_value);
Larry Hastings31826802013-10-19 00:09:25 -07002873
2874exit:
2875 /* Cleanup for path */
2876 path_cleanup(&path);
2877
2878 return return_value;
2879}
2880
Larry Hastings2f936352014-08-05 14:04:04 +10002881static int
Larry Hastingsebdcb502013-11-23 14:54:00 -08002882os_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 +10002883/*[clinic end generated code: output=dfd404666906f012 input=b75a756797af45ec]*/
Larry Hastings31826802013-10-19 00:09:25 -07002884{
Larry Hastings2f936352014-08-05 14:04:04 +10002885 int return_value;
Victor Stinner8c62be82010-05-06 00:08:46 +00002886
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002887#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002888 DWORD attr;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002889#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07002890 int result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002891#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07002892
Larry Hastings9cf065c2012-06-22 16:30:09 -07002893#ifndef HAVE_FACCESSAT
2894 if (follow_symlinks_specified("access", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002895 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002896
2897 if (effective_ids) {
2898 argument_unavailable_error("access", "effective_ids");
Larry Hastings2f936352014-08-05 14:04:04 +10002899 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002900 }
2901#endif
2902
2903#ifdef MS_WINDOWS
2904 Py_BEGIN_ALLOW_THREADS
Christian Heimesebe83f92013-10-19 22:36:17 +02002905 if (path->wide != NULL)
2906 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002907 else
Christian Heimesebe83f92013-10-19 22:36:17 +02002908 attr = GetFileAttributesA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002909 Py_END_ALLOW_THREADS
2910
2911 /*
Georg Brandlf7875592012-06-24 13:58:31 +02002912 * Access is possible if
Larry Hastings9cf065c2012-06-22 16:30:09 -07002913 * * we didn't get a -1, and
2914 * * write access wasn't requested,
2915 * * or the file isn't read-only,
2916 * * or it's a directory.
2917 * (Directories cannot be read-only on Windows.)
2918 */
Larry Hastings2f936352014-08-05 14:04:04 +10002919 return_value = (attr != INVALID_FILE_ATTRIBUTES) &&
Georg Brandl5bb7aa92012-06-23 12:48:40 +02002920 (!(mode & 2) ||
Larry Hastings9cf065c2012-06-22 16:30:09 -07002921 !(attr & FILE_ATTRIBUTE_READONLY) ||
Larry Hastings2f936352014-08-05 14:04:04 +10002922 (attr & FILE_ATTRIBUTE_DIRECTORY));
Larry Hastings9cf065c2012-06-22 16:30:09 -07002923#else
2924
2925 Py_BEGIN_ALLOW_THREADS
2926#ifdef HAVE_FACCESSAT
2927 if ((dir_fd != DEFAULT_DIR_FD) ||
2928 effective_ids ||
2929 !follow_symlinks) {
2930 int flags = 0;
2931 if (!follow_symlinks)
2932 flags |= AT_SYMLINK_NOFOLLOW;
2933 if (effective_ids)
2934 flags |= AT_EACCESS;
Larry Hastings31826802013-10-19 00:09:25 -07002935 result = faccessat(dir_fd, path->narrow, mode, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002936 }
2937 else
2938#endif
Larry Hastings31826802013-10-19 00:09:25 -07002939 result = access(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002940 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002941 return_value = !result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002942#endif
2943
Larry Hastings9cf065c2012-06-22 16:30:09 -07002944 return return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002945}
2946
Guido van Rossumd371ff11999-01-25 16:12:23 +00002947#ifndef F_OK
2948#define F_OK 0
2949#endif
2950#ifndef R_OK
2951#define R_OK 4
2952#endif
2953#ifndef W_OK
2954#define W_OK 2
2955#endif
2956#ifndef X_OK
2957#define X_OK 1
2958#endif
2959
Larry Hastings31826802013-10-19 00:09:25 -07002960
Guido van Rossumd371ff11999-01-25 16:12:23 +00002961#ifdef HAVE_TTYNAME
Larry Hastings61272b72014-01-07 12:41:53 -08002962/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002963os.ttyname -> DecodeFSDefault
2964
2965 fd: int
2966 Integer file descriptor handle.
2967
2968 /
2969
2970Return the name of the terminal device connected to 'fd'.
Larry Hastings61272b72014-01-07 12:41:53 -08002971[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002972
2973PyDoc_STRVAR(os_ttyname__doc__,
Larry Hastings2623c8c2014-02-08 22:15:29 -08002974"ttyname($module, fd, /)\n"
2975"--\n"
2976"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002977"Return the name of the terminal device connected to \'fd\'.\n"
2978"\n"
Larry Hastings31826802013-10-19 00:09:25 -07002979" fd\n"
2980" Integer file descriptor handle.");
2981
2982#define OS_TTYNAME_METHODDEF \
2983 {"ttyname", (PyCFunction)os_ttyname, METH_VARARGS, os_ttyname__doc__},
2984
2985static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002986os_ttyname_impl(PyModuleDef *module, int fd);
Guido van Rossum94f6f721999-01-06 18:42:14 +00002987
2988static PyObject *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002989os_ttyname(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002990{
Larry Hastings31826802013-10-19 00:09:25 -07002991 PyObject *return_value = NULL;
2992 int fd;
2993 char *_return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002994
Larry Hastings31826802013-10-19 00:09:25 -07002995 if (!PyArg_ParseTuple(args,
2996 "i:ttyname",
2997 &fd))
2998 goto exit;
Larry Hastingsed4a1c52013-11-18 09:32:13 -08002999 _return_value = os_ttyname_impl(module, fd);
Larry Hastings31826802013-10-19 00:09:25 -07003000 if (_return_value == NULL)
3001 goto exit;
3002 return_value = PyUnicode_DecodeFSDefault(_return_value);
3003
3004exit:
3005 return return_value;
3006}
3007
3008static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08003009os_ttyname_impl(PyModuleDef *module, int fd)
Larry Hastings2623c8c2014-02-08 22:15:29 -08003010/*[clinic end generated code: output=cee7bc4cffec01a2 input=5f72ca83e76b3b45]*/
Larry Hastings31826802013-10-19 00:09:25 -07003011{
3012 char *ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003013
Larry Hastings31826802013-10-19 00:09:25 -07003014 ret = ttyname(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00003015 if (ret == NULL)
Larry Hastings31826802013-10-19 00:09:25 -07003016 posix_error();
3017 return ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00003018}
Guido van Rossumd371ff11999-01-25 16:12:23 +00003019#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00003020
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003021#ifdef HAVE_CTERMID
Larry Hastings2f936352014-08-05 14:04:04 +10003022/*[clinic input]
3023os.ctermid
3024
3025Return the name of the controlling terminal for this process.
3026[clinic start generated code]*/
3027
3028PyDoc_STRVAR(os_ctermid__doc__,
3029"ctermid($module, /)\n"
3030"--\n"
3031"\n"
3032"Return the name of the controlling terminal for this process.");
3033
3034#define OS_CTERMID_METHODDEF \
3035 {"ctermid", (PyCFunction)os_ctermid, METH_NOARGS, os_ctermid__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003036
3037static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003038os_ctermid_impl(PyModuleDef *module);
3039
3040static PyObject *
3041os_ctermid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3042{
3043 return os_ctermid_impl(module);
3044}
3045
3046static PyObject *
3047os_ctermid_impl(PyModuleDef *module)
3048/*[clinic end generated code: output=277bf7964ec2d782 input=3b87fdd52556382d]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003049{
Victor Stinner8c62be82010-05-06 00:08:46 +00003050 char *ret;
3051 char buffer[L_ctermid];
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003052
Greg Wardb48bc172000-03-01 21:51:56 +00003053#ifdef USE_CTERMID_R
Victor Stinner8c62be82010-05-06 00:08:46 +00003054 ret = ctermid_r(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003055#else
Victor Stinner8c62be82010-05-06 00:08:46 +00003056 ret = ctermid(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003057#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00003058 if (ret == NULL)
3059 return posix_error();
Victor Stinner5fe6de82010-08-15 09:12:51 +00003060 return PyUnicode_DecodeFSDefault(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003061}
Larry Hastings2f936352014-08-05 14:04:04 +10003062#endif /* HAVE_CTERMID */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00003063
Larry Hastings2f936352014-08-05 14:04:04 +10003064
3065/*[clinic input]
3066os.chdir
3067
3068 path: path_t(allow_fd='PATH_HAVE_FCHDIR')
3069
3070Change the current working directory to the specified path.
3071
3072path may always be specified as a string.
3073On some platforms, path may also be specified as an open file descriptor.
3074 If this functionality is unavailable, using it raises an exception.
3075[clinic start generated code]*/
3076
3077PyDoc_STRVAR(os_chdir__doc__,
3078"chdir($module, /, path)\n"
3079"--\n"
3080"\n"
3081"Change the current working directory to the specified path.\n"
3082"\n"
3083"path may always be specified as a string.\n"
3084"On some platforms, path may also be specified as an open file descriptor.\n"
3085" If this functionality is unavailable, using it raises an exception.");
3086
3087#define OS_CHDIR_METHODDEF \
3088 {"chdir", (PyCFunction)os_chdir, METH_VARARGS|METH_KEYWORDS, os_chdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003089
Barry Warsaw53699e91996-12-10 23:23:01 +00003090static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003091os_chdir_impl(PyModuleDef *module, path_t *path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003092
Larry Hastings2f936352014-08-05 14:04:04 +10003093static PyObject *
3094os_chdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3095{
3096 PyObject *return_value = NULL;
3097 static char *_keywords[] = {"path", NULL};
3098 path_t path = PATH_T_INITIALIZE("chdir", "path", 0, PATH_HAVE_FCHDIR);
3099
3100 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3101 "O&:chdir", _keywords,
3102 path_converter, &path))
3103 goto exit;
3104 return_value = os_chdir_impl(module, &path);
3105
3106exit:
3107 /* Cleanup for path */
3108 path_cleanup(&path);
3109
3110 return return_value;
3111}
3112
3113static PyObject *
3114os_chdir_impl(PyModuleDef *module, path_t *path)
3115/*[clinic end generated code: output=cc07592dd23ca9e0 input=1a4a15b4d12cb15d]*/
3116{
3117 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003118
3119 Py_BEGIN_ALLOW_THREADS
3120#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10003121 if (path->wide)
3122 result = win32_wchdir(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003123 else
Larry Hastings2f936352014-08-05 14:04:04 +10003124 result = win32_chdir(path->narrow);
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03003125 result = !result; /* on unix, success = 0, on windows, success = !0 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003126#else
3127#ifdef HAVE_FCHDIR
Larry Hastings2f936352014-08-05 14:04:04 +10003128 if (path->fd != -1)
3129 result = fchdir(path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003130 else
3131#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003132 result = chdir(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003133#endif
3134 Py_END_ALLOW_THREADS
3135
3136 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003137 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003138 }
3139
Larry Hastings2f936352014-08-05 14:04:04 +10003140 Py_RETURN_NONE;
3141}
3142
3143
3144#ifdef HAVE_FCHDIR
3145/*[clinic input]
3146os.fchdir
3147
3148 fd: fildes
3149
3150Change to the directory of the given file descriptor.
3151
3152fd must be opened on a directory, not a file.
3153Equivalent to os.chdir(fd).
3154
3155[clinic start generated code]*/
3156
3157PyDoc_STRVAR(os_fchdir__doc__,
3158"fchdir($module, /, fd)\n"
3159"--\n"
3160"\n"
3161"Change to the directory of the given file descriptor.\n"
3162"\n"
3163"fd must be opened on a directory, not a file.\n"
3164"Equivalent to os.chdir(fd).");
3165
3166#define OS_FCHDIR_METHODDEF \
3167 {"fchdir", (PyCFunction)os_fchdir, METH_VARARGS|METH_KEYWORDS, os_fchdir__doc__},
3168
3169static PyObject *
3170os_fchdir_impl(PyModuleDef *module, int fd);
3171
3172static PyObject *
3173os_fchdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
3174{
3175 PyObject *return_value = NULL;
3176 static char *_keywords[] = {"fd", NULL};
3177 int fd;
3178
3179 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3180 "O&:fchdir", _keywords,
3181 fildes_converter, &fd))
3182 goto exit;
3183 return_value = os_fchdir_impl(module, fd);
Georg Brandlf7875592012-06-24 13:58:31 +02003184
Larry Hastings9cf065c2012-06-22 16:30:09 -07003185exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07003186 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003187}
3188
Fred Drake4d1e64b2002-04-15 19:40:07 +00003189static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003190os_fchdir_impl(PyModuleDef *module, int fd)
3191/*[clinic end generated code: output=9f6dbc89b2778834 input=18e816479a2fa985]*/
Fred Drake4d1e64b2002-04-15 19:40:07 +00003192{
Larry Hastings2f936352014-08-05 14:04:04 +10003193 return posix_fildes_fd(fd, fchdir);
Fred Drake4d1e64b2002-04-15 19:40:07 +00003194}
3195#endif /* HAVE_FCHDIR */
3196
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003197
Larry Hastings2f936352014-08-05 14:04:04 +10003198/*[clinic input]
3199os.chmod
3200
3201 path: path_t(allow_fd='PATH_HAVE_FCHMOD')
3202 Path to be modified. May always be specified as a str or bytes.
3203 On some platforms, path may also be specified as an open file descriptor.
3204 If this functionality is unavailable, using it raises an exception.
3205
3206 mode: int
3207 Operating-system mode bitfield.
3208
3209 *
3210
3211 dir_fd : dir_fd(requires='fchmodat') = None
3212 If not None, it should be a file descriptor open to a directory,
3213 and path should be relative; path will then be relative to that
3214 directory.
3215
3216 follow_symlinks: bool = True
3217 If False, and the last element of the path is a symbolic link,
3218 chmod will modify the symbolic link itself instead of the file
3219 the link points to.
3220
3221Change the access permissions of a file.
3222
3223It is an error to use dir_fd or follow_symlinks when specifying path as
3224 an open file descriptor.
3225dir_fd and follow_symlinks may not be implemented on your platform.
3226 If they are unavailable, using them will raise a NotImplementedError.
3227
3228[clinic start generated code]*/
3229
3230PyDoc_STRVAR(os_chmod__doc__,
3231"chmod($module, /, path, mode, *, dir_fd=None, follow_symlinks=True)\n"
3232"--\n"
3233"\n"
3234"Change the access permissions of a file.\n"
3235"\n"
3236" path\n"
3237" Path to be modified. May always be specified as a str or bytes.\n"
3238" On some platforms, path may also be specified as an open file descriptor.\n"
3239" If this functionality is unavailable, using it raises an exception.\n"
3240" mode\n"
3241" Operating-system mode bitfield.\n"
3242" dir_fd\n"
3243" If not None, it should be a file descriptor open to a directory,\n"
3244" and path should be relative; path will then be relative to that\n"
3245" directory.\n"
3246" follow_symlinks\n"
3247" If False, and the last element of the path is a symbolic link,\n"
3248" chmod will modify the symbolic link itself instead of the file\n"
3249" the link points to.\n"
3250"\n"
3251"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3252" an open file descriptor.\n"
3253"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3254" If they are unavailable, using them will raise a NotImplementedError.");
3255
3256#define OS_CHMOD_METHODDEF \
3257 {"chmod", (PyCFunction)os_chmod, METH_VARARGS|METH_KEYWORDS, os_chmod__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003258
Barry Warsaw53699e91996-12-10 23:23:01 +00003259static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003260os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks);
3261
3262static PyObject *
3263os_chmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003264{
Larry Hastings2f936352014-08-05 14:04:04 +10003265 PyObject *return_value = NULL;
3266 static char *_keywords[] = {"path", "mode", "dir_fd", "follow_symlinks", NULL};
3267 path_t path = PATH_T_INITIALIZE("chmod", "path", 0, PATH_HAVE_FCHMOD);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003268 int mode;
3269 int dir_fd = DEFAULT_DIR_FD;
3270 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10003271
3272 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3273 "O&i|$O&p:chmod", _keywords,
3274 path_converter, &path, &mode, FCHMODAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3275 goto exit;
3276 return_value = os_chmod_impl(module, &path, mode, dir_fd, follow_symlinks);
3277
3278exit:
3279 /* Cleanup for path */
3280 path_cleanup(&path);
3281
3282 return return_value;
3283}
3284
3285static PyObject *
3286os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd, int follow_symlinks)
3287/*[clinic end generated code: output=1e9db031aea46422 input=7f1618e5e15cc196]*/
3288{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003289 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003290
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003291#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003292 DWORD attr;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003293#endif
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00003294
Larry Hastings9cf065c2012-06-22 16:30:09 -07003295#ifdef HAVE_FCHMODAT
3296 int fchmodat_nofollow_unsupported = 0;
3297#endif
3298
Larry Hastings9cf065c2012-06-22 16:30:09 -07003299#if !(defined(HAVE_FCHMODAT) || defined(HAVE_LCHMOD))
3300 if (follow_symlinks_specified("chmod", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003301 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003302#endif
3303
3304#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003305 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003306 if (path->wide)
3307 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003308 else
Larry Hastings2f936352014-08-05 14:04:04 +10003309 attr = GetFileAttributesA(path->narrow);
Tim Golden23005082013-10-25 11:22:37 +01003310 if (attr == INVALID_FILE_ATTRIBUTES)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003311 result = 0;
3312 else {
3313 if (mode & _S_IWRITE)
Victor Stinner8c62be82010-05-06 00:08:46 +00003314 attr &= ~FILE_ATTRIBUTE_READONLY;
3315 else
3316 attr |= FILE_ATTRIBUTE_READONLY;
Larry Hastings2f936352014-08-05 14:04:04 +10003317 if (path->wide)
3318 result = SetFileAttributesW(path->wide, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003319 else
Larry Hastings2f936352014-08-05 14:04:04 +10003320 result = SetFileAttributesA(path->narrow, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003321 }
3322 Py_END_ALLOW_THREADS
3323
3324 if (!result) {
Larry Hastings2f936352014-08-05 14:04:04 +10003325 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003326 }
3327#else /* MS_WINDOWS */
3328 Py_BEGIN_ALLOW_THREADS
3329#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003330 if (path->fd != -1)
3331 result = fchmod(path->fd, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003332 else
3333#endif
3334#ifdef HAVE_LCHMOD
3335 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003336 result = lchmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003337 else
3338#endif
3339#ifdef HAVE_FCHMODAT
3340 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks) {
3341 /*
3342 * fchmodat() doesn't currently support AT_SYMLINK_NOFOLLOW!
3343 * The documentation specifically shows how to use it,
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003344 * and then says it isn't implemented yet.
3345 * (true on linux with glibc 2.15, and openindiana 3.x)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003346 *
3347 * Once it is supported, os.chmod will automatically
3348 * support dir_fd and follow_symlinks=False. (Hopefully.)
3349 * Until then, we need to be careful what exception we raise.
3350 */
Larry Hastings2f936352014-08-05 14:04:04 +10003351 result = fchmodat(dir_fd, path->narrow, mode,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003352 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3353 /*
3354 * But wait! We can't throw the exception without allowing threads,
3355 * and we can't do that in this nested scope. (Macro trickery, sigh.)
3356 */
3357 fchmodat_nofollow_unsupported =
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07003358 result &&
3359 ((errno == ENOTSUP) || (errno == EOPNOTSUPP)) &&
3360 !follow_symlinks;
Victor Stinner8c62be82010-05-06 00:08:46 +00003361 }
3362 else
Thomas Wouters477c8d52006-05-27 19:21:47 +00003363#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003364 result = chmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003365 Py_END_ALLOW_THREADS
3366
3367 if (result) {
3368#ifdef HAVE_FCHMODAT
3369 if (fchmodat_nofollow_unsupported) {
3370 if (dir_fd != DEFAULT_DIR_FD)
3371 dir_fd_and_follow_symlinks_invalid("chmod",
3372 dir_fd, follow_symlinks);
3373 else
3374 follow_symlinks_specified("chmod", follow_symlinks);
3375 }
3376 else
3377#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003378 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003379 }
3380#endif
3381
Larry Hastings2f936352014-08-05 14:04:04 +10003382 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003383}
3384
Larry Hastings9cf065c2012-06-22 16:30:09 -07003385
Christian Heimes4e30a842007-11-30 22:12:06 +00003386#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003387/*[clinic input]
3388os.fchmod
3389
3390 fd: int
3391 mode: int
3392
3393Change the access permissions of the file given by file descriptor fd.
3394
3395Equivalent to os.chmod(fd, mode).
3396[clinic start generated code]*/
3397
3398PyDoc_STRVAR(os_fchmod__doc__,
3399"fchmod($module, /, fd, mode)\n"
3400"--\n"
3401"\n"
3402"Change the access permissions of the file given by file descriptor fd.\n"
3403"\n"
3404"Equivalent to os.chmod(fd, mode).");
3405
3406#define OS_FCHMOD_METHODDEF \
3407 {"fchmod", (PyCFunction)os_fchmod, METH_VARARGS|METH_KEYWORDS, os_fchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003408
3409static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003410os_fchmod_impl(PyModuleDef *module, int fd, int mode);
3411
3412static PyObject *
3413os_fchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003414{
Larry Hastings2f936352014-08-05 14:04:04 +10003415 PyObject *return_value = NULL;
3416 static char *_keywords[] = {"fd", "mode", NULL};
3417 int fd;
3418 int mode;
3419
3420 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3421 "ii:fchmod", _keywords,
3422 &fd, &mode))
3423 goto exit;
3424 return_value = os_fchmod_impl(module, fd, mode);
3425
3426exit:
3427 return return_value;
3428}
3429
3430static PyObject *
3431os_fchmod_impl(PyModuleDef *module, int fd, int mode)
3432/*[clinic end generated code: output=3c19fbfd724a8e0f input=8ab11975ca01ee5b]*/
3433{
3434 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003435 Py_BEGIN_ALLOW_THREADS
3436 res = fchmod(fd, mode);
3437 Py_END_ALLOW_THREADS
3438 if (res < 0)
3439 return posix_error();
3440 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003441}
3442#endif /* HAVE_FCHMOD */
3443
Larry Hastings2f936352014-08-05 14:04:04 +10003444
Christian Heimes4e30a842007-11-30 22:12:06 +00003445#ifdef HAVE_LCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10003446/*[clinic input]
3447os.lchmod
3448
3449 path: path_t
3450 mode: int
3451
3452Change the access permissions of a file, without following symbolic links.
3453
3454If path is a symlink, this affects the link itself rather than the target.
3455Equivalent to chmod(path, mode, follow_symlinks=False)."
3456[clinic start generated code]*/
3457
3458PyDoc_STRVAR(os_lchmod__doc__,
3459"lchmod($module, /, path, mode)\n"
3460"--\n"
3461"\n"
3462"Change the access permissions of a file, without following symbolic links.\n"
3463"\n"
3464"If path is a symlink, this affects the link itself rather than the target.\n"
3465"Equivalent to chmod(path, mode, follow_symlinks=False).\"");
3466
3467#define OS_LCHMOD_METHODDEF \
3468 {"lchmod", (PyCFunction)os_lchmod, METH_VARARGS|METH_KEYWORDS, os_lchmod__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00003469
3470static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003471os_lchmod_impl(PyModuleDef *module, path_t *path, int mode);
3472
3473static PyObject *
3474os_lchmod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00003475{
Larry Hastings2f936352014-08-05 14:04:04 +10003476 PyObject *return_value = NULL;
3477 static char *_keywords[] = {"path", "mode", NULL};
3478 path_t path = PATH_T_INITIALIZE("lchmod", "path", 0, 0);
3479 int mode;
3480
3481 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3482 "O&i:lchmod", _keywords,
3483 path_converter, &path, &mode))
3484 goto exit;
3485 return_value = os_lchmod_impl(module, &path, mode);
3486
3487exit:
3488 /* Cleanup for path */
3489 path_cleanup(&path);
3490
3491 return return_value;
3492}
3493
3494static PyObject *
3495os_lchmod_impl(PyModuleDef *module, path_t *path, int mode)
3496/*[clinic end generated code: output=2849977d65f8c68c input=90c5663c7465d24f]*/
3497{
Victor Stinner8c62be82010-05-06 00:08:46 +00003498 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003499 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003500 res = lchmod(path->narrow, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +00003501 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003502 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003503 path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003504 return NULL;
3505 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003506 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003507}
3508#endif /* HAVE_LCHMOD */
3509
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003510
Thomas Wouterscf297e42007-02-23 15:07:44 +00003511#ifdef HAVE_CHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003512/*[clinic input]
3513os.chflags
3514
3515 path: path_t
3516 flags: unsigned_long(bitwise=True)
3517 follow_symlinks: bool=True
3518
3519Set file flags.
3520
3521If follow_symlinks is False, and the last element of the path is a symbolic
3522 link, chflags will change flags on the symbolic link itself instead of the
3523 file the link points to.
3524follow_symlinks may not be implemented on your platform. If it is
3525unavailable, using it will raise a NotImplementedError.
3526
3527[clinic start generated code]*/
3528
3529PyDoc_STRVAR(os_chflags__doc__,
3530"chflags($module, /, path, flags, follow_symlinks=True)\n"
3531"--\n"
3532"\n"
3533"Set file flags.\n"
3534"\n"
3535"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3536" link, chflags will change flags on the symbolic link itself instead of the\n"
3537" file the link points to.\n"
3538"follow_symlinks may not be implemented on your platform. If it is\n"
3539"unavailable, using it will raise a NotImplementedError.");
3540
3541#define OS_CHFLAGS_METHODDEF \
3542 {"chflags", (PyCFunction)os_chflags, METH_VARARGS|METH_KEYWORDS, os_chflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003543
3544static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003545os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks);
3546
3547static PyObject *
3548os_chflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003549{
Larry Hastings2f936352014-08-05 14:04:04 +10003550 PyObject *return_value = NULL;
3551 static char *_keywords[] = {"path", "flags", "follow_symlinks", NULL};
3552 path_t path = PATH_T_INITIALIZE("chflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003553 unsigned long flags;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003554 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003555
Larry Hastings2f936352014-08-05 14:04:04 +10003556 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3557 "O&k|p:chflags", _keywords,
3558 path_converter, &path, &flags, &follow_symlinks))
3559 goto exit;
3560 return_value = os_chflags_impl(module, &path, flags, follow_symlinks);
3561
3562exit:
3563 /* Cleanup for path */
3564 path_cleanup(&path);
3565
3566 return return_value;
3567}
3568
3569static PyObject *
3570os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags, int follow_symlinks)
3571/*[clinic end generated code: output=2767927bf071e3cf input=0327e29feb876236]*/
3572{
3573 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003574
3575#ifndef HAVE_LCHFLAGS
3576 if (follow_symlinks_specified("chflags", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003577 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003578#endif
3579
Victor Stinner8c62be82010-05-06 00:08:46 +00003580 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003581#ifdef HAVE_LCHFLAGS
3582 if (!follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10003583 result = lchflags(path->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003584 else
3585#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003586 result = chflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003587 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003588
Larry Hastings2f936352014-08-05 14:04:04 +10003589 if (result)
3590 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003591
Larry Hastings2f936352014-08-05 14:04:04 +10003592 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003593}
3594#endif /* HAVE_CHFLAGS */
3595
Larry Hastings2f936352014-08-05 14:04:04 +10003596
Thomas Wouterscf297e42007-02-23 15:07:44 +00003597#ifdef HAVE_LCHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10003598/*[clinic input]
3599os.lchflags
3600
3601 path: path_t
3602 flags: unsigned_long(bitwise=True)
3603
3604Set file flags.
3605
3606This function will not follow symbolic links.
3607Equivalent to chflags(path, flags, follow_symlinks=False).
3608[clinic start generated code]*/
3609
3610PyDoc_STRVAR(os_lchflags__doc__,
3611"lchflags($module, /, path, flags)\n"
3612"--\n"
3613"\n"
3614"Set file flags.\n"
3615"\n"
3616"This function will not follow symbolic links.\n"
3617"Equivalent to chflags(path, flags, follow_symlinks=False).");
3618
3619#define OS_LCHFLAGS_METHODDEF \
3620 {"lchflags", (PyCFunction)os_lchflags, METH_VARARGS|METH_KEYWORDS, os_lchflags__doc__},
Thomas Wouterscf297e42007-02-23 15:07:44 +00003621
3622static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003623os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags);
3624
3625static PyObject *
3626os_lchflags(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouterscf297e42007-02-23 15:07:44 +00003627{
Larry Hastings2f936352014-08-05 14:04:04 +10003628 PyObject *return_value = NULL;
3629 static char *_keywords[] = {"path", "flags", NULL};
3630 path_t path = PATH_T_INITIALIZE("lchflags", "path", 0, 0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003631 unsigned long flags;
Larry Hastings2f936352014-08-05 14:04:04 +10003632
3633 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3634 "O&k:lchflags", _keywords,
3635 path_converter, &path, &flags))
3636 goto exit;
3637 return_value = os_lchflags_impl(module, &path, flags);
3638
3639exit:
3640 /* Cleanup for path */
3641 path_cleanup(&path);
3642
3643 return return_value;
3644}
3645
3646static PyObject *
3647os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags)
3648/*[clinic end generated code: output=bb93b6b8a5e45aa7 input=f9f82ea8b585ca9d]*/
3649{
Victor Stinner8c62be82010-05-06 00:08:46 +00003650 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003651 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003652 res = lchflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003653 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003654 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003655 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003656 }
Victor Stinner292c8352012-10-30 02:17:38 +01003657 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003658}
3659#endif /* HAVE_LCHFLAGS */
3660
Larry Hastings2f936352014-08-05 14:04:04 +10003661
Martin v. Löwis244edc82001-10-04 22:44:26 +00003662#ifdef HAVE_CHROOT
Larry Hastings2f936352014-08-05 14:04:04 +10003663/*[clinic input]
3664os.chroot
3665 path: path_t
3666
3667Change root directory to path.
3668
3669[clinic start generated code]*/
3670
3671PyDoc_STRVAR(os_chroot__doc__,
3672"chroot($module, /, path)\n"
3673"--\n"
3674"\n"
3675"Change root directory to path.");
3676
3677#define OS_CHROOT_METHODDEF \
3678 {"chroot", (PyCFunction)os_chroot, METH_VARARGS|METH_KEYWORDS, os_chroot__doc__},
Martin v. Löwis244edc82001-10-04 22:44:26 +00003679
3680static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003681os_chroot_impl(PyModuleDef *module, path_t *path);
3682
3683static PyObject *
3684os_chroot(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis244edc82001-10-04 22:44:26 +00003685{
Larry Hastings2f936352014-08-05 14:04:04 +10003686 PyObject *return_value = NULL;
3687 static char *_keywords[] = {"path", NULL};
3688 path_t path = PATH_T_INITIALIZE("chroot", "path", 0, 0);
3689
3690 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3691 "O&:chroot", _keywords,
3692 path_converter, &path))
3693 goto exit;
3694 return_value = os_chroot_impl(module, &path);
3695
3696exit:
3697 /* Cleanup for path */
3698 path_cleanup(&path);
3699
3700 return return_value;
Martin v. Löwis244edc82001-10-04 22:44:26 +00003701}
Larry Hastings2f936352014-08-05 14:04:04 +10003702
3703static PyObject *
3704os_chroot_impl(PyModuleDef *module, path_t *path)
3705/*[clinic end generated code: output=15b1256cbe4f24a1 input=14822965652c3dc3]*/
3706{
3707 int res;
3708 Py_BEGIN_ALLOW_THREADS
3709 res = chroot(path->narrow);
3710 Py_END_ALLOW_THREADS
3711 if (res < 0)
3712 return path_error(path);
3713 Py_RETURN_NONE;
3714}
3715#endif /* HAVE_CHROOT */
3716
Martin v. Löwis244edc82001-10-04 22:44:26 +00003717
Guido van Rossum21142a01999-01-08 21:05:37 +00003718#ifdef HAVE_FSYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003719/*[clinic input]
3720os.fsync
3721
3722 fd: fildes
3723
3724Force write of fd to disk.
3725[clinic start generated code]*/
3726
3727PyDoc_STRVAR(os_fsync__doc__,
3728"fsync($module, /, fd)\n"
3729"--\n"
3730"\n"
3731"Force write of fd to disk.");
3732
3733#define OS_FSYNC_METHODDEF \
3734 {"fsync", (PyCFunction)os_fsync, METH_VARARGS|METH_KEYWORDS, os_fsync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003735
3736static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003737os_fsync_impl(PyModuleDef *module, int fd);
3738
3739static PyObject *
3740os_fsync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003741{
Larry Hastings2f936352014-08-05 14:04:04 +10003742 PyObject *return_value = NULL;
3743 static char *_keywords[] = {"fd", NULL};
3744 int fd;
3745
3746 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3747 "O&:fsync", _keywords,
3748 fildes_converter, &fd))
3749 goto exit;
3750 return_value = os_fsync_impl(module, fd);
3751
3752exit:
3753 return return_value;
3754}
3755
3756static PyObject *
3757os_fsync_impl(PyModuleDef *module, int fd)
3758/*[clinic end generated code: output=59f32d3a0b360133 input=21c3645c056967f2]*/
3759{
3760 return posix_fildes_fd(fd, fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003761}
3762#endif /* HAVE_FSYNC */
3763
Larry Hastings2f936352014-08-05 14:04:04 +10003764
Ross Lagerwall7807c352011-03-17 20:20:30 +02003765#ifdef HAVE_SYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003766/*[clinic input]
3767os.sync
3768
3769Force write of everything to disk.
3770[clinic start generated code]*/
3771
3772PyDoc_STRVAR(os_sync__doc__,
3773"sync($module, /)\n"
3774"--\n"
3775"\n"
3776"Force write of everything to disk.");
3777
3778#define OS_SYNC_METHODDEF \
3779 {"sync", (PyCFunction)os_sync, METH_NOARGS, os_sync__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02003780
3781static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003782os_sync_impl(PyModuleDef *module);
3783
3784static PyObject *
3785os_sync(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
3786{
3787 return os_sync_impl(module);
3788}
3789
3790static PyObject *
3791os_sync_impl(PyModuleDef *module)
3792/*[clinic end generated code: output=526c495683d0bb38 input=84749fe5e9b404ff]*/
Ross Lagerwall7807c352011-03-17 20:20:30 +02003793{
3794 Py_BEGIN_ALLOW_THREADS
3795 sync();
3796 Py_END_ALLOW_THREADS
3797 Py_RETURN_NONE;
3798}
Larry Hastings2f936352014-08-05 14:04:04 +10003799#endif /* HAVE_SYNC */
3800
Ross Lagerwall7807c352011-03-17 20:20:30 +02003801
Guido van Rossum21142a01999-01-08 21:05:37 +00003802#ifdef HAVE_FDATASYNC
Guido van Rossum7f58e2e2000-09-22 17:26:14 +00003803#ifdef __hpux
Guido van Rossumecc23b02000-09-22 16:01:05 +00003804extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
3805#endif
3806
Larry Hastings2f936352014-08-05 14:04:04 +10003807/*[clinic input]
3808os.fdatasync
3809
3810 fd: fildes
3811
3812Force write of fd to disk without forcing update of metadata.
3813[clinic start generated code]*/
3814
3815PyDoc_STRVAR(os_fdatasync__doc__,
3816"fdatasync($module, /, fd)\n"
3817"--\n"
3818"\n"
3819"Force write of fd to disk without forcing update of metadata.");
3820
3821#define OS_FDATASYNC_METHODDEF \
3822 {"fdatasync", (PyCFunction)os_fdatasync, METH_VARARGS|METH_KEYWORDS, os_fdatasync__doc__},
Guido van Rossum21142a01999-01-08 21:05:37 +00003823
3824static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003825os_fdatasync_impl(PyModuleDef *module, int fd);
3826
3827static PyObject *
3828os_fdatasync(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum21142a01999-01-08 21:05:37 +00003829{
Larry Hastings2f936352014-08-05 14:04:04 +10003830 PyObject *return_value = NULL;
3831 static char *_keywords[] = {"fd", NULL};
3832 int fd;
3833
3834 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3835 "O&:fdatasync", _keywords,
3836 fildes_converter, &fd))
3837 goto exit;
3838 return_value = os_fdatasync_impl(module, fd);
3839
3840exit:
3841 return return_value;
3842}
3843
3844static PyObject *
3845os_fdatasync_impl(PyModuleDef *module, int fd)
3846/*[clinic end generated code: output=2335fdfd37c92180 input=bc74791ee54dd291]*/
3847{
3848 return posix_fildes_fd(fd, fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003849}
3850#endif /* HAVE_FDATASYNC */
3851
3852
Fredrik Lundh10723342000-07-10 16:38:09 +00003853#ifdef HAVE_CHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003854/*[clinic input]
3855os.chown
3856
3857 path : path_t(allow_fd='PATH_HAVE_FCHOWN')
3858 Path to be examined; can be string, bytes, or open-file-descriptor int.
3859
3860 uid: uid_t
3861
3862 gid: gid_t
3863
3864 *
3865
3866 dir_fd : dir_fd(requires='fchownat') = None
3867 If not None, it should be a file descriptor open to a directory,
3868 and path should be relative; path will then be relative to that
3869 directory.
3870
3871 follow_symlinks: bool = True
3872 If False, and the last element of the path is a symbolic link,
3873 stat will examine the symbolic link itself instead of the file
3874 the link points to.
3875
3876Change the owner and group id of path to the numeric uid and gid.\
3877
3878path may always be specified as a string.
3879On some platforms, path may also be specified as an open file descriptor.
3880 If this functionality is unavailable, using it raises an exception.
3881If dir_fd is not None, it should be a file descriptor open to a directory,
3882 and path should be relative; path will then be relative to that directory.
3883If follow_symlinks is False, and the last element of the path is a symbolic
3884 link, chown will modify the symbolic link itself instead of the file the
3885 link points to.
3886It is an error to use dir_fd or follow_symlinks when specifying path as
3887 an open file descriptor.
3888dir_fd and follow_symlinks may not be implemented on your platform.
3889 If they are unavailable, using them will raise a NotImplementedError.
3890
3891[clinic start generated code]*/
3892
3893PyDoc_STRVAR(os_chown__doc__,
3894"chown($module, /, path, uid, gid, *, dir_fd=None, follow_symlinks=True)\n"
3895"--\n"
3896"\n"
3897"Change the owner and group id of path to the numeric uid and gid.\\\n"
3898"\n"
3899" path\n"
3900" Path to be examined; can be string, bytes, or open-file-descriptor int.\n"
3901" dir_fd\n"
3902" If not None, it should be a file descriptor open to a directory,\n"
3903" and path should be relative; path will then be relative to that\n"
3904" directory.\n"
3905" follow_symlinks\n"
3906" If False, and the last element of the path is a symbolic link,\n"
3907" stat will examine the symbolic link itself instead of the file\n"
3908" the link points to.\n"
3909"\n"
3910"path may always be specified as a string.\n"
3911"On some platforms, path may also be specified as an open file descriptor.\n"
3912" If this functionality is unavailable, using it raises an exception.\n"
3913"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
3914" and path should be relative; path will then be relative to that directory.\n"
3915"If follow_symlinks is False, and the last element of the path is a symbolic\n"
3916" link, chown will modify the symbolic link itself instead of the file the\n"
3917" link points to.\n"
3918"It is an error to use dir_fd or follow_symlinks when specifying path as\n"
3919" an open file descriptor.\n"
3920"dir_fd and follow_symlinks may not be implemented on your platform.\n"
3921" If they are unavailable, using them will raise a NotImplementedError.");
3922
3923#define OS_CHOWN_METHODDEF \
3924 {"chown", (PyCFunction)os_chown, METH_VARARGS|METH_KEYWORDS, os_chown__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003925
Barry Warsaw53699e91996-12-10 23:23:01 +00003926static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10003927os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks);
3928
3929static PyObject *
3930os_chown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumb6775db1994-08-01 11:34:53 +00003931{
Larry Hastings2f936352014-08-05 14:04:04 +10003932 PyObject *return_value = NULL;
3933 static char *_keywords[] = {"path", "uid", "gid", "dir_fd", "follow_symlinks", NULL};
3934 path_t path = PATH_T_INITIALIZE("chown", "path", 0, PATH_HAVE_FCHOWN);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003935 uid_t uid;
3936 gid_t gid;
3937 int dir_fd = DEFAULT_DIR_FD;
3938 int follow_symlinks = 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003939
Larry Hastings2f936352014-08-05 14:04:04 +10003940 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
3941 "O&O&O&|$O&p:chown", _keywords,
3942 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid, FCHOWNAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
3943 goto exit;
3944 return_value = os_chown_impl(module, &path, uid, gid, dir_fd, follow_symlinks);
3945
3946exit:
3947 /* Cleanup for path */
3948 path_cleanup(&path);
3949
3950 return return_value;
3951}
3952
3953static PyObject *
3954os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid, int dir_fd, int follow_symlinks)
3955/*[clinic end generated code: output=22f011e3b4f9ff49 input=a61cc35574814d5d]*/
3956{
3957 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003958
3959#if !(defined(HAVE_LCHOWN) || defined(HAVE_FCHOWNAT))
3960 if (follow_symlinks_specified("chown", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003961 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003962#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003963 if (dir_fd_and_fd_invalid("chown", dir_fd, path->fd) ||
3964 fd_and_follow_symlinks_invalid("chown", path->fd, follow_symlinks))
3965 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003966
3967#ifdef __APPLE__
3968 /*
3969 * This is for Mac OS X 10.3, which doesn't have lchown.
3970 * (But we still have an lchown symbol because of weak-linking.)
3971 * It doesn't have fchownat either. So there's no possibility
3972 * of a graceful failover.
Georg Brandlf7875592012-06-24 13:58:31 +02003973 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003974 if ((!follow_symlinks) && (lchown == NULL)) {
3975 follow_symlinks_specified("chown", follow_symlinks);
Larry Hastings2f936352014-08-05 14:04:04 +10003976 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003977 }
3978#endif
3979
Victor Stinner8c62be82010-05-06 00:08:46 +00003980 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003981#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003982 if (path->fd != -1)
3983 result = fchown(path->fd, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003984 else
3985#endif
3986#ifdef HAVE_LCHOWN
3987 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003988 result = lchown(path->narrow, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003989 else
3990#endif
3991#ifdef HAVE_FCHOWNAT
3992 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003993 result = fchownat(dir_fd, path->narrow, uid, gid,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003994 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3995 else
3996#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003997 result = chown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00003998 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003999
Larry Hastings2f936352014-08-05 14:04:04 +10004000 if (result)
4001 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004002
Larry Hastings2f936352014-08-05 14:04:04 +10004003 Py_RETURN_NONE;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004004}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004005#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00004006
Larry Hastings2f936352014-08-05 14:04:04 +10004007
Christian Heimes4e30a842007-11-30 22:12:06 +00004008#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004009/*[clinic input]
4010os.fchown
4011
4012 fd: int
4013 uid: uid_t
4014 gid: gid_t
4015
4016Change the owner and group id of the file specified by file descriptor.
4017
4018Equivalent to os.chown(fd, uid, gid).
4019
4020[clinic start generated code]*/
4021
4022PyDoc_STRVAR(os_fchown__doc__,
4023"fchown($module, /, fd, uid, gid)\n"
4024"--\n"
4025"\n"
4026"Change the owner and group id of the file specified by file descriptor.\n"
4027"\n"
4028"Equivalent to os.chown(fd, uid, gid).");
4029
4030#define OS_FCHOWN_METHODDEF \
4031 {"fchown", (PyCFunction)os_fchown, METH_VARARGS|METH_KEYWORDS, os_fchown__doc__},
Christian Heimes4e30a842007-11-30 22:12:06 +00004032
4033static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004034os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid);
4035
4036static PyObject *
4037os_fchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Christian Heimes4e30a842007-11-30 22:12:06 +00004038{
Larry Hastings2f936352014-08-05 14:04:04 +10004039 PyObject *return_value = NULL;
4040 static char *_keywords[] = {"fd", "uid", "gid", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00004041 int fd;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004042 uid_t uid;
4043 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004044
4045 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4046 "iO&O&:fchown", _keywords,
4047 &fd, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4048 goto exit;
4049 return_value = os_fchown_impl(module, fd, uid, gid);
4050
4051exit:
4052 return return_value;
4053}
4054
4055static PyObject *
4056os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid)
4057/*[clinic end generated code: output=687781cb7d8974d6 input=3af544ba1b13a0d7]*/
4058{
Victor Stinner8c62be82010-05-06 00:08:46 +00004059 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004060 Py_BEGIN_ALLOW_THREADS
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004061 res = fchown(fd, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004062 Py_END_ALLOW_THREADS
4063 if (res < 0)
4064 return posix_error();
4065 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00004066}
4067#endif /* HAVE_FCHOWN */
4068
Larry Hastings2f936352014-08-05 14:04:04 +10004069
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004070#ifdef HAVE_LCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10004071/*[clinic input]
4072os.lchown
4073
4074 path : path_t
4075 uid: uid_t
4076 gid: gid_t
4077
4078Change the owner and group id of path to the numeric uid and gid.
4079
4080This function will not follow symbolic links.
4081Equivalent to os.chown(path, uid, gid, follow_symlinks=False).
4082[clinic start generated code]*/
4083
4084PyDoc_STRVAR(os_lchown__doc__,
4085"lchown($module, /, path, uid, gid)\n"
4086"--\n"
4087"\n"
4088"Change the owner and group id of path to the numeric uid and gid.\n"
4089"\n"
4090"This function will not follow symbolic links.\n"
4091"Equivalent to os.chown(path, uid, gid, follow_symlinks=False).");
4092
4093#define OS_LCHOWN_METHODDEF \
4094 {"lchown", (PyCFunction)os_lchown, METH_VARARGS|METH_KEYWORDS, os_lchown__doc__},
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004095
4096static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004097os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid);
4098
4099static PyObject *
4100os_lchown(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004101{
Larry Hastings2f936352014-08-05 14:04:04 +10004102 PyObject *return_value = NULL;
4103 static char *_keywords[] = {"path", "uid", "gid", NULL};
4104 path_t path = PATH_T_INITIALIZE("lchown", "path", 0, 0);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02004105 uid_t uid;
4106 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10004107
4108 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4109 "O&O&O&:lchown", _keywords,
4110 path_converter, &path, _Py_Uid_Converter, &uid, _Py_Gid_Converter, &gid))
4111 goto exit;
4112 return_value = os_lchown_impl(module, &path, uid, gid);
4113
4114exit:
4115 /* Cleanup for path */
4116 path_cleanup(&path);
4117
4118 return return_value;
4119}
4120
4121static PyObject *
4122os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid)
4123/*[clinic end generated code: output=bf25fdb0d25130e2 input=b1c6014d563a7161]*/
4124{
Victor Stinner8c62be82010-05-06 00:08:46 +00004125 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00004126 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004127 res = lchown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00004128 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01004129 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10004130 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01004131 }
Larry Hastings2f936352014-08-05 14:04:04 +10004132 Py_RETURN_NONE;
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00004133}
4134#endif /* HAVE_LCHOWN */
4135
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004136
Barry Warsaw53699e91996-12-10 23:23:01 +00004137static PyObject *
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004138posix_getcwd(int use_bytes)
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004139{
Victor Stinner8c62be82010-05-06 00:08:46 +00004140 char buf[1026];
4141 char *res;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004142
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004143#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00004144 if (!use_bytes) {
4145 wchar_t wbuf[1026];
4146 wchar_t *wbuf2 = wbuf;
4147 PyObject *resobj;
4148 DWORD len;
4149 Py_BEGIN_ALLOW_THREADS
Victor Stinner75875072013-11-24 19:23:25 +01004150 len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004151 /* If the buffer is large enough, len does not include the
4152 terminating \0. If the buffer is too small, len includes
4153 the space needed for the terminator. */
Victor Stinner75875072013-11-24 19:23:25 +01004154 if (len >= Py_ARRAY_LENGTH(wbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004155 wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004156 if (wbuf2)
4157 len = GetCurrentDirectoryW(len, wbuf2);
4158 }
4159 Py_END_ALLOW_THREADS
4160 if (!wbuf2) {
4161 PyErr_NoMemory();
4162 return NULL;
4163 }
4164 if (!len) {
Victor Stinnerb024e842012-10-31 22:24:06 +01004165 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004166 PyMem_RawFree(wbuf2);
Victor Stinnerb024e842012-10-31 22:24:06 +01004167 return PyErr_SetFromWindowsErr(0);
Victor Stinner8c62be82010-05-06 00:08:46 +00004168 }
4169 resobj = PyUnicode_FromWideChar(wbuf2, len);
Victor Stinnerb024e842012-10-31 22:24:06 +01004170 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004171 PyMem_RawFree(wbuf2);
Victor Stinner8c62be82010-05-06 00:08:46 +00004172 return resobj;
4173 }
Victor Stinnerf7c5ae22011-11-16 23:43:07 +01004174
4175 if (win32_warn_bytes_api())
4176 return NULL;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004177#endif
4178
Victor Stinner8c62be82010-05-06 00:08:46 +00004179 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004180 res = getcwd(buf, sizeof buf);
Victor Stinner8c62be82010-05-06 00:08:46 +00004181 Py_END_ALLOW_THREADS
4182 if (res == NULL)
4183 return posix_error();
4184 if (use_bytes)
4185 return PyBytes_FromStringAndSize(buf, strlen(buf));
Victor Stinner97c18ab2010-05-07 16:34:53 +00004186 return PyUnicode_DecodeFSDefault(buf);
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004187}
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004188
Larry Hastings2f936352014-08-05 14:04:04 +10004189
4190/*[clinic input]
4191os.getcwd
4192
4193Return a unicode string representing the current working directory.
4194[clinic start generated code]*/
4195
4196PyDoc_STRVAR(os_getcwd__doc__,
4197"getcwd($module, /)\n"
4198"--\n"
4199"\n"
4200"Return a unicode string representing the current working directory.");
4201
4202#define OS_GETCWD_METHODDEF \
4203 {"getcwd", (PyCFunction)os_getcwd, METH_NOARGS, os_getcwd__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004204
4205static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004206os_getcwd_impl(PyModuleDef *module);
4207
4208static PyObject *
4209os_getcwd(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4210{
4211 return os_getcwd_impl(module);
4212}
4213
4214static PyObject *
4215os_getcwd_impl(PyModuleDef *module)
4216/*[clinic end generated code: output=d70b281db5c78ff7 input=f069211bb70e3d39]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004217{
4218 return posix_getcwd(0);
4219}
4220
Larry Hastings2f936352014-08-05 14:04:04 +10004221
4222/*[clinic input]
4223os.getcwdb
4224
4225Return a bytes string representing the current working directory.
4226[clinic start generated code]*/
4227
4228PyDoc_STRVAR(os_getcwdb__doc__,
4229"getcwdb($module, /)\n"
4230"--\n"
4231"\n"
4232"Return a bytes string representing the current working directory.");
4233
4234#define OS_GETCWDB_METHODDEF \
4235 {"getcwdb", (PyCFunction)os_getcwdb, METH_NOARGS, os_getcwdb__doc__},
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004236
4237static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004238os_getcwdb_impl(PyModuleDef *module);
4239
4240static PyObject *
4241os_getcwdb(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
4242{
4243 return os_getcwdb_impl(module);
4244}
4245
4246static PyObject *
4247os_getcwdb_impl(PyModuleDef *module)
4248/*[clinic end generated code: output=75da47f2d75f9166 input=f6f6a378dad3d9cb]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00004249{
4250 return posix_getcwd(1);
4251}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004252
Larry Hastings2f936352014-08-05 14:04:04 +10004253
Larry Hastings9cf065c2012-06-22 16:30:09 -07004254#if ((!defined(HAVE_LINK)) && defined(MS_WINDOWS))
4255#define HAVE_LINK 1
4256#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004257
Guido van Rossumb6775db1994-08-01 11:34:53 +00004258#ifdef HAVE_LINK
Larry Hastings2f936352014-08-05 14:04:04 +10004259/*[clinic input]
4260
4261os.link
4262
4263 src : path_t
4264 dst : path_t
4265 *
4266 src_dir_fd : dir_fd = None
4267 dst_dir_fd : dir_fd = None
4268 follow_symlinks: bool = True
4269
4270Create a hard link to a file.
4271
4272If either src_dir_fd or dst_dir_fd is not None, it should be a file
4273 descriptor open to a directory, and the respective path string (src or dst)
4274 should be relative; the path will then be relative to that directory.
4275If follow_symlinks is False, and the last element of src is a symbolic
4276 link, link will create a link to the symbolic link itself instead of the
4277 file the link points to.
4278src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your
4279 platform. If they are unavailable, using them will raise a
4280 NotImplementedError.
4281[clinic start generated code]*/
4282
4283PyDoc_STRVAR(os_link__doc__,
4284"link($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None,\n"
4285" follow_symlinks=True)\n"
4286"--\n"
4287"\n"
4288"Create a hard link to a file.\n"
4289"\n"
4290"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
4291" descriptor open to a directory, and the respective path string (src or dst)\n"
4292" should be relative; the path will then be relative to that directory.\n"
4293"If follow_symlinks is False, and the last element of src is a symbolic\n"
4294" link, link will create a link to the symbolic link itself instead of the\n"
4295" file the link points to.\n"
4296"src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your\n"
4297" platform. If they are unavailable, using them will raise a\n"
4298" NotImplementedError.");
4299
4300#define OS_LINK_METHODDEF \
4301 {"link", (PyCFunction)os_link, METH_VARARGS|METH_KEYWORDS, os_link__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004302
Barry Warsaw53699e91996-12-10 23:23:01 +00004303static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004304os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks);
4305
4306static PyObject *
4307os_link(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004308{
Larry Hastings2f936352014-08-05 14:04:04 +10004309 PyObject *return_value = NULL;
4310 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", "follow_symlinks", NULL};
4311 path_t src = PATH_T_INITIALIZE("link", "src", 0, 0);
4312 path_t dst = PATH_T_INITIALIZE("link", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004313 int src_dir_fd = DEFAULT_DIR_FD;
4314 int dst_dir_fd = DEFAULT_DIR_FD;
4315 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +10004316
4317 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4318 "O&O&|$O&O&p:link", _keywords,
4319 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd, &follow_symlinks))
4320 goto exit;
4321 return_value = os_link_impl(module, &src, &dst, src_dir_fd, dst_dir_fd, follow_symlinks);
4322
4323exit:
4324 /* Cleanup for src */
4325 path_cleanup(&src);
4326 /* Cleanup for dst */
4327 path_cleanup(&dst);
4328
4329 return return_value;
4330}
4331
4332static PyObject *
4333os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd, int follow_symlinks)
4334/*[clinic end generated code: output=53477662fe02e183 input=b0095ebbcbaa7e04]*/
4335{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004336#ifdef MS_WINDOWS
4337 BOOL result;
4338#else
4339 int result;
4340#endif
4341
Larry Hastings9cf065c2012-06-22 16:30:09 -07004342#ifndef HAVE_LINKAT
4343 if ((src_dir_fd != DEFAULT_DIR_FD) || (dst_dir_fd != DEFAULT_DIR_FD)) {
4344 argument_unavailable_error("link", "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10004345 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004346 }
4347#endif
4348
Larry Hastings2f936352014-08-05 14:04:04 +10004349 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004350 PyErr_SetString(PyExc_NotImplementedError,
4351 "link: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10004352 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004353 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004354
Brian Curtin1b9df392010-11-24 20:24:31 +00004355#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004356 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004357 if (src->wide)
4358 result = CreateHardLinkW(dst->wide, src->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004359 else
Larry Hastings2f936352014-08-05 14:04:04 +10004360 result = CreateHardLinkA(dst->narrow, src->narrow, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004361 Py_END_ALLOW_THREADS
Brian Curtin1b9df392010-11-24 20:24:31 +00004362
Larry Hastings2f936352014-08-05 14:04:04 +10004363 if (!result)
4364 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004365#else
4366 Py_BEGIN_ALLOW_THREADS
Larry Hastings67cbf7b2012-06-22 17:06:48 -07004367#ifdef HAVE_LINKAT
Larry Hastings9cf065c2012-06-22 16:30:09 -07004368 if ((src_dir_fd != DEFAULT_DIR_FD) ||
4369 (dst_dir_fd != DEFAULT_DIR_FD) ||
4370 (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004371 result = linkat(src_dir_fd, src->narrow,
4372 dst_dir_fd, dst->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004373 follow_symlinks ? AT_SYMLINK_FOLLOW : 0);
4374 else
4375#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004376 result = link(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004377 Py_END_ALLOW_THREADS
Brian Curtinfc889c42010-11-28 23:59:46 +00004378
Larry Hastings2f936352014-08-05 14:04:04 +10004379 if (result)
4380 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004381#endif
4382
Larry Hastings2f936352014-08-05 14:04:04 +10004383 Py_RETURN_NONE;
Brian Curtin1b9df392010-11-24 20:24:31 +00004384}
Larry Hastings9cf065c2012-06-22 16:30:09 -07004385#endif
4386
Brian Curtin1b9df392010-11-24 20:24:31 +00004387
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004388#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
Barry Warsaw53699e91996-12-10 23:23:01 +00004389static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004390_listdir_windows_no_opendir(path_t *path, PyObject *list)
Guido van Rossumb6775db1994-08-01 11:34:53 +00004391{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004392 PyObject *v;
4393 HANDLE hFindFile = INVALID_HANDLE_VALUE;
4394 BOOL result;
4395 WIN32_FIND_DATA FileData;
Victor Stinner75875072013-11-24 19:23:25 +01004396 char namebuf[MAX_PATH+4]; /* Overallocate for "\*.*" */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004397 char *bufptr = namebuf;
4398 /* only claim to have space for MAX_PATH */
Victor Stinner75875072013-11-24 19:23:25 +01004399 Py_ssize_t len = Py_ARRAY_LENGTH(namebuf)-4;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004400 PyObject *po = NULL;
4401 wchar_t *wnamebuf = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004402
Gregory P. Smith40a21602013-03-20 20:52:50 -07004403 if (!path->narrow) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004404 WIN32_FIND_DATAW wFileData;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004405 wchar_t *po_wchars;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004406
Gregory P. Smith40a21602013-03-20 20:52:50 -07004407 if (!path->wide) { /* Default arg: "." */
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004408 po_wchars = L".";
4409 len = 1;
4410 } else {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004411 po_wchars = path->wide;
4412 len = wcslen(path->wide);
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004413 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004414 /* The +5 is so we can append "\\*.*\0" */
Victor Stinnerb6404912013-07-07 16:21:41 +02004415 wnamebuf = PyMem_Malloc((len + 5) * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004416 if (!wnamebuf) {
4417 PyErr_NoMemory();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004418 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004419 }
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00004420 wcscpy(wnamebuf, po_wchars);
Victor Stinner8c62be82010-05-06 00:08:46 +00004421 if (len > 0) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004422 wchar_t wch = wnamebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004423 if (wch != SEP && wch != ALTSEP && wch != L':')
4424 wnamebuf[len++] = SEP;
Victor Stinner8c62be82010-05-06 00:08:46 +00004425 wcscpy(wnamebuf + len, L"*.*");
4426 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004427 if ((list = PyList_New(0)) == NULL) {
4428 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004429 }
Antoine Pitroub73caab2010-08-09 23:39:31 +00004430 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004431 hFindFile = FindFirstFileW(wnamebuf, &wFileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004432 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004433 if (hFindFile == INVALID_HANDLE_VALUE) {
4434 int error = GetLastError();
Larry Hastings9cf065c2012-06-22 16:30:09 -07004435 if (error == ERROR_FILE_NOT_FOUND)
4436 goto exit;
4437 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004438 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004439 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004440 }
4441 do {
4442 /* Skip over . and .. */
4443 if (wcscmp(wFileData.cFileName, L".") != 0 &&
4444 wcscmp(wFileData.cFileName, L"..") != 0) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004445 v = PyUnicode_FromWideChar(wFileData.cFileName,
4446 wcslen(wFileData.cFileName));
Victor Stinner8c62be82010-05-06 00:08:46 +00004447 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004448 Py_DECREF(list);
4449 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004450 break;
4451 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004452 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004453 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004454 Py_DECREF(list);
4455 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004456 break;
4457 }
4458 Py_DECREF(v);
4459 }
4460 Py_BEGIN_ALLOW_THREADS
4461 result = FindNextFileW(hFindFile, &wFileData);
4462 Py_END_ALLOW_THREADS
4463 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4464 it got to the end of the directory. */
4465 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004466 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004467 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004468 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004469 }
4470 } while (result == TRUE);
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00004471
Larry Hastings9cf065c2012-06-22 16:30:09 -07004472 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004473 }
Gregory P. Smith40a21602013-03-20 20:52:50 -07004474 strcpy(namebuf, path->narrow);
4475 len = path->length;
Victor Stinner8c62be82010-05-06 00:08:46 +00004476 if (len > 0) {
4477 char ch = namebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01004478 if (ch != '\\' && ch != '/' && ch != ':')
4479 namebuf[len++] = '\\';
Victor Stinner8c62be82010-05-06 00:08:46 +00004480 strcpy(namebuf + len, "*.*");
4481 }
Guido van Rossumb6775db1994-08-01 11:34:53 +00004482
Larry Hastings9cf065c2012-06-22 16:30:09 -07004483 if ((list = PyList_New(0)) == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +00004484 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00004485
Antoine Pitroub73caab2010-08-09 23:39:31 +00004486 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004487 hFindFile = FindFirstFile(namebuf, &FileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00004488 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00004489 if (hFindFile == INVALID_HANDLE_VALUE) {
4490 int error = GetLastError();
4491 if (error == ERROR_FILE_NOT_FOUND)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004492 goto exit;
4493 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004494 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004495 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004496 }
4497 do {
4498 /* Skip over . and .. */
4499 if (strcmp(FileData.cFileName, ".") != 0 &&
4500 strcmp(FileData.cFileName, "..") != 0) {
4501 v = PyBytes_FromString(FileData.cFileName);
4502 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004503 Py_DECREF(list);
4504 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004505 break;
4506 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004507 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004508 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004509 Py_DECREF(list);
4510 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004511 break;
4512 }
4513 Py_DECREF(v);
4514 }
4515 Py_BEGIN_ALLOW_THREADS
4516 result = FindNextFile(hFindFile, &FileData);
4517 Py_END_ALLOW_THREADS
4518 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
4519 it got to the end of the directory. */
4520 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004521 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004522 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004523 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004524 }
4525 } while (result == TRUE);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004526
Larry Hastings9cf065c2012-06-22 16:30:09 -07004527exit:
4528 if (hFindFile != INVALID_HANDLE_VALUE) {
4529 if (FindClose(hFindFile) == FALSE) {
4530 if (list != NULL) {
4531 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004532 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004533 }
4534 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004535 }
Victor Stinnerb6404912013-07-07 16:21:41 +02004536 PyMem_Free(wnamebuf);
Guido van Rossumb6775db1994-08-01 11:34:53 +00004537
Larry Hastings9cf065c2012-06-22 16:30:09 -07004538 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004539} /* end of _listdir_windows_no_opendir */
4540
4541#else /* thus POSIX, ie: not (MS_WINDOWS and not HAVE_OPENDIR) */
4542
4543static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07004544_posix_listdir(path_t *path, PyObject *list)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004545{
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004546 PyObject *v;
4547 DIR *dirp = NULL;
4548 struct dirent *ep;
4549 int return_str; /* if false, return bytes */
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004550#ifdef HAVE_FDOPENDIR
4551 int fd = -1;
4552#endif
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004553
Victor Stinner8c62be82010-05-06 00:08:46 +00004554 errno = 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004555#ifdef HAVE_FDOPENDIR
Gregory P. Smith40a21602013-03-20 20:52:50 -07004556 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004557 /* closedir() closes the FD, so we duplicate it */
Victor Stinnerdaf45552013-08-28 00:53:59 +02004558 fd = _Py_dup(path->fd);
Victor Stinnerf3266652013-12-19 13:24:49 +01004559 if (fd == -1)
4560 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004561
Larry Hastingsfdaea062012-06-25 04:42:23 -07004562 return_str = 1;
4563
Larry Hastings9cf065c2012-06-22 16:30:09 -07004564 Py_BEGIN_ALLOW_THREADS
4565 dirp = fdopendir(fd);
4566 Py_END_ALLOW_THREADS
4567 }
4568 else
4569#endif
4570 {
Larry Hastingsfdaea062012-06-25 04:42:23 -07004571 char *name;
Gregory P. Smith40a21602013-03-20 20:52:50 -07004572 if (path->narrow) {
4573 name = path->narrow;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004574 /* only return bytes if they specified a bytes object */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004575 return_str = !(PyBytes_Check(path->object));
Larry Hastingsfdaea062012-06-25 04:42:23 -07004576 }
4577 else {
4578 name = ".";
4579 return_str = 1;
4580 }
4581
Larry Hastings9cf065c2012-06-22 16:30:09 -07004582 Py_BEGIN_ALLOW_THREADS
4583 dirp = opendir(name);
4584 Py_END_ALLOW_THREADS
4585 }
4586
4587 if (dirp == NULL) {
Gregory P. Smith40a21602013-03-20 20:52:50 -07004588 list = path_error(path);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004589#ifdef HAVE_FDOPENDIR
4590 if (fd != -1) {
4591 Py_BEGIN_ALLOW_THREADS
4592 close(fd);
4593 Py_END_ALLOW_THREADS
4594 }
4595#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004596 goto exit;
4597 }
4598 if ((list = PyList_New(0)) == NULL) {
4599 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004600 }
4601 for (;;) {
4602 errno = 0;
4603 Py_BEGIN_ALLOW_THREADS
4604 ep = readdir(dirp);
4605 Py_END_ALLOW_THREADS
4606 if (ep == NULL) {
4607 if (errno == 0) {
4608 break;
4609 } else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004610 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004611 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004612 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004613 }
4614 }
4615 if (ep->d_name[0] == '.' &&
4616 (NAMLEN(ep) == 1 ||
4617 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
4618 continue;
Larry Hastingsfdaea062012-06-25 04:42:23 -07004619 if (return_str)
Victor Stinnera45598a2010-05-14 16:35:39 +00004620 v = PyUnicode_DecodeFSDefaultAndSize(ep->d_name, NAMLEN(ep));
4621 else
4622 v = PyBytes_FromStringAndSize(ep->d_name, NAMLEN(ep));
Victor Stinner8c62be82010-05-06 00:08:46 +00004623 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004624 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004625 break;
4626 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004627 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00004628 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004629 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00004630 break;
4631 }
4632 Py_DECREF(v);
4633 }
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00004634
Larry Hastings9cf065c2012-06-22 16:30:09 -07004635exit:
4636 if (dirp != NULL) {
4637 Py_BEGIN_ALLOW_THREADS
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004638#ifdef HAVE_FDOPENDIR
Larry Hastings9cf065c2012-06-22 16:30:09 -07004639 if (fd > -1)
4640 rewinddir(dirp);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07004641#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004642 closedir(dirp);
4643 Py_END_ALLOW_THREADS
4644 }
4645
Larry Hastings9cf065c2012-06-22 16:30:09 -07004646 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004647} /* end of _posix_listdir */
4648#endif /* which OS */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00004649
Larry Hastings2f936352014-08-05 14:04:04 +10004650
4651/*[clinic input]
4652os.listdir
4653
4654 path : path_t(nullable=True, allow_fd='PATH_HAVE_FDOPENDIR') = None
4655
4656Return a list containing the names of the files in the directory.
4657
4658path can be specified as either str or bytes. If path is bytes,
4659 the filenames returned will also be bytes; in all other circumstances
4660 the filenames returned will be str.
4661If path is None, uses the path='.'.
4662On some platforms, path may also be specified as an open file descriptor;\
4663 the file descriptor must refer to a directory.
4664 If this functionality is unavailable, using it raises NotImplementedError.
4665
4666The list is in arbitrary order. It does not include the special
4667entries '.' and '..' even if they are present in the directory.
4668
4669
4670[clinic start generated code]*/
4671
4672PyDoc_STRVAR(os_listdir__doc__,
4673"listdir($module, /, path=None)\n"
4674"--\n"
4675"\n"
4676"Return a list containing the names of the files in the directory.\n"
4677"\n"
4678"path can be specified as either str or bytes. If path is bytes,\n"
4679" the filenames returned will also be bytes; in all other circumstances\n"
4680" the filenames returned will be str.\n"
4681"If path is None, uses the path=\'.\'.\n"
4682"On some platforms, path may also be specified as an open file descriptor;\\\n"
4683" the file descriptor must refer to a directory.\n"
4684" If this functionality is unavailable, using it raises NotImplementedError.\n"
4685"\n"
4686"The list is in arbitrary order. It does not include the special\n"
4687"entries \'.\' and \'..\' even if they are present in the directory.");
4688
4689#define OS_LISTDIR_METHODDEF \
4690 {"listdir", (PyCFunction)os_listdir, METH_VARARGS|METH_KEYWORDS, os_listdir__doc__},
4691
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004692static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004693os_listdir_impl(PyModuleDef *module, path_t *path);
4694
4695static PyObject *
4696os_listdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004697{
Larry Hastings2f936352014-08-05 14:04:04 +10004698 PyObject *return_value = NULL;
4699 static char *_keywords[] = {"path", NULL};
4700 path_t path = PATH_T_INITIALIZE("listdir", "path", 1, PATH_HAVE_FDOPENDIR);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004701
Larry Hastings2f936352014-08-05 14:04:04 +10004702 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4703 "|O&:listdir", _keywords,
4704 path_converter, &path))
4705 goto exit;
4706 return_value = os_listdir_impl(module, &path);
Gregory P. Smith40a21602013-03-20 20:52:50 -07004707
Larry Hastings2f936352014-08-05 14:04:04 +10004708exit:
4709 /* Cleanup for path */
Gregory P. Smith40a21602013-03-20 20:52:50 -07004710 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +10004711
Gregory P. Smith40a21602013-03-20 20:52:50 -07004712 return return_value;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07004713}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004714
Larry Hastings2f936352014-08-05 14:04:04 +10004715static PyObject *
4716os_listdir_impl(PyModuleDef *module, path_t *path)
4717/*[clinic end generated code: output=e159bd9be6909018 input=09e300416e3cd729]*/
4718{
4719#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
4720 return _listdir_windows_no_opendir(path, NULL);
4721#else
4722 return _posix_listdir(path, NULL);
4723#endif
4724}
4725
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00004726#ifdef MS_WINDOWS
Mark Hammondef8b6542001-05-13 08:04:26 +00004727/* A helper function for abspath on win32 */
Larry Hastings2f936352014-08-05 14:04:04 +10004728/* AC 3.5: probably just convert to using path converter */
Mark Hammondef8b6542001-05-13 08:04:26 +00004729static PyObject *
4730posix__getfullpathname(PyObject *self, PyObject *args)
4731{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004732 const char *path;
Victor Stinner75875072013-11-24 19:23:25 +01004733 char outbuf[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00004734 char *temp;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004735 PyObject *po;
4736
4737 if (PyArg_ParseTuple(args, "U|:_getfullpathname", &po))
4738 {
4739 wchar_t *wpath;
Victor Stinner75875072013-11-24 19:23:25 +01004740 wchar_t woutbuf[MAX_PATH], *woutbufp = woutbuf;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004741 wchar_t *wtemp;
Victor Stinner8c62be82010-05-06 00:08:46 +00004742 DWORD result;
4743 PyObject *v;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004744
4745 wpath = PyUnicode_AsUnicode(po);
4746 if (wpath == NULL)
4747 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00004748 result = GetFullPathNameW(wpath,
Victor Stinner63941882011-09-29 00:42:28 +02004749 Py_ARRAY_LENGTH(woutbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004750 woutbuf, &wtemp);
Victor Stinner63941882011-09-29 00:42:28 +02004751 if (result > Py_ARRAY_LENGTH(woutbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02004752 woutbufp = PyMem_Malloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00004753 if (!woutbufp)
4754 return PyErr_NoMemory();
4755 result = GetFullPathNameW(wpath, result, woutbufp, &wtemp);
4756 }
4757 if (result)
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004758 v = PyUnicode_FromWideChar(woutbufp, wcslen(woutbufp));
Victor Stinner8c62be82010-05-06 00:08:46 +00004759 else
Victor Stinnereb5657a2011-09-30 01:44:27 +02004760 v = win32_error_object("GetFullPathNameW", po);
Victor Stinner8c62be82010-05-06 00:08:46 +00004761 if (woutbufp != woutbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02004762 PyMem_Free(woutbufp);
Victor Stinner8c62be82010-05-06 00:08:46 +00004763 return v;
4764 }
4765 /* Drop the argument parsing error as narrow strings
4766 are also valid. */
4767 PyErr_Clear();
Victor Stinnereb5657a2011-09-30 01:44:27 +02004768
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004769 if (!PyArg_ParseTuple (args, "y:_getfullpathname",
4770 &path))
Victor Stinner8c62be82010-05-06 00:08:46 +00004771 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004772 if (win32_warn_bytes_api())
4773 return NULL;
Victor Stinner63941882011-09-29 00:42:28 +02004774 if (!GetFullPathName(path, Py_ARRAY_LENGTH(outbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00004775 outbuf, &temp)) {
4776 win32_error("GetFullPathName", path);
Victor Stinner8c62be82010-05-06 00:08:46 +00004777 return NULL;
4778 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004779 if (PyUnicode_Check(PyTuple_GetItem(args, 0))) {
4780 return PyUnicode_Decode(outbuf, strlen(outbuf),
4781 Py_FileSystemDefaultEncoding, NULL);
4782 }
4783 return PyBytes_FromString(outbuf);
Larry Hastings2f936352014-08-05 14:04:04 +10004784}
Brian Curtind40e6f72010-07-08 21:39:08 +00004785
Brian Curtind25aef52011-06-13 15:16:04 -05004786
Larry Hastings2f936352014-08-05 14:04:04 +10004787/*[clinic input]
4788os._getfinalpathname
Brian Curtinf5e76d02010-11-24 13:14:05 +00004789
Larry Hastings2f936352014-08-05 14:04:04 +10004790 path: unicode
4791 /
4792
4793A helper function for samepath on windows.
4794[clinic start generated code]*/
4795
4796PyDoc_STRVAR(os__getfinalpathname__doc__,
4797"_getfinalpathname($module, path, /)\n"
4798"--\n"
4799"\n"
4800"A helper function for samepath on windows.");
4801
4802#define OS__GETFINALPATHNAME_METHODDEF \
4803 {"_getfinalpathname", (PyCFunction)os__getfinalpathname, METH_VARARGS, os__getfinalpathname__doc__},
4804
Brian Curtind40e6f72010-07-08 21:39:08 +00004805static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004806os__getfinalpathname_impl(PyModuleDef *module, PyObject *path);
4807
4808static PyObject *
4809os__getfinalpathname(PyModuleDef *module, PyObject *args)
4810{
4811 PyObject *return_value = NULL;
4812 PyObject *path;
4813
4814 if (!PyArg_ParseTuple(args,
4815 "U:_getfinalpathname",
4816 &path))
4817 goto exit;
4818 return_value = os__getfinalpathname_impl(module, path);
4819
4820exit:
4821 return return_value;
4822}
4823
4824static PyObject *
4825os__getfinalpathname_impl(PyModuleDef *module, PyObject *path)
4826/*[clinic end generated code: output=4563c6eacf1b0881 input=71d5e89334891bf4]*/
Brian Curtind40e6f72010-07-08 21:39:08 +00004827{
4828 HANDLE hFile;
4829 int buf_size;
4830 wchar_t *target_path;
4831 int result_length;
Larry Hastings2f936352014-08-05 14:04:04 +10004832 PyObject *result;
4833 wchar_t *path_wchar;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004834
Larry Hastings2f936352014-08-05 14:04:04 +10004835 path_wchar = PyUnicode_AsUnicode(path);
4836 if (path_wchar == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02004837 return NULL;
Brian Curtind40e6f72010-07-08 21:39:08 +00004838
4839 if(!check_GetFinalPathNameByHandle()) {
4840 /* If the OS doesn't have GetFinalPathNameByHandle, return a
4841 NotImplementedError. */
4842 return PyErr_Format(PyExc_NotImplementedError,
4843 "GetFinalPathNameByHandle not available on this platform");
4844 }
4845
4846 hFile = CreateFileW(
Larry Hastings2f936352014-08-05 14:04:04 +10004847 path_wchar,
Brian Curtind40e6f72010-07-08 21:39:08 +00004848 0, /* desired access */
4849 0, /* share mode */
4850 NULL, /* security attributes */
4851 OPEN_EXISTING,
4852 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
4853 FILE_FLAG_BACKUP_SEMANTICS,
4854 NULL);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004855
Victor Stinnereb5657a2011-09-30 01:44:27 +02004856 if(hFile == INVALID_HANDLE_VALUE)
Larry Hastings2f936352014-08-05 14:04:04 +10004857 return win32_error_object("CreateFileW", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004858
4859 /* We have a good handle to the target, use it to determine the
4860 target path name. */
4861 buf_size = Py_GetFinalPathNameByHandleW(hFile, 0, 0, VOLUME_NAME_NT);
4862
4863 if(!buf_size)
Larry Hastings2f936352014-08-05 14:04:04 +10004864 return win32_error_object("GetFinalPathNameByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004865
Victor Stinnerb6404912013-07-07 16:21:41 +02004866 target_path = (wchar_t *)PyMem_Malloc((buf_size+1)*sizeof(wchar_t));
Brian Curtind40e6f72010-07-08 21:39:08 +00004867 if(!target_path)
4868 return PyErr_NoMemory();
4869
4870 result_length = Py_GetFinalPathNameByHandleW(hFile, target_path,
4871 buf_size, VOLUME_NAME_DOS);
4872 if(!result_length)
Larry Hastings2f936352014-08-05 14:04:04 +10004873 return win32_error_object("GetFinalPathNamyByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004874
4875 if(!CloseHandle(hFile))
Larry Hastings2f936352014-08-05 14:04:04 +10004876 return win32_error_object("CloseHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004877
4878 target_path[result_length] = 0;
Victor Stinner9d3b93b2011-11-22 02:27:30 +01004879 result = PyUnicode_FromWideChar(target_path, result_length);
Victor Stinnerb6404912013-07-07 16:21:41 +02004880 PyMem_Free(target_path);
Brian Curtind40e6f72010-07-08 21:39:08 +00004881 return result;
Larry Hastings2f936352014-08-05 14:04:04 +10004882}
Brian Curtin62857742010-09-06 17:07:27 +00004883
Brian Curtin95d028f2011-06-09 09:10:38 -05004884PyDoc_STRVAR(posix__isdir__doc__,
4885"Return true if the pathname refers to an existing directory.");
4886
Larry Hastings2f936352014-08-05 14:04:04 +10004887/* AC 3.5: convert using path converter */
Brian Curtin9c669cc2011-06-08 18:17:18 -05004888static PyObject *
4889posix__isdir(PyObject *self, PyObject *args)
4890{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004891 const char *path;
Victor Stinnereb5657a2011-09-30 01:44:27 +02004892 PyObject *po;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004893 DWORD attributes;
4894
4895 if (PyArg_ParseTuple(args, "U|:_isdir", &po)) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02004896 wchar_t *wpath = PyUnicode_AsUnicode(po);
4897 if (wpath == NULL)
4898 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004899
4900 attributes = GetFileAttributesW(wpath);
4901 if (attributes == INVALID_FILE_ATTRIBUTES)
4902 Py_RETURN_FALSE;
4903 goto check;
4904 }
4905 /* Drop the argument parsing error as narrow strings
4906 are also valid. */
4907 PyErr_Clear();
4908
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004909 if (!PyArg_ParseTuple(args, "y:_isdir", &path))
Brian Curtin9c669cc2011-06-08 18:17:18 -05004910 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01004911 if (win32_warn_bytes_api())
4912 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05004913 attributes = GetFileAttributesA(path);
4914 if (attributes == INVALID_FILE_ATTRIBUTES)
4915 Py_RETURN_FALSE;
4916
4917check:
4918 if (attributes & FILE_ATTRIBUTE_DIRECTORY)
4919 Py_RETURN_TRUE;
4920 else
4921 Py_RETURN_FALSE;
4922}
Tim Golden6b528062013-08-01 12:44:00 +01004923
Tim Golden6b528062013-08-01 12:44:00 +01004924
Larry Hastings2f936352014-08-05 14:04:04 +10004925/*[clinic input]
4926os._getvolumepathname
4927
4928 path: unicode
4929
4930A helper function for ismount on Win32.
4931[clinic start generated code]*/
4932
4933PyDoc_STRVAR(os__getvolumepathname__doc__,
4934"_getvolumepathname($module, /, path)\n"
4935"--\n"
4936"\n"
4937"A helper function for ismount on Win32.");
4938
4939#define OS__GETVOLUMEPATHNAME_METHODDEF \
4940 {"_getvolumepathname", (PyCFunction)os__getvolumepathname, METH_VARARGS|METH_KEYWORDS, os__getvolumepathname__doc__},
4941
Tim Golden6b528062013-08-01 12:44:00 +01004942static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004943os__getvolumepathname_impl(PyModuleDef *module, PyObject *path);
4944
4945static PyObject *
4946os__getvolumepathname(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Tim Golden6b528062013-08-01 12:44:00 +01004947{
Larry Hastings2f936352014-08-05 14:04:04 +10004948 PyObject *return_value = NULL;
4949 static char *_keywords[] = {"path", NULL};
4950 PyObject *path;
4951
4952 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
4953 "U:_getvolumepathname", _keywords,
4954 &path))
4955 goto exit;
4956 return_value = os__getvolumepathname_impl(module, path);
4957
4958exit:
4959 return return_value;
4960}
4961
4962static PyObject *
4963os__getvolumepathname_impl(PyModuleDef *module, PyObject *path)
4964/*[clinic end generated code: output=ac0833b6d6da7657 input=7eacadc40acbda6b]*/
4965{
4966 PyObject *result;
4967 wchar_t *path_wchar, *mountpath=NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01004968 size_t buflen;
Tim Golden6b528062013-08-01 12:44:00 +01004969 BOOL ret;
4970
Larry Hastings2f936352014-08-05 14:04:04 +10004971 path_wchar = PyUnicode_AsUnicodeAndSize(path, &buflen);
4972 if (path_wchar == NULL)
Tim Golden6b528062013-08-01 12:44:00 +01004973 return NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01004974 buflen += 1;
Tim Golden6b528062013-08-01 12:44:00 +01004975
4976 /* Volume path should be shorter than entire path */
Victor Stinner6edddfa2013-11-24 19:22:57 +01004977 buflen = Py_MAX(buflen, MAX_PATH);
4978
4979 if (buflen > DWORD_MAX) {
4980 PyErr_SetString(PyExc_OverflowError, "path too long");
4981 return NULL;
4982 }
4983
4984 mountpath = (wchar_t *)PyMem_Malloc(buflen * sizeof(wchar_t));
Tim Golden6b528062013-08-01 12:44:00 +01004985 if (mountpath == NULL)
4986 return PyErr_NoMemory();
4987
4988 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004989 ret = GetVolumePathNameW(path_wchar, mountpath,
Victor Stinner6edddfa2013-11-24 19:22:57 +01004990 Py_SAFE_DOWNCAST(buflen, size_t, DWORD));
Tim Golden6b528062013-08-01 12:44:00 +01004991 Py_END_ALLOW_THREADS
4992
4993 if (!ret) {
Larry Hastings2f936352014-08-05 14:04:04 +10004994 result = win32_error_object("_getvolumepathname", path);
Tim Golden6b528062013-08-01 12:44:00 +01004995 goto exit;
4996 }
4997 result = PyUnicode_FromWideChar(mountpath, wcslen(mountpath));
4998
4999exit:
5000 PyMem_Free(mountpath);
5001 return result;
5002}
Tim Golden6b528062013-08-01 12:44:00 +01005003
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00005004#endif /* MS_WINDOWS */
Mark Hammondef8b6542001-05-13 08:04:26 +00005005
Larry Hastings2f936352014-08-05 14:04:04 +10005006
5007/*[clinic input]
5008os.mkdir
5009
5010 path : path_t
5011
5012 mode: int = 0o777
5013
5014 *
5015
5016 dir_fd : dir_fd(requires='mkdirat') = None
5017
5018# "mkdir(path, mode=0o777, *, dir_fd=None)\n\n\
5019
5020Create a directory.
5021
5022If dir_fd is not None, it should be a file descriptor open to a directory,
5023 and path should be relative; path will then be relative to that directory.
5024dir_fd may not be implemented on your platform.
5025 If it is unavailable, using it will raise a NotImplementedError.
5026
5027The mode argument is ignored on Windows.
5028[clinic start generated code]*/
5029
5030PyDoc_STRVAR(os_mkdir__doc__,
5031"mkdir($module, /, path, mode=511, *, dir_fd=None)\n"
5032"--\n"
5033"\n"
5034"Create a directory.\n"
5035"\n"
5036"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5037" and path should be relative; path will then be relative to that directory.\n"
5038"dir_fd may not be implemented on your platform.\n"
5039" If it is unavailable, using it will raise a NotImplementedError.\n"
5040"\n"
5041"The mode argument is ignored on Windows.");
5042
5043#define OS_MKDIR_METHODDEF \
5044 {"mkdir", (PyCFunction)os_mkdir, METH_VARARGS|METH_KEYWORDS, os_mkdir__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005045
Barry Warsaw53699e91996-12-10 23:23:01 +00005046static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005047os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005048
Larry Hastings2f936352014-08-05 14:04:04 +10005049static PyObject *
5050os_mkdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5051{
5052 PyObject *return_value = NULL;
5053 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
5054 path_t path = PATH_T_INITIALIZE("mkdir", "path", 0, 0);
5055 int mode = 511;
5056 int dir_fd = DEFAULT_DIR_FD;
5057
5058 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5059 "O&|i$O&:mkdir", _keywords,
5060 path_converter, &path, &mode, MKDIRAT_DIR_FD_CONVERTER, &dir_fd))
5061 goto exit;
5062 return_value = os_mkdir_impl(module, &path, mode, dir_fd);
5063
5064exit:
5065 /* Cleanup for path */
5066 path_cleanup(&path);
5067
5068 return return_value;
5069}
5070
5071static PyObject *
5072os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
5073/*[clinic end generated code: output=55c6ef2bc1b207e6 input=e965f68377e9b1ce]*/
5074{
5075 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005076
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00005077#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005078 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005079 if (path->wide)
5080 result = CreateDirectoryW(path->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005081 else
Larry Hastings2f936352014-08-05 14:04:04 +10005082 result = CreateDirectoryA(path->narrow, NULL);
Victor Stinner8c62be82010-05-06 00:08:46 +00005083 Py_END_ALLOW_THREADS
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005084
Larry Hastings2f936352014-08-05 14:04:04 +10005085 if (!result)
5086 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005087#else
Victor Stinner8c62be82010-05-06 00:08:46 +00005088 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07005089#if HAVE_MKDIRAT
5090 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005091 result = mkdirat(dir_fd, path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005092 else
5093#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00005094#if ( defined(__WATCOMC__) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Larry Hastings2f936352014-08-05 14:04:04 +10005095 result = mkdir(path->narrow);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005096#else
Larry Hastings2f936352014-08-05 14:04:04 +10005097 result = mkdir(path->narrow, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005098#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005099 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005100 if (result < 0)
5101 return path_error(path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00005102#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005103 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005104}
5105
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005106
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005107/* sys/resource.h is needed for at least: wait3(), wait4(), broken nice. */
5108#if defined(HAVE_SYS_RESOURCE_H)
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005109#include <sys/resource.h>
5110#endif
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005111
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00005112
5113#ifdef HAVE_NICE
Larry Hastings2f936352014-08-05 14:04:04 +10005114/*[clinic input]
5115os.nice
5116
5117 increment: int
5118 /
5119
5120Add increment to the priority of process and return the new priority.
5121[clinic start generated code]*/
5122
5123PyDoc_STRVAR(os_nice__doc__,
5124"nice($module, increment, /)\n"
5125"--\n"
5126"\n"
5127"Add increment to the priority of process and return the new priority.");
5128
5129#define OS_NICE_METHODDEF \
5130 {"nice", (PyCFunction)os_nice, METH_VARARGS, os_nice__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005131
Barry Warsaw53699e91996-12-10 23:23:01 +00005132static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005133os_nice_impl(PyModuleDef *module, int increment);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005134
Larry Hastings2f936352014-08-05 14:04:04 +10005135static PyObject *
5136os_nice(PyModuleDef *module, PyObject *args)
5137{
5138 PyObject *return_value = NULL;
5139 int increment;
5140
5141 if (!PyArg_ParseTuple(args,
5142 "i:nice",
5143 &increment))
5144 goto exit;
5145 return_value = os_nice_impl(module, increment);
5146
5147exit:
5148 return return_value;
5149}
5150
5151static PyObject *
5152os_nice_impl(PyModuleDef *module, int increment)
5153/*[clinic end generated code: output=c360dc2a3bd8e3d0 input=864be2d402a21da2]*/
5154{
5155 int value;
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005156
Victor Stinner8c62be82010-05-06 00:08:46 +00005157 /* There are two flavours of 'nice': one that returns the new
5158 priority (as required by almost all standards out there) and the
5159 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
5160 the use of getpriority() to get the new priority.
Tim Peters5aa91602002-01-30 05:46:57 +00005161
Victor Stinner8c62be82010-05-06 00:08:46 +00005162 If we are of the nice family that returns the new priority, we
5163 need to clear errno before the call, and check if errno is filled
5164 before calling posix_error() on a returnvalue of -1, because the
5165 -1 may be the actual new priority! */
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005166
Victor Stinner8c62be82010-05-06 00:08:46 +00005167 errno = 0;
5168 value = nice(increment);
Thomas Wouterse38b2f12001-07-11 22:35:31 +00005169#if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005170 if (value == 0)
5171 value = getpriority(PRIO_PROCESS, 0);
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00005172#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00005173 if (value == -1 && errno != 0)
5174 /* either nice() or getpriority() returned an error */
5175 return posix_error();
5176 return PyLong_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00005177}
Guido van Rossumb6775db1994-08-01 11:34:53 +00005178#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00005179
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005180
5181#ifdef HAVE_GETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005182/*[clinic input]
5183os.getpriority
5184
5185 which: int
5186 who: int
5187
5188Return program scheduling priority.
5189[clinic start generated code]*/
5190
5191PyDoc_STRVAR(os_getpriority__doc__,
5192"getpriority($module, /, which, who)\n"
5193"--\n"
5194"\n"
5195"Return program scheduling priority.");
5196
5197#define OS_GETPRIORITY_METHODDEF \
5198 {"getpriority", (PyCFunction)os_getpriority, METH_VARARGS|METH_KEYWORDS, os_getpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005199
5200static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005201os_getpriority_impl(PyModuleDef *module, int which, int who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005202
Larry Hastings2f936352014-08-05 14:04:04 +10005203static PyObject *
5204os_getpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5205{
5206 PyObject *return_value = NULL;
5207 static char *_keywords[] = {"which", "who", NULL};
5208 int which;
5209 int who;
5210
5211 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5212 "ii:getpriority", _keywords,
5213 &which, &who))
5214 goto exit;
5215 return_value = os_getpriority_impl(module, which, who);
5216
5217exit:
5218 return return_value;
5219}
5220
5221static PyObject *
5222os_getpriority_impl(PyModuleDef *module, int which, int who)
5223/*[clinic end generated code: output=81639cf765f05dae input=9be615d40e2544ef]*/
5224{
5225 int retval;
5226
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005227 errno = 0;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005228 retval = getpriority(which, who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005229 if (errno != 0)
5230 return posix_error();
5231 return PyLong_FromLong((long)retval);
5232}
5233#endif /* HAVE_GETPRIORITY */
5234
5235
5236#ifdef HAVE_SETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10005237/*[clinic input]
5238os.setpriority
5239
5240 which: int
5241 who: int
5242 priority: int
5243
5244Set program scheduling priority.
5245[clinic start generated code]*/
5246
5247PyDoc_STRVAR(os_setpriority__doc__,
5248"setpriority($module, /, which, who, priority)\n"
5249"--\n"
5250"\n"
5251"Set program scheduling priority.");
5252
5253#define OS_SETPRIORITY_METHODDEF \
5254 {"setpriority", (PyCFunction)os_setpriority, METH_VARARGS|METH_KEYWORDS, os_setpriority__doc__},
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005255
5256static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005257os_setpriority_impl(PyModuleDef *module, int which, int who, int priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005258
Larry Hastings2f936352014-08-05 14:04:04 +10005259static PyObject *
5260os_setpriority(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5261{
5262 PyObject *return_value = NULL;
5263 static char *_keywords[] = {"which", "who", "priority", NULL};
5264 int which;
5265 int who;
5266 int priority;
5267
5268 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5269 "iii:setpriority", _keywords,
5270 &which, &who, &priority))
5271 goto exit;
5272 return_value = os_setpriority_impl(module, which, who, priority);
5273
5274exit:
5275 return return_value;
5276}
5277
5278static PyObject *
5279os_setpriority_impl(PyModuleDef *module, int which, int who, int priority)
5280/*[clinic end generated code: output=ddad62651fb2120c input=710ccbf65b9dc513]*/
5281{
5282 int retval;
5283
5284 retval = setpriority(which, who, priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00005285 if (retval == -1)
5286 return posix_error();
5287 Py_RETURN_NONE;
5288}
5289#endif /* HAVE_SETPRIORITY */
5290
5291
Barry Warsaw53699e91996-12-10 23:23:01 +00005292static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005293internal_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 +00005294{
Larry Hastings9cf065c2012-06-22 16:30:09 -07005295 char *function_name = is_replace ? "replace" : "rename";
Larry Hastings9cf065c2012-06-22 16:30:09 -07005296 int dir_fd_specified;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005297
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005298#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00005299 BOOL result;
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005300 int flags = is_replace ? MOVEFILE_REPLACE_EXISTING : 0;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005301#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005302 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00005303#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07005304
Larry Hastings9cf065c2012-06-22 16:30:09 -07005305 dir_fd_specified = (src_dir_fd != DEFAULT_DIR_FD) ||
5306 (dst_dir_fd != DEFAULT_DIR_FD);
5307#ifndef HAVE_RENAMEAT
5308 if (dir_fd_specified) {
5309 argument_unavailable_error(function_name, "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10005310 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005311 }
5312#endif
5313
Larry Hastings2f936352014-08-05 14:04:04 +10005314 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07005315 PyErr_Format(PyExc_ValueError,
5316 "%s: src and dst must be the same type", function_name);
Larry Hastings2f936352014-08-05 14:04:04 +10005317 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005318 }
5319
5320#ifdef MS_WINDOWS
5321 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005322 if (src->wide)
5323 result = MoveFileExW(src->wide, dst->wide, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005324 else
Larry Hastings2f936352014-08-05 14:04:04 +10005325 result = MoveFileExA(src->narrow, dst->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005326 Py_END_ALLOW_THREADS
5327
Larry Hastings2f936352014-08-05 14:04:04 +10005328 if (!result)
5329 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005330
5331#else
5332 Py_BEGIN_ALLOW_THREADS
5333#ifdef HAVE_RENAMEAT
5334 if (dir_fd_specified)
Larry Hastings2f936352014-08-05 14:04:04 +10005335 result = renameat(src_dir_fd, src->narrow, dst_dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005336 else
5337#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005338 result = rename(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005339 Py_END_ALLOW_THREADS
5340
Larry Hastings2f936352014-08-05 14:04:04 +10005341 if (result)
5342 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005343#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005344 Py_RETURN_NONE;
5345}
Larry Hastings9cf065c2012-06-22 16:30:09 -07005346
Larry Hastings2f936352014-08-05 14:04:04 +10005347
5348/*[clinic input]
5349os.rename
5350
5351 src : path_t
5352 dst : path_t
5353 *
5354 src_dir_fd : dir_fd = None
5355 dst_dir_fd : dir_fd = None
5356
5357Rename a file or directory.
5358
5359If either src_dir_fd or dst_dir_fd is not None, it should be a file
5360 descriptor open to a directory, and the respective path string (src or dst)
5361 should be relative; the path will then be relative to that directory.
5362src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5363 If they are unavailable, using them will raise a NotImplementedError.
5364[clinic start generated code]*/
5365
5366PyDoc_STRVAR(os_rename__doc__,
5367"rename($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5368"--\n"
5369"\n"
5370"Rename a file or directory.\n"
5371"\n"
5372"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5373" descriptor open to a directory, and the respective path string (src or dst)\n"
5374" should be relative; the path will then be relative to that directory.\n"
5375"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5376" If they are unavailable, using them will raise a NotImplementedError.");
5377
5378#define OS_RENAME_METHODDEF \
5379 {"rename", (PyCFunction)os_rename, METH_VARARGS|METH_KEYWORDS, os_rename__doc__},
5380
5381static PyObject *
5382os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd);
5383
5384static PyObject *
5385os_rename(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5386{
5387 PyObject *return_value = NULL;
5388 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5389 path_t src = PATH_T_INITIALIZE("rename", "src", 0, 0);
5390 path_t dst = PATH_T_INITIALIZE("rename", "dst", 0, 0);
5391 int src_dir_fd = DEFAULT_DIR_FD;
5392 int dst_dir_fd = DEFAULT_DIR_FD;
5393
5394 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5395 "O&O&|$O&O&:rename", _keywords,
5396 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5397 goto exit;
5398 return_value = os_rename_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5399
Larry Hastings9cf065c2012-06-22 16:30:09 -07005400exit:
Larry Hastings2f936352014-08-05 14:04:04 +10005401 /* Cleanup for src */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005402 path_cleanup(&src);
Larry Hastings2f936352014-08-05 14:04:04 +10005403 /* Cleanup for dst */
Larry Hastings9cf065c2012-06-22 16:30:09 -07005404 path_cleanup(&dst);
Larry Hastings2f936352014-08-05 14:04:04 +10005405
Larry Hastings9cf065c2012-06-22 16:30:09 -07005406 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005407}
5408
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005409static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005410os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5411/*[clinic end generated code: output=c936bdc81f460a1e input=faa61c847912c850]*/
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005412{
Larry Hastings2f936352014-08-05 14:04:04 +10005413 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 0);
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005414}
5415
Larry Hastings2f936352014-08-05 14:04:04 +10005416
5417/*[clinic input]
5418os.replace = os.rename
5419
5420Rename a file or directory, overwriting the destination.
5421
5422If either src_dir_fd or dst_dir_fd is not None, it should be a file
5423 descriptor open to a directory, and the respective path string (src or dst)
5424 should be relative; the path will then be relative to that directory.
5425src_dir_fd and dst_dir_fd, may not be implemented on your platform.
5426 If they are unavailable, using them will raise a NotImplementedError."
5427[clinic start generated code]*/
5428
5429PyDoc_STRVAR(os_replace__doc__,
5430"replace($module, /, src, dst, *, src_dir_fd=None, dst_dir_fd=None)\n"
5431"--\n"
5432"\n"
5433"Rename a file or directory, overwriting the destination.\n"
5434"\n"
5435"If either src_dir_fd or dst_dir_fd is not None, it should be a file\n"
5436" descriptor open to a directory, and the respective path string (src or dst)\n"
5437" should be relative; the path will then be relative to that directory.\n"
5438"src_dir_fd and dst_dir_fd, may not be implemented on your platform.\n"
5439" If they are unavailable, using them will raise a NotImplementedError.\"");
5440
5441#define OS_REPLACE_METHODDEF \
5442 {"replace", (PyCFunction)os_replace, METH_VARARGS|METH_KEYWORDS, os_replace__doc__},
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01005443
5444static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005445os_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 +00005446
Barry Warsaw53699e91996-12-10 23:23:01 +00005447static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005448os_replace(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005449{
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005450 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10005451 static char *_keywords[] = {"src", "dst", "src_dir_fd", "dst_dir_fd", NULL};
5452 path_t src = PATH_T_INITIALIZE("replace", "src", 0, 0);
5453 path_t dst = PATH_T_INITIALIZE("replace", "dst", 0, 0);
5454 int src_dir_fd = DEFAULT_DIR_FD;
5455 int dst_dir_fd = DEFAULT_DIR_FD;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005456
Larry Hastings2f936352014-08-05 14:04:04 +10005457 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5458 "O&O&|$O&O&:replace", _keywords,
5459 path_converter, &src, path_converter, &dst, dir_fd_converter, &src_dir_fd, dir_fd_converter, &dst_dir_fd))
5460 goto exit;
5461 return_value = os_replace_impl(module, &src, &dst, src_dir_fd, dst_dir_fd);
5462
5463exit:
5464 /* Cleanup for src */
5465 path_cleanup(&src);
5466 /* Cleanup for dst */
5467 path_cleanup(&dst);
5468
5469 return return_value;
5470}
5471
5472static PyObject *
5473os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd, int dst_dir_fd)
5474/*[clinic end generated code: output=224e4710d290d171 input=25515dfb107c8421]*/
5475{
5476 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 1);
5477}
5478
5479
5480/*[clinic input]
5481os.rmdir
5482
5483 path: path_t
5484 *
5485 dir_fd: dir_fd(requires='unlinkat') = None
5486
5487Remove a directory.
5488
5489If dir_fd is not None, it should be a file descriptor open to a directory,
5490 and path should be relative; path will then be relative to that directory.
5491dir_fd may not be implemented on your platform.
5492 If it is unavailable, using it will raise a NotImplementedError.
5493[clinic start generated code]*/
5494
5495PyDoc_STRVAR(os_rmdir__doc__,
5496"rmdir($module, /, path, *, dir_fd=None)\n"
5497"--\n"
5498"\n"
5499"Remove a directory.\n"
5500"\n"
5501"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5502" and path should be relative; path will then be relative to that directory.\n"
5503"dir_fd may not be implemented on your platform.\n"
5504" If it is unavailable, using it will raise a NotImplementedError.");
5505
5506#define OS_RMDIR_METHODDEF \
5507 {"rmdir", (PyCFunction)os_rmdir, METH_VARARGS|METH_KEYWORDS, os_rmdir__doc__},
5508
5509static PyObject *
5510os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd);
5511
5512static PyObject *
5513os_rmdir(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5514{
5515 PyObject *return_value = NULL;
5516 static char *_keywords[] = {"path", "dir_fd", NULL};
5517 path_t path = PATH_T_INITIALIZE("rmdir", "path", 0, 0);
5518 int dir_fd = DEFAULT_DIR_FD;
5519
5520 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5521 "O&|$O&:rmdir", _keywords,
5522 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5523 goto exit;
5524 return_value = os_rmdir_impl(module, &path, dir_fd);
5525
5526exit:
5527 /* Cleanup for path */
5528 path_cleanup(&path);
5529
5530 return return_value;
5531}
5532
5533static PyObject *
5534os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd)
5535/*[clinic end generated code: output=70b9fdbe3bee0591 input=38c8b375ca34a7e2]*/
5536{
5537 int result;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005538
5539 Py_BEGIN_ALLOW_THREADS
5540#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005541 if (path->wide)
5542 result = RemoveDirectoryW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005543 else
Larry Hastings2f936352014-08-05 14:04:04 +10005544 result = RemoveDirectoryA(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005545 result = !result; /* Windows, success=1, UNIX, success=0 */
5546#else
5547#ifdef HAVE_UNLINKAT
5548 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005549 result = unlinkat(dir_fd, path->narrow, AT_REMOVEDIR);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005550 else
5551#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005552 result = rmdir(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005553#endif
5554 Py_END_ALLOW_THREADS
5555
Larry Hastings2f936352014-08-05 14:04:04 +10005556 if (result)
5557 return path_error(path);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005558
Larry Hastings2f936352014-08-05 14:04:04 +10005559 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005560}
5561
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005562
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005563#ifdef HAVE_SYSTEM
Larry Hastings2f936352014-08-05 14:04:04 +10005564#ifdef MS_WINDOWS
5565/*[clinic input]
5566os.system -> long
5567
5568 command: Py_UNICODE
5569
5570Execute the command in a subshell.
5571[clinic start generated code]*/
5572
5573PyDoc_STRVAR(os_system__doc__,
5574"system($module, /, command)\n"
5575"--\n"
5576"\n"
5577"Execute the command in a subshell.");
5578
5579#define OS_SYSTEM_METHODDEF \
5580 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5581
5582static long
5583os_system_impl(PyModuleDef *module, Py_UNICODE *command);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005584
Barry Warsaw53699e91996-12-10 23:23:01 +00005585static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005586os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005587{
Larry Hastings2f936352014-08-05 14:04:04 +10005588 PyObject *return_value = NULL;
5589 static char *_keywords[] = {"command", NULL};
5590 Py_UNICODE *command;
5591 long _return_value;
Victor Stinnercfa72782010-04-16 11:45:13 +00005592
Larry Hastings2f936352014-08-05 14:04:04 +10005593 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5594 "u:system", _keywords,
5595 &command))
5596 goto exit;
5597 _return_value = os_system_impl(module, command);
5598 if ((_return_value == -1) && PyErr_Occurred())
5599 goto exit;
5600 return_value = PyLong_FromLong(_return_value);
Victor Stinnercfa72782010-04-16 11:45:13 +00005601
Larry Hastings2f936352014-08-05 14:04:04 +10005602exit:
5603 return return_value;
5604}
5605
5606static long
5607os_system_impl(PyModuleDef *module, Py_UNICODE *command)
5608/*[clinic end generated code: output=29fe699c0b2e9d38 input=303f5ce97df606b0]*/
5609{
5610 long result;
Victor Stinner8c62be82010-05-06 00:08:46 +00005611 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005612 result = _wsystem(command);
Victor Stinner8c62be82010-05-06 00:08:46 +00005613 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005614 return result;
5615}
5616#else /* MS_WINDOWS */
5617/*[clinic input]
5618os.system -> long
5619
5620 command: FSConverter
5621
5622Execute the command in a subshell.
5623[clinic start generated code]*/
5624
5625PyDoc_STRVAR(os_system__doc__,
5626"system($module, /, command)\n"
5627"--\n"
5628"\n"
5629"Execute the command in a subshell.");
5630
5631#define OS_SYSTEM_METHODDEF \
5632 {"system", (PyCFunction)os_system, METH_VARARGS|METH_KEYWORDS, os_system__doc__},
5633
5634static long
5635os_system_impl(PyModuleDef *module, PyObject *command);
5636
5637static PyObject *
5638os_system(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5639{
5640 PyObject *return_value = NULL;
5641 static char *_keywords[] = {"command", NULL};
5642 PyObject *command = NULL;
5643 long _return_value;
5644
5645 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5646 "O&:system", _keywords,
5647 PyUnicode_FSConverter, &command))
5648 goto exit;
5649 _return_value = os_system_impl(module, command);
5650 if ((_return_value == -1) && PyErr_Occurred())
5651 goto exit;
5652 return_value = PyLong_FromLong(_return_value);
5653
5654exit:
5655 /* Cleanup for command */
5656 Py_XDECREF(command);
5657
5658 return return_value;
5659}
5660
5661static long
5662os_system_impl(PyModuleDef *module, PyObject *command)
5663/*[clinic end generated code: output=5be9f3c40ead3bad input=86a58554ba6094af]*/
5664{
5665 long result;
5666 char *bytes = PyBytes_AsString(command);
5667 Py_BEGIN_ALLOW_THREADS
5668 result = system(bytes);
5669 Py_END_ALLOW_THREADS
5670 return result;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005671}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00005672#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005673#endif /* HAVE_SYSTEM */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005674
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005675
Larry Hastings2f936352014-08-05 14:04:04 +10005676/*[clinic input]
5677os.umask
5678
5679 mask: int
5680 /
5681
5682Set the current numeric umask and return the previous umask.
5683[clinic start generated code]*/
5684
5685PyDoc_STRVAR(os_umask__doc__,
5686"umask($module, mask, /)\n"
5687"--\n"
5688"\n"
5689"Set the current numeric umask and return the previous umask.");
5690
5691#define OS_UMASK_METHODDEF \
5692 {"umask", (PyCFunction)os_umask, METH_VARARGS, os_umask__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005693
Barry Warsaw53699e91996-12-10 23:23:01 +00005694static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005695os_umask_impl(PyModuleDef *module, int mask);
5696
5697static PyObject *
5698os_umask(PyModuleDef *module, PyObject *args)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005699{
Larry Hastings2f936352014-08-05 14:04:04 +10005700 PyObject *return_value = NULL;
5701 int mask;
5702
5703 if (!PyArg_ParseTuple(args,
5704 "i:umask",
5705 &mask))
5706 goto exit;
5707 return_value = os_umask_impl(module, mask);
5708
5709exit:
5710 return return_value;
5711}
5712
5713static PyObject *
5714os_umask_impl(PyModuleDef *module, int mask)
5715/*[clinic end generated code: output=90048b39d2d4a961 input=ab6bfd9b24d8a7e8]*/
5716{
5717 int i = (int)umask(mask);
Victor Stinner8c62be82010-05-06 00:08:46 +00005718 if (i < 0)
5719 return posix_error();
5720 return PyLong_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005721}
5722
Brian Curtind40e6f72010-07-08 21:39:08 +00005723#ifdef MS_WINDOWS
5724
5725/* override the default DeleteFileW behavior so that directory
5726symlinks can be removed with this function, the same as with
5727Unix symlinks */
5728BOOL WINAPI Py_DeleteFileW(LPCWSTR lpFileName)
5729{
5730 WIN32_FILE_ATTRIBUTE_DATA info;
5731 WIN32_FIND_DATAW find_data;
5732 HANDLE find_data_handle;
5733 int is_directory = 0;
5734 int is_link = 0;
5735
5736 if (GetFileAttributesExW(lpFileName, GetFileExInfoStandard, &info)) {
5737 is_directory = info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00005738
Brian Curtind40e6f72010-07-08 21:39:08 +00005739 /* Get WIN32_FIND_DATA structure for the path to determine if
5740 it is a symlink */
5741 if(is_directory &&
5742 info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
5743 find_data_handle = FindFirstFileW(lpFileName, &find_data);
5744
5745 if(find_data_handle != INVALID_HANDLE_VALUE) {
Tim Golden0321cf22014-05-05 19:46:17 +01005746 /* IO_REPARSE_TAG_SYMLINK if it is a symlink and
5747 IO_REPARSE_TAG_MOUNT_POINT if it is a junction point. */
5748 is_link = find_data.dwReserved0 == IO_REPARSE_TAG_SYMLINK ||
5749 find_data.dwReserved0 == IO_REPARSE_TAG_MOUNT_POINT;
Brian Curtind40e6f72010-07-08 21:39:08 +00005750 FindClose(find_data_handle);
5751 }
5752 }
5753 }
5754
5755 if (is_directory && is_link)
5756 return RemoveDirectoryW(lpFileName);
5757
5758 return DeleteFileW(lpFileName);
5759}
5760#endif /* MS_WINDOWS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005761
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005762
Larry Hastings2f936352014-08-05 14:04:04 +10005763/*[clinic input]
5764os.unlink
5765
5766 path: path_t
5767 *
5768 dir_fd: dir_fd(requires='unlinkat')=None
5769
5770Remove a file (same as remove()).
5771
5772If dir_fd is not None, it should be a file descriptor open to a directory,
5773 and path should be relative; path will then be relative to that directory.
5774dir_fd may not be implemented on your platform.
5775 If it is unavailable, using it will raise a NotImplementedError.
5776
5777[clinic start generated code]*/
5778
5779PyDoc_STRVAR(os_unlink__doc__,
5780"unlink($module, /, path, *, dir_fd=None)\n"
5781"--\n"
5782"\n"
5783"Remove a file (same as remove()).\n"
5784"\n"
5785"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5786" and path should be relative; path will then be relative to that directory.\n"
5787"dir_fd may not be implemented on your platform.\n"
5788" If it is unavailable, using it will raise a NotImplementedError.");
5789
5790#define OS_UNLINK_METHODDEF \
5791 {"unlink", (PyCFunction)os_unlink, METH_VARARGS|METH_KEYWORDS, os_unlink__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005792
Barry Warsaw53699e91996-12-10 23:23:01 +00005793static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005794os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005795
Larry Hastings2f936352014-08-05 14:04:04 +10005796static PyObject *
5797os_unlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5798{
5799 PyObject *return_value = NULL;
5800 static char *_keywords[] = {"path", "dir_fd", NULL};
5801 path_t path = PATH_T_INITIALIZE("unlink", "path", 0, 0);
5802 int dir_fd = DEFAULT_DIR_FD;
5803
5804 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5805 "O&|$O&:unlink", _keywords,
5806 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5807 goto exit;
5808 return_value = os_unlink_impl(module, &path, dir_fd);
5809
5810exit:
5811 /* Cleanup for path */
5812 path_cleanup(&path);
5813
5814 return return_value;
5815}
5816
5817static PyObject *
5818os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd)
5819/*[clinic end generated code: output=59a6e66d67ff2e75 input=d7bcde2b1b2a2552]*/
5820{
5821 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07005822
5823 Py_BEGIN_ALLOW_THREADS
5824#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10005825 if (path->wide)
5826 result = Py_DeleteFileW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07005827 else
Larry Hastings2f936352014-08-05 14:04:04 +10005828 result = DeleteFileA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005829 result = !result; /* Windows, success=1, UNIX, success=0 */
5830#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07005831#ifdef HAVE_UNLINKAT
5832 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10005833 result = unlinkat(dir_fd, path->narrow, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005834 else
5835#endif /* HAVE_UNLINKAT */
Larry Hastings2f936352014-08-05 14:04:04 +10005836 result = unlink(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005837#endif
5838 Py_END_ALLOW_THREADS
5839
Larry Hastings2f936352014-08-05 14:04:04 +10005840 if (result)
5841 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005842
Larry Hastings2f936352014-08-05 14:04:04 +10005843 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00005844}
5845
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005846
Larry Hastings2f936352014-08-05 14:04:04 +10005847/*[clinic input]
5848os.remove = os.unlink
5849
5850Remove a file (same as unlink()).
5851
5852If dir_fd is not None, it should be a file descriptor open to a directory,
5853 and path should be relative; path will then be relative to that directory.
5854dir_fd may not be implemented on your platform.
5855 If it is unavailable, using it will raise a NotImplementedError.
5856[clinic start generated code]*/
5857
5858PyDoc_STRVAR(os_remove__doc__,
5859"remove($module, /, path, *, dir_fd=None)\n"
5860"--\n"
5861"\n"
5862"Remove a file (same as unlink()).\n"
5863"\n"
5864"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
5865" and path should be relative; path will then be relative to that directory.\n"
5866"dir_fd may not be implemented on your platform.\n"
5867" If it is unavailable, using it will raise a NotImplementedError.");
5868
5869#define OS_REMOVE_METHODDEF \
5870 {"remove", (PyCFunction)os_remove, METH_VARARGS|METH_KEYWORDS, os_remove__doc__},
5871
5872static PyObject *
5873os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd);
5874
5875static PyObject *
5876os_remove(PyModuleDef *module, PyObject *args, PyObject *kwargs)
5877{
5878 PyObject *return_value = NULL;
5879 static char *_keywords[] = {"path", "dir_fd", NULL};
5880 path_t path = PATH_T_INITIALIZE("remove", "path", 0, 0);
5881 int dir_fd = DEFAULT_DIR_FD;
5882
5883 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
5884 "O&|$O&:remove", _keywords,
5885 path_converter, &path, UNLINKAT_DIR_FD_CONVERTER, &dir_fd))
5886 goto exit;
5887 return_value = os_remove_impl(module, &path, dir_fd);
5888
5889exit:
5890 /* Cleanup for path */
5891 path_cleanup(&path);
5892
5893 return return_value;
5894}
5895
5896static PyObject *
5897os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd)
5898/*[clinic end generated code: output=cb170cf1e195b8ed input=e05c5ab55cd30983]*/
5899{
5900 return os_unlink_impl(module, path, dir_fd);
5901}
5902
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005903
Larry Hastings605a62d2012-06-24 04:33:36 -07005904static PyStructSequence_Field uname_result_fields[] = {
5905 {"sysname", "operating system name"},
5906 {"nodename", "name of machine on network (implementation-defined)"},
5907 {"release", "operating system release"},
5908 {"version", "operating system version"},
5909 {"machine", "hardware identifier"},
5910 {NULL}
5911};
5912
5913PyDoc_STRVAR(uname_result__doc__,
5914"uname_result: Result from os.uname().\n\n\
5915This object may be accessed either as a tuple of\n\
5916 (sysname, nodename, release, version, machine),\n\
5917or via the attributes sysname, nodename, release, version, and machine.\n\
5918\n\
5919See os.uname for more information.");
5920
5921static PyStructSequence_Desc uname_result_desc = {
5922 "uname_result", /* name */
5923 uname_result__doc__, /* doc */
5924 uname_result_fields,
5925 5
5926};
5927
5928static PyTypeObject UnameResultType;
5929
5930
5931#ifdef HAVE_UNAME
Larry Hastings2f936352014-08-05 14:04:04 +10005932/*[clinic input]
5933os.uname
5934
5935Return an object identifying the current operating system.
5936
5937The object behaves like a named tuple with the following fields:
5938 (sysname, nodename, release, version, machine)
5939
5940[clinic start generated code]*/
5941
5942PyDoc_STRVAR(os_uname__doc__,
5943"uname($module, /)\n"
5944"--\n"
5945"\n"
5946"Return an object identifying the current operating system.\n"
5947"\n"
5948"The object behaves like a named tuple with the following fields:\n"
5949" (sysname, nodename, release, version, machine)");
5950
5951#define OS_UNAME_METHODDEF \
5952 {"uname", (PyCFunction)os_uname, METH_NOARGS, os_uname__doc__},
5953
Barry Warsaw53699e91996-12-10 23:23:01 +00005954static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10005955os_uname_impl(PyModuleDef *module);
5956
5957static PyObject *
5958os_uname(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
5959{
5960 return os_uname_impl(module);
5961}
5962
5963static PyObject *
5964os_uname_impl(PyModuleDef *module)
5965/*[clinic end generated code: output=459a86521ff5041c input=e68bd246db3043ed]*/
Guido van Rossumc39de5f1992-02-05 11:15:54 +00005966{
Victor Stinner8c62be82010-05-06 00:08:46 +00005967 struct utsname u;
5968 int res;
Larry Hastings605a62d2012-06-24 04:33:36 -07005969 PyObject *value;
Neal Norwitze241ce82003-02-17 18:17:05 +00005970
Victor Stinner8c62be82010-05-06 00:08:46 +00005971 Py_BEGIN_ALLOW_THREADS
5972 res = uname(&u);
5973 Py_END_ALLOW_THREADS
5974 if (res < 0)
5975 return posix_error();
Larry Hastings605a62d2012-06-24 04:33:36 -07005976
5977 value = PyStructSequence_New(&UnameResultType);
5978 if (value == NULL)
5979 return NULL;
5980
5981#define SET(i, field) \
5982 { \
Victor Stinnera534fc42013-06-03 22:07:27 +02005983 PyObject *o = PyUnicode_DecodeFSDefault(field); \
Larry Hastings605a62d2012-06-24 04:33:36 -07005984 if (!o) { \
5985 Py_DECREF(value); \
5986 return NULL; \
5987 } \
5988 PyStructSequence_SET_ITEM(value, i, o); \
5989 } \
5990
5991 SET(0, u.sysname);
5992 SET(1, u.nodename);
5993 SET(2, u.release);
5994 SET(3, u.version);
5995 SET(4, u.machine);
5996
5997#undef SET
5998
5999 return value;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00006000}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006001#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006002
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006003
Larry Hastings9cf065c2012-06-22 16:30:09 -07006004
6005typedef struct {
6006 int now;
6007 time_t atime_s;
6008 long atime_ns;
6009 time_t mtime_s;
6010 long mtime_ns;
6011} utime_t;
6012
6013/*
Victor Stinner484df002014-10-09 13:52:31 +02006014 * these macros assume that "ut" is a pointer to a utime_t
Larry Hastings9cf065c2012-06-22 16:30:09 -07006015 * they also intentionally leak the declaration of a pointer named "time"
6016 */
6017#define UTIME_TO_TIMESPEC \
6018 struct timespec ts[2]; \
6019 struct timespec *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006020 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006021 time = NULL; \
6022 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006023 ts[0].tv_sec = ut->atime_s; \
6024 ts[0].tv_nsec = ut->atime_ns; \
6025 ts[1].tv_sec = ut->mtime_s; \
6026 ts[1].tv_nsec = ut->mtime_ns; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006027 time = ts; \
6028 } \
6029
6030#define UTIME_TO_TIMEVAL \
6031 struct timeval tv[2]; \
6032 struct timeval *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006033 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006034 time = NULL; \
6035 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006036 tv[0].tv_sec = ut->atime_s; \
6037 tv[0].tv_usec = ut->atime_ns / 1000; \
6038 tv[1].tv_sec = ut->mtime_s; \
6039 tv[1].tv_usec = ut->mtime_ns / 1000; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006040 time = tv; \
6041 } \
6042
6043#define UTIME_TO_UTIMBUF \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006044 struct utimbuf u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006045 struct utimbuf *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006046 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006047 time = NULL; \
6048 else { \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006049 u.actime = ut->atime_s; \
6050 u.modtime = ut->mtime_s; \
6051 time = &u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006052 }
6053
6054#define UTIME_TO_TIME_T \
6055 time_t timet[2]; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006056 time_t *time; \
Victor Stinner484df002014-10-09 13:52:31 +02006057 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006058 time = NULL; \
6059 else { \
Victor Stinner484df002014-10-09 13:52:31 +02006060 timet[0] = ut->atime_s; \
6061 timet[1] = ut->mtime_s; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02006062 time = timet; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07006063 } \
6064
6065
6066#define UTIME_HAVE_DIR_FD (defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT))
6067
6068#if UTIME_HAVE_DIR_FD
6069
6070static int
Victor Stinner484df002014-10-09 13:52:31 +02006071utime_dir_fd(utime_t *ut, int dir_fd, char *path, int follow_symlinks)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006072{
6073#ifdef HAVE_UTIMENSAT
6074 int flags = follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW;
6075 UTIME_TO_TIMESPEC;
6076 return utimensat(dir_fd, path, time, flags);
6077#elif defined(HAVE_FUTIMESAT)
6078 UTIME_TO_TIMEVAL;
6079 /*
6080 * follow_symlinks will never be false here;
6081 * we only allow !follow_symlinks and dir_fd together
6082 * if we have utimensat()
6083 */
6084 assert(follow_symlinks);
6085 return futimesat(dir_fd, path, time);
6086#endif
6087}
6088
Larry Hastings2f936352014-08-05 14:04:04 +10006089 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_converter
6090#else
6091 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings9cf065c2012-06-22 16:30:09 -07006092#endif
6093
6094#define UTIME_HAVE_FD (defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS))
6095
6096#if UTIME_HAVE_FD
6097
6098static int
Victor Stinner484df002014-10-09 13:52:31 +02006099utime_fd(utime_t *ut, int fd)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006100{
6101#ifdef HAVE_FUTIMENS
6102 UTIME_TO_TIMESPEC;
6103 return futimens(fd, time);
6104#else
6105 UTIME_TO_TIMEVAL;
6106 return futimes(fd, time);
6107#endif
6108}
6109
Larry Hastings2f936352014-08-05 14:04:04 +10006110 #define PATH_UTIME_HAVE_FD 1
6111#else
6112 #define PATH_UTIME_HAVE_FD 0
Larry Hastings9cf065c2012-06-22 16:30:09 -07006113#endif
6114
6115
6116#define UTIME_HAVE_NOFOLLOW_SYMLINKS \
6117 (defined(HAVE_UTIMENSAT) || defined(HAVE_LUTIMES))
6118
6119#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6120
6121static int
Victor Stinner484df002014-10-09 13:52:31 +02006122utime_nofollow_symlinks(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006123{
6124#ifdef HAVE_UTIMENSAT
6125 UTIME_TO_TIMESPEC;
6126 return utimensat(DEFAULT_DIR_FD, path, time, AT_SYMLINK_NOFOLLOW);
6127#else
6128 UTIME_TO_TIMEVAL;
6129 return lutimes(path, time);
6130#endif
6131}
6132
6133#endif
6134
6135#ifndef MS_WINDOWS
6136
6137static int
Victor Stinner484df002014-10-09 13:52:31 +02006138utime_default(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07006139{
6140#ifdef HAVE_UTIMENSAT
6141 UTIME_TO_TIMESPEC;
6142 return utimensat(DEFAULT_DIR_FD, path, time, 0);
6143#elif defined(HAVE_UTIMES)
6144 UTIME_TO_TIMEVAL;
6145 return utimes(path, time);
6146#elif defined(HAVE_UTIME_H)
6147 UTIME_TO_UTIMBUF;
6148 return utime(path, time);
6149#else
6150 UTIME_TO_TIME_T;
6151 return utime(path, time);
6152#endif
6153}
6154
6155#endif
6156
Larry Hastings76ad59b2012-05-03 00:30:07 -07006157static int
6158split_py_long_to_s_and_ns(PyObject *py_long, time_t *s, long *ns)
6159{
6160 int result = 0;
Benjamin Petersonfbd85a02012-05-04 11:06:09 -04006161 PyObject *divmod;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006162 divmod = PyNumber_Divmod(py_long, billion);
6163 if (!divmod)
6164 goto exit;
6165 *s = _PyLong_AsTime_t(PyTuple_GET_ITEM(divmod, 0));
6166 if ((*s == -1) && PyErr_Occurred())
6167 goto exit;
6168 *ns = PyLong_AsLong(PyTuple_GET_ITEM(divmod, 1));
Benjamin Peterson35a8f0d2012-05-04 01:10:59 -04006169 if ((*ns == -1) && PyErr_Occurred())
Larry Hastings76ad59b2012-05-03 00:30:07 -07006170 goto exit;
6171
6172 result = 1;
6173exit:
6174 Py_XDECREF(divmod);
6175 return result;
6176}
6177
Larry Hastings2f936352014-08-05 14:04:04 +10006178
6179/*[clinic input]
6180os.utime
6181
6182 path: path_t(allow_fd='PATH_UTIME_HAVE_FD')
6183 times: object = NULL
6184 *
6185 ns: object = NULL
6186 dir_fd: dir_fd(requires='futimensat') = None
6187 follow_symlinks: bool=True
6188
6189# "utime(path, times=None, *, ns=None, dir_fd=None, follow_symlinks=True)\n\
6190
6191Set the access and modified time of path.
6192
6193path may always be specified as a string.
6194On some platforms, path may also be specified as an open file descriptor.
6195 If this functionality is unavailable, using it raises an exception.
6196
6197If times is not None, it must be a tuple (atime, mtime);
6198 atime and mtime should be expressed as float seconds since the epoch.
6199If ns is not None, it must be a tuple (atime_ns, mtime_ns);
6200 atime_ns and mtime_ns should be expressed as integer nanoseconds
6201 since the epoch.
6202If both times and ns are None, utime uses the current time.
6203Specifying tuples for both times and ns is an error.
6204
6205If dir_fd is not None, it should be a file descriptor open to a directory,
6206 and path should be relative; path will then be relative to that directory.
6207If follow_symlinks is False, and the last element of the path is a symbolic
6208 link, utime will modify the symbolic link itself instead of the file the
6209 link points to.
6210It is an error to use dir_fd or follow_symlinks when specifying path
6211 as an open file descriptor.
6212dir_fd and follow_symlinks may not be available on your platform.
6213 If they are unavailable, using them will raise a NotImplementedError.
6214
6215[clinic start generated code]*/
6216
6217PyDoc_STRVAR(os_utime__doc__,
6218"utime($module, /, path, times=None, *, ns=None, dir_fd=None,\n"
6219" follow_symlinks=True)\n"
6220"--\n"
6221"\n"
6222"Set the access and modified time of path.\n"
6223"\n"
6224"path may always be specified as a string.\n"
6225"On some platforms, path may also be specified as an open file descriptor.\n"
6226" If this functionality is unavailable, using it raises an exception.\n"
6227"\n"
6228"If times is not None, it must be a tuple (atime, mtime);\n"
6229" atime and mtime should be expressed as float seconds since the epoch.\n"
6230"If ns is not None, it must be a tuple (atime_ns, mtime_ns);\n"
6231" atime_ns and mtime_ns should be expressed as integer nanoseconds\n"
6232" since the epoch.\n"
6233"If both times and ns are None, utime uses the current time.\n"
6234"Specifying tuples for both times and ns is an error.\n"
6235"\n"
6236"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
6237" and path should be relative; path will then be relative to that directory.\n"
6238"If follow_symlinks is False, and the last element of the path is a symbolic\n"
6239" link, utime will modify the symbolic link itself instead of the file the\n"
6240" link points to.\n"
6241"It is an error to use dir_fd or follow_symlinks when specifying path\n"
6242" as an open file descriptor.\n"
6243"dir_fd and follow_symlinks may not be available on your platform.\n"
6244" If they are unavailable, using them will raise a NotImplementedError.");
6245
6246#define OS_UTIME_METHODDEF \
6247 {"utime", (PyCFunction)os_utime, METH_VARARGS|METH_KEYWORDS, os_utime__doc__},
6248
Larry Hastings9cf065c2012-06-22 16:30:09 -07006249static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006250os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks);
6251
6252static PyObject *
6253os_utime(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Larry Hastings76ad59b2012-05-03 00:30:07 -07006254{
Larry Hastings2f936352014-08-05 14:04:04 +10006255 PyObject *return_value = NULL;
6256 static char *_keywords[] = {"path", "times", "ns", "dir_fd", "follow_symlinks", NULL};
6257 path_t path = PATH_T_INITIALIZE("utime", "path", 0, PATH_UTIME_HAVE_FD);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006258 PyObject *times = NULL;
6259 PyObject *ns = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07006260 int dir_fd = DEFAULT_DIR_FD;
6261 int follow_symlinks = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006262
Larry Hastings2f936352014-08-05 14:04:04 +10006263 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6264 "O&|O$OO&p:utime", _keywords,
6265 path_converter, &path, &times, &ns, FUTIMENSAT_DIR_FD_CONVERTER, &dir_fd, &follow_symlinks))
6266 goto exit;
6267 return_value = os_utime_impl(module, &path, times, ns, dir_fd, follow_symlinks);
Larry Hastings76ad59b2012-05-03 00:30:07 -07006268
Larry Hastings2f936352014-08-05 14:04:04 +10006269exit:
6270 /* Cleanup for path */
6271 path_cleanup(&path);
6272
6273 return return_value;
6274}
6275
6276static PyObject *
6277os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times, PyObject *ns, int dir_fd, int follow_symlinks)
6278/*[clinic end generated code: output=891489c35cc68c5d input=1f18c17d5941aa82]*/
6279{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006280#ifdef MS_WINDOWS
6281 HANDLE hFile;
6282 FILETIME atime, mtime;
6283#else
6284 int result;
6285#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006286
Larry Hastings9cf065c2012-06-22 16:30:09 -07006287 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10006288 utime_t utime;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006289
Christian Heimesb3c87242013-08-01 00:08:16 +02006290 memset(&utime, 0, sizeof(utime_t));
Larry Hastings76ad59b2012-05-03 00:30:07 -07006291
Larry Hastings9cf065c2012-06-22 16:30:09 -07006292 if (times && (times != Py_None) && ns) {
6293 PyErr_SetString(PyExc_ValueError,
6294 "utime: you may specify either 'times'"
6295 " or 'ns' but not both");
6296 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006297 }
6298
6299 if (times && (times != Py_None)) {
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006300 time_t a_sec, m_sec;
6301 long a_nsec, m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006302 if (!PyTuple_CheckExact(times) || (PyTuple_Size(times) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006303 PyErr_SetString(PyExc_TypeError,
6304 "utime: 'times' must be either"
6305 " a tuple of two ints or None");
6306 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006307 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006308 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006309 if (_PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 0),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006310 &a_sec, &a_nsec, _PyTime_ROUND_DOWN) == -1 ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006311 _PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 1),
Victor Stinner3c1b3792014-02-17 00:02:43 +01006312 &m_sec, &m_nsec, _PyTime_ROUND_DOWN) == -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006313 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006314 }
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02006315 utime.atime_s = a_sec;
6316 utime.atime_ns = a_nsec;
6317 utime.mtime_s = m_sec;
6318 utime.mtime_ns = m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006319 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006320 else if (ns) {
Larry Hastings76ad59b2012-05-03 00:30:07 -07006321 if (!PyTuple_CheckExact(ns) || (PyTuple_Size(ns) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006322 PyErr_SetString(PyExc_TypeError,
6323 "utime: 'ns' must be a tuple of two ints");
6324 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006325 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006326 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006327 if (!split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 0),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006328 &utime.atime_s, &utime.atime_ns) ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006329 !split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 1),
Larry Hastings9cf065c2012-06-22 16:30:09 -07006330 &utime.mtime_s, &utime.mtime_ns)) {
6331 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006332 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07006333 }
6334 else {
6335 /* times and ns are both None/unspecified. use "now". */
6336 utime.now = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006337 }
6338
Larry Hastings9cf065c2012-06-22 16:30:09 -07006339#if !UTIME_HAVE_NOFOLLOW_SYMLINKS
6340 if (follow_symlinks_specified("utime", follow_symlinks))
6341 goto exit;
6342#endif
Benjamin Petersonb399ab22012-05-04 01:31:13 -04006343
Larry Hastings2f936352014-08-05 14:04:04 +10006344 if (path_and_dir_fd_invalid("utime", path, dir_fd) ||
6345 dir_fd_and_fd_invalid("utime", dir_fd, path->fd) ||
6346 fd_and_follow_symlinks_invalid("utime", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -07006347 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07006348
Larry Hastings9cf065c2012-06-22 16:30:09 -07006349#if !defined(HAVE_UTIMENSAT)
6350 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
Georg Brandl969288e2012-06-26 09:25:44 +02006351 PyErr_SetString(PyExc_ValueError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006352 "utime: cannot use dir_fd and follow_symlinks "
6353 "together on this platform");
6354 goto exit;
6355 }
6356#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07006357
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006358#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07006359 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006360 if (path->wide)
6361 hFile = CreateFileW(path->wide, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006362 NULL, OPEN_EXISTING,
6363 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006364 else
Larry Hastings2f936352014-08-05 14:04:04 +10006365 hFile = CreateFileA(path->narrow, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00006366 NULL, OPEN_EXISTING,
6367 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006368 Py_END_ALLOW_THREADS
6369 if (hFile == INVALID_HANDLE_VALUE) {
Larry Hastings2f936352014-08-05 14:04:04 +10006370 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006371 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07006372 }
6373
Larry Hastings9cf065c2012-06-22 16:30:09 -07006374 if (utime.now) {
Antoine Pitrou91a7af32013-11-23 15:23:26 +01006375 GetSystemTimeAsFileTime(&mtime);
6376 atime = mtime;
Victor Stinner8c62be82010-05-06 00:08:46 +00006377 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006378 else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006379 time_t_to_FILE_TIME(utime.atime_s, utime.atime_ns, &atime);
6380 time_t_to_FILE_TIME(utime.mtime_s, utime.mtime_ns, &mtime);
Victor Stinner8c62be82010-05-06 00:08:46 +00006381 }
6382 if (!SetFileTime(hFile, NULL, &atime, &mtime)) {
6383 /* Avoid putting the file name into the error here,
6384 as that may confuse the user into believing that
6385 something is wrong with the file, when it also
6386 could be the time stamp that gives a problem. */
Victor Stinnerb024e842012-10-31 22:24:06 +01006387 PyErr_SetFromWindowsErr(0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006388 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006389 }
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006390#else /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006391 Py_BEGIN_ALLOW_THREADS
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00006392
Larry Hastings9cf065c2012-06-22 16:30:09 -07006393#if UTIME_HAVE_NOFOLLOW_SYMLINKS
6394 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10006395 result = utime_nofollow_symlinks(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006396 else
Larry Hastings9e3e70b2011-09-08 19:29:07 -07006397#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07006398
6399#if UTIME_HAVE_DIR_FD
6400 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10006401 result = utime_dir_fd(&utime, dir_fd, path->narrow, follow_symlinks);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006402 else
6403#endif
6404
6405#if UTIME_HAVE_FD
Larry Hastings2f936352014-08-05 14:04:04 +10006406 if (path->fd != -1)
6407 result = utime_fd(&utime, path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006408 else
6409#endif
6410
Larry Hastings2f936352014-08-05 14:04:04 +10006411 result = utime_default(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006412
6413 Py_END_ALLOW_THREADS
6414
6415 if (result < 0) {
6416 /* see previous comment about not putting filename in error here */
6417 return_value = posix_error();
6418 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00006419 }
Larry Hastings76ad59b2012-05-03 00:30:07 -07006420
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00006421#endif /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07006422
6423 Py_INCREF(Py_None);
6424 return_value = Py_None;
6425
6426exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006427#ifdef MS_WINDOWS
6428 if (hFile != INVALID_HANDLE_VALUE)
6429 CloseHandle(hFile);
6430#endif
6431 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00006432}
6433
Guido van Rossum3b066191991-06-04 19:40:25 +00006434/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006435
Larry Hastings2f936352014-08-05 14:04:04 +10006436
6437/*[clinic input]
6438os._exit
6439
6440 status: int
6441
6442Exit to the system with specified status, without normal exit processing.
6443[clinic start generated code]*/
6444
6445PyDoc_STRVAR(os__exit__doc__,
6446"_exit($module, /, status)\n"
6447"--\n"
6448"\n"
6449"Exit to the system with specified status, without normal exit processing.");
6450
6451#define OS__EXIT_METHODDEF \
6452 {"_exit", (PyCFunction)os__exit, METH_VARARGS|METH_KEYWORDS, os__exit__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006453
Barry Warsaw53699e91996-12-10 23:23:01 +00006454static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006455os__exit_impl(PyModuleDef *module, int status);
6456
6457static PyObject *
6458os__exit(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum85e3b011991-06-03 12:42:10 +00006459{
Larry Hastings2f936352014-08-05 14:04:04 +10006460 PyObject *return_value = NULL;
6461 static char *_keywords[] = {"status", NULL};
6462 int status;
6463
6464 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6465 "i:_exit", _keywords,
6466 &status))
6467 goto exit;
6468 return_value = os__exit_impl(module, status);
6469
6470exit:
6471 return return_value;
6472}
6473
6474static PyObject *
6475os__exit_impl(PyModuleDef *module, int status)
6476/*[clinic end generated code: output=4f9858c4cc2dcb89 input=5e6d57556b0c4a62]*/
6477{
6478 _exit(status);
Victor Stinner8c62be82010-05-06 00:08:46 +00006479 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006480}
6481
Martin v. Löwis114619e2002-10-07 06:44:21 +00006482#if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
6483static void
Martin v. Löwis725507b2006-03-07 12:08:51 +00006484free_string_array(char **array, Py_ssize_t count)
Martin v. Löwis114619e2002-10-07 06:44:21 +00006485{
Victor Stinner8c62be82010-05-06 00:08:46 +00006486 Py_ssize_t i;
6487 for (i = 0; i < count; i++)
6488 PyMem_Free(array[i]);
6489 PyMem_DEL(array);
Martin v. Löwis114619e2002-10-07 06:44:21 +00006490}
Martin v. Löwis011e8422009-05-05 04:43:17 +00006491
Antoine Pitrou69f71142009-05-24 21:25:49 +00006492static
Martin v. Löwis011e8422009-05-05 04:43:17 +00006493int fsconvert_strdup(PyObject *o, char**out)
6494{
Victor Stinner8c62be82010-05-06 00:08:46 +00006495 PyObject *bytes;
6496 Py_ssize_t size;
6497 if (!PyUnicode_FSConverter(o, &bytes))
6498 return 0;
6499 size = PyBytes_GET_SIZE(bytes);
6500 *out = PyMem_Malloc(size+1);
Victor Stinner50abf222013-11-07 23:56:10 +01006501 if (!*out) {
6502 PyErr_NoMemory();
Victor Stinner8c62be82010-05-06 00:08:46 +00006503 return 0;
Victor Stinner50abf222013-11-07 23:56:10 +01006504 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006505 memcpy(*out, PyBytes_AsString(bytes), size+1);
6506 Py_DECREF(bytes);
6507 return 1;
Martin v. Löwis011e8422009-05-05 04:43:17 +00006508}
Martin v. Löwis114619e2002-10-07 06:44:21 +00006509#endif
6510
Ross Lagerwall7807c352011-03-17 20:20:30 +02006511#if defined(HAVE_EXECV) || defined (HAVE_FEXECVE)
Victor Stinner13bb71c2010-04-23 21:41:56 +00006512static char**
6513parse_envlist(PyObject* env, Py_ssize_t *envc_ptr)
6514{
Victor Stinner8c62be82010-05-06 00:08:46 +00006515 char **envlist;
6516 Py_ssize_t i, pos, envc;
6517 PyObject *keys=NULL, *vals=NULL;
6518 PyObject *key, *val, *key2, *val2;
6519 char *p, *k, *v;
6520 size_t len;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006521
Victor Stinner8c62be82010-05-06 00:08:46 +00006522 i = PyMapping_Size(env);
6523 if (i < 0)
6524 return NULL;
6525 envlist = PyMem_NEW(char *, i + 1);
6526 if (envlist == NULL) {
6527 PyErr_NoMemory();
6528 return NULL;
6529 }
6530 envc = 0;
6531 keys = PyMapping_Keys(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006532 if (!keys)
6533 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00006534 vals = PyMapping_Values(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01006535 if (!vals)
Victor Stinner8c62be82010-05-06 00:08:46 +00006536 goto error;
6537 if (!PyList_Check(keys) || !PyList_Check(vals)) {
6538 PyErr_Format(PyExc_TypeError,
6539 "env.keys() or env.values() is not a list");
6540 goto error;
6541 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006542
Victor Stinner8c62be82010-05-06 00:08:46 +00006543 for (pos = 0; pos < i; pos++) {
6544 key = PyList_GetItem(keys, pos);
6545 val = PyList_GetItem(vals, pos);
6546 if (!key || !val)
6547 goto error;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006548
Victor Stinner8c62be82010-05-06 00:08:46 +00006549 if (PyUnicode_FSConverter(key, &key2) == 0)
6550 goto error;
6551 if (PyUnicode_FSConverter(val, &val2) == 0) {
6552 Py_DECREF(key2);
6553 goto error;
6554 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00006555
Victor Stinner8c62be82010-05-06 00:08:46 +00006556 k = PyBytes_AsString(key2);
6557 v = PyBytes_AsString(val2);
6558 len = PyBytes_GET_SIZE(key2) + PyBytes_GET_SIZE(val2) + 2;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006559
Victor Stinner8c62be82010-05-06 00:08:46 +00006560 p = PyMem_NEW(char, len);
6561 if (p == NULL) {
6562 PyErr_NoMemory();
6563 Py_DECREF(key2);
6564 Py_DECREF(val2);
6565 goto error;
6566 }
6567 PyOS_snprintf(p, len, "%s=%s", k, v);
6568 envlist[envc++] = p;
6569 Py_DECREF(key2);
6570 Py_DECREF(val2);
Victor Stinner8c62be82010-05-06 00:08:46 +00006571 }
6572 Py_DECREF(vals);
6573 Py_DECREF(keys);
Victor Stinner13bb71c2010-04-23 21:41:56 +00006574
Victor Stinner8c62be82010-05-06 00:08:46 +00006575 envlist[envc] = 0;
6576 *envc_ptr = envc;
6577 return envlist;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006578
6579error:
Victor Stinner8c62be82010-05-06 00:08:46 +00006580 Py_XDECREF(keys);
6581 Py_XDECREF(vals);
6582 while (--envc >= 0)
6583 PyMem_DEL(envlist[envc]);
6584 PyMem_DEL(envlist);
6585 return NULL;
Victor Stinner13bb71c2010-04-23 21:41:56 +00006586}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006587
Ross Lagerwall7807c352011-03-17 20:20:30 +02006588static char**
6589parse_arglist(PyObject* argv, Py_ssize_t *argc)
6590{
6591 int i;
6592 char **argvlist = PyMem_NEW(char *, *argc+1);
6593 if (argvlist == NULL) {
6594 PyErr_NoMemory();
6595 return NULL;
6596 }
6597 for (i = 0; i < *argc; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006598 PyObject* item = PySequence_ITEM(argv, i);
6599 if (item == NULL)
6600 goto fail;
6601 if (!fsconvert_strdup(item, &argvlist[i])) {
6602 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006603 goto fail;
6604 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006605 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006606 }
6607 argvlist[*argc] = NULL;
6608 return argvlist;
6609fail:
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02006610 *argc = i;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006611 free_string_array(argvlist, *argc);
6612 return NULL;
6613}
6614#endif
6615
Larry Hastings2f936352014-08-05 14:04:04 +10006616
Ross Lagerwall7807c352011-03-17 20:20:30 +02006617#ifdef HAVE_EXECV
Larry Hastings2f936352014-08-05 14:04:04 +10006618/*[clinic input]
6619os.execv
6620
6621 path: FSConverter
6622 Path of executable file.
6623 argv: object
6624 Tuple or list of strings.
6625 /
6626
6627Execute an executable path with arguments, replacing current process.
6628[clinic start generated code]*/
6629
6630PyDoc_STRVAR(os_execv__doc__,
6631"execv($module, path, argv, /)\n"
6632"--\n"
6633"\n"
6634"Execute an executable path with arguments, replacing current process.\n"
6635"\n"
6636" path\n"
6637" Path of executable file.\n"
6638" argv\n"
6639" Tuple or list of strings.");
6640
6641#define OS_EXECV_METHODDEF \
6642 {"execv", (PyCFunction)os_execv, METH_VARARGS, os_execv__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02006643
6644static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006645os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv);
6646
6647static PyObject *
6648os_execv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006649{
Larry Hastings2f936352014-08-05 14:04:04 +10006650 PyObject *return_value = NULL;
6651 PyObject *path = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006652 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006653
6654 if (!PyArg_ParseTuple(args,
6655 "O&O:execv",
6656 PyUnicode_FSConverter, &path, &argv))
6657 goto exit;
6658 return_value = os_execv_impl(module, path, argv);
6659
6660exit:
6661 /* Cleanup for path */
6662 Py_XDECREF(path);
6663
6664 return return_value;
6665}
6666
6667static PyObject *
6668os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv)
6669/*[clinic end generated code: output=b0f5f2caa6097edc input=96041559925e5229]*/
6670{
6671 char *path_char;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006672 char **argvlist;
6673 Py_ssize_t argc;
6674
6675 /* execv has two arguments: (path, argv), where
6676 argv is a list or tuple of strings. */
6677
Larry Hastings2f936352014-08-05 14:04:04 +10006678 path_char = PyBytes_AsString(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006679 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
6680 PyErr_SetString(PyExc_TypeError,
6681 "execv() arg 2 must be a tuple or list");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006682 return NULL;
6683 }
6684 argc = PySequence_Size(argv);
6685 if (argc < 1) {
6686 PyErr_SetString(PyExc_ValueError, "execv() arg 2 must not be empty");
Ross Lagerwall7807c352011-03-17 20:20:30 +02006687 return NULL;
6688 }
6689
6690 argvlist = parse_arglist(argv, &argc);
6691 if (argvlist == NULL) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02006692 return NULL;
6693 }
6694
Larry Hastings2f936352014-08-05 14:04:04 +10006695 execv(path_char, argvlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006696
6697 /* If we get here it's definitely an error */
6698
6699 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006700 return posix_error();
6701}
6702
Larry Hastings2f936352014-08-05 14:04:04 +10006703
6704/*[clinic input]
6705os.execve
6706
6707 path: path_t(allow_fd='PATH_HAVE_FEXECVE')
6708 Path of executable file.
6709 argv: object
6710 Tuple or list of strings.
6711 env: object
6712 Dictionary of strings mapping to strings.
6713
6714Execute an executable path with arguments, replacing current process.
6715[clinic start generated code]*/
6716
6717PyDoc_STRVAR(os_execve__doc__,
6718"execve($module, /, path, argv, env)\n"
6719"--\n"
6720"\n"
6721"Execute an executable path with arguments, replacing current process.\n"
6722"\n"
6723" path\n"
6724" Path of executable file.\n"
6725" argv\n"
6726" Tuple or list of strings.\n"
6727" env\n"
6728" Dictionary of strings mapping to strings.");
6729
6730#define OS_EXECVE_METHODDEF \
6731 {"execve", (PyCFunction)os_execve, METH_VARARGS|METH_KEYWORDS, os_execve__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006732
Barry Warsaw53699e91996-12-10 23:23:01 +00006733static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006734os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env);
6735
6736static PyObject *
6737os_execve(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006738{
Larry Hastings2f936352014-08-05 14:04:04 +10006739 PyObject *return_value = NULL;
6740 static char *_keywords[] = {"path", "argv", "env", NULL};
6741 path_t path = PATH_T_INITIALIZE("execve", "path", 0, PATH_HAVE_FEXECVE);
6742 PyObject *argv;
6743 PyObject *env;
6744
6745 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
6746 "O&OO:execve", _keywords,
6747 path_converter, &path, &argv, &env))
6748 goto exit;
6749 return_value = os_execve_impl(module, &path, argv, env);
6750
6751exit:
6752 /* Cleanup for path */
6753 path_cleanup(&path);
6754
6755 return return_value;
6756}
6757
6758static PyObject *
6759os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv, PyObject *env)
6760/*[clinic end generated code: output=fb283760f5d15ab7 input=626804fa092606d9]*/
6761{
Larry Hastings9cf065c2012-06-22 16:30:09 -07006762 char **argvlist = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006763 char **envlist;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006764 Py_ssize_t argc, envc;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006765
Victor Stinner8c62be82010-05-06 00:08:46 +00006766 /* execve has three arguments: (path, argv, env), where
6767 argv is a list or tuple of strings and env is a dictionary
6768 like posix.environ. */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006769
Ross Lagerwall7807c352011-03-17 20:20:30 +02006770 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006771 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006772 "execve: argv must be a tuple or list");
6773 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006774 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02006775 argc = PySequence_Size(argv);
Victor Stinner8c62be82010-05-06 00:08:46 +00006776 if (!PyMapping_Check(env)) {
6777 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07006778 "execve: environment must be a mapping object");
6779 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006780 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006781
Ross Lagerwall7807c352011-03-17 20:20:30 +02006782 argvlist = parse_arglist(argv, &argc);
Victor Stinner8c62be82010-05-06 00:08:46 +00006783 if (argvlist == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07006784 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00006785 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00006786
Victor Stinner8c62be82010-05-06 00:08:46 +00006787 envlist = parse_envlist(env, &envc);
6788 if (envlist == NULL)
Ross Lagerwall7807c352011-03-17 20:20:30 +02006789 goto fail;
6790
Larry Hastings9cf065c2012-06-22 16:30:09 -07006791#ifdef HAVE_FEXECVE
Larry Hastings2f936352014-08-05 14:04:04 +10006792 if (path->fd > -1)
6793 fexecve(path->fd, argvlist, envlist);
Larry Hastings9cf065c2012-06-22 16:30:09 -07006794 else
6795#endif
Larry Hastings2f936352014-08-05 14:04:04 +10006796 execve(path->narrow, argvlist, envlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006797
6798 /* If we get here it's definitely an error */
6799
Larry Hastings2f936352014-08-05 14:04:04 +10006800 path_error(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006801
6802 while (--envc >= 0)
6803 PyMem_DEL(envlist[envc]);
6804 PyMem_DEL(envlist);
6805 fail:
Larry Hastings9cf065c2012-06-22 16:30:09 -07006806 if (argvlist)
6807 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02006808 return NULL;
6809}
Larry Hastings9cf065c2012-06-22 16:30:09 -07006810#endif /* HAVE_EXECV */
6811
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006812
Guido van Rossuma1065681999-01-25 23:20:23 +00006813#ifdef HAVE_SPAWNV
Larry Hastings2f936352014-08-05 14:04:04 +10006814/*[clinic input]
6815os.spawnv
6816
6817 mode: int
6818 Mode of process creation.
6819 path: FSConverter
6820 Path of executable file.
6821 argv: object
6822 Tuple or list of strings.
6823 /
6824
6825Execute the program specified by path in a new process.
6826[clinic start generated code]*/
6827
6828PyDoc_STRVAR(os_spawnv__doc__,
6829"spawnv($module, mode, path, argv, /)\n"
6830"--\n"
6831"\n"
6832"Execute the program specified by path in a new process.\n"
6833"\n"
6834" mode\n"
6835" Mode of process creation.\n"
6836" path\n"
6837" Path of executable file.\n"
6838" argv\n"
6839" Tuple or list of strings.");
6840
6841#define OS_SPAWNV_METHODDEF \
6842 {"spawnv", (PyCFunction)os_spawnv, METH_VARARGS, os_spawnv__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00006843
6844static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006845os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv);
6846
6847static PyObject *
6848os_spawnv(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00006849{
Larry Hastings2f936352014-08-05 14:04:04 +10006850 PyObject *return_value = NULL;
6851 int mode;
6852 PyObject *path = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00006853 PyObject *argv;
Larry Hastings2f936352014-08-05 14:04:04 +10006854
6855 if (!PyArg_ParseTuple(args,
6856 "iO&O:spawnv",
6857 &mode, PyUnicode_FSConverter, &path, &argv))
6858 goto exit;
6859 return_value = os_spawnv_impl(module, mode, path, argv);
6860
6861exit:
6862 /* Cleanup for path */
6863 Py_XDECREF(path);
6864
6865 return return_value;
6866}
6867
6868static PyObject *
6869os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv)
6870/*[clinic end generated code: output=dfee6be062e780e3 input=042c91dfc1e6debc]*/
6871{
6872 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00006873 char **argvlist;
Larry Hastings2f936352014-08-05 14:04:04 +10006874 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00006875 Py_ssize_t argc;
6876 Py_intptr_t spawnval;
6877 PyObject *(*getitem)(PyObject *, Py_ssize_t);
Guido van Rossuma1065681999-01-25 23:20:23 +00006878
Victor Stinner8c62be82010-05-06 00:08:46 +00006879 /* spawnv has three arguments: (mode, path, argv), where
6880 argv is a list or tuple of strings. */
Guido van Rossuma1065681999-01-25 23:20:23 +00006881
Larry Hastings2f936352014-08-05 14:04:04 +10006882 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00006883 if (PyList_Check(argv)) {
6884 argc = PyList_Size(argv);
6885 getitem = PyList_GetItem;
6886 }
6887 else if (PyTuple_Check(argv)) {
6888 argc = PyTuple_Size(argv);
6889 getitem = PyTuple_GetItem;
6890 }
6891 else {
6892 PyErr_SetString(PyExc_TypeError,
6893 "spawnv() arg 2 must be a tuple or list");
Victor Stinner8c62be82010-05-06 00:08:46 +00006894 return NULL;
6895 }
Guido van Rossuma1065681999-01-25 23:20:23 +00006896
Victor Stinner8c62be82010-05-06 00:08:46 +00006897 argvlist = PyMem_NEW(char *, argc+1);
6898 if (argvlist == NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006899 return PyErr_NoMemory();
6900 }
6901 for (i = 0; i < argc; i++) {
6902 if (!fsconvert_strdup((*getitem)(argv, i),
6903 &argvlist[i])) {
6904 free_string_array(argvlist, i);
6905 PyErr_SetString(
6906 PyExc_TypeError,
6907 "spawnv() arg 2 must contain only strings");
Victor Stinner8c62be82010-05-06 00:08:46 +00006908 return NULL;
6909 }
6910 }
6911 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00006912
Victor Stinner8c62be82010-05-06 00:08:46 +00006913 if (mode == _OLD_P_OVERLAY)
6914 mode = _P_OVERLAY;
Tim Peters5aa91602002-01-30 05:46:57 +00006915
Victor Stinner8c62be82010-05-06 00:08:46 +00006916 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10006917 spawnval = _spawnv(mode, path_char, argvlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00006918 Py_END_ALLOW_THREADS
Tim Peters5aa91602002-01-30 05:46:57 +00006919
Victor Stinner8c62be82010-05-06 00:08:46 +00006920 free_string_array(argvlist, argc);
Guido van Rossuma1065681999-01-25 23:20:23 +00006921
Victor Stinner8c62be82010-05-06 00:08:46 +00006922 if (spawnval == -1)
6923 return posix_error();
6924 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006925 return Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00006926}
6927
6928
Larry Hastings2f936352014-08-05 14:04:04 +10006929/*[clinic input]
6930os.spawnve
6931
6932 mode: int
6933 Mode of process creation.
6934 path: FSConverter
6935 Path of executable file.
6936 argv: object
6937 Tuple or list of strings.
6938 env: object
6939 Dictionary of strings mapping to strings.
6940 /
6941
6942Execute the program specified by path in a new process.
6943[clinic start generated code]*/
6944
6945PyDoc_STRVAR(os_spawnve__doc__,
6946"spawnve($module, mode, path, argv, env, /)\n"
6947"--\n"
6948"\n"
6949"Execute the program specified by path in a new process.\n"
6950"\n"
6951" mode\n"
6952" Mode of process creation.\n"
6953" path\n"
6954" Path of executable file.\n"
6955" argv\n"
6956" Tuple or list of strings.\n"
6957" env\n"
6958" Dictionary of strings mapping to strings.");
6959
6960#define OS_SPAWNVE_METHODDEF \
6961 {"spawnve", (PyCFunction)os_spawnve, METH_VARARGS, os_spawnve__doc__},
Guido van Rossuma1065681999-01-25 23:20:23 +00006962
6963static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006964os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env);
6965
6966static PyObject *
6967os_spawnve(PyModuleDef *module, PyObject *args)
Guido van Rossuma1065681999-01-25 23:20:23 +00006968{
Larry Hastings2f936352014-08-05 14:04:04 +10006969 PyObject *return_value = NULL;
6970 int mode;
6971 PyObject *path = NULL;
6972 PyObject *argv;
6973 PyObject *env;
6974
6975 if (!PyArg_ParseTuple(args,
6976 "iO&OO:spawnve",
6977 &mode, PyUnicode_FSConverter, &path, &argv, &env))
6978 goto exit;
6979 return_value = os_spawnve_impl(module, mode, path, argv, env);
6980
6981exit:
6982 /* Cleanup for path */
6983 Py_XDECREF(path);
6984
6985 return return_value;
6986}
6987
6988static PyObject *
6989os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv, PyObject *env)
6990/*[clinic end generated code: output=6f7df38473f63c7c input=02362fd937963f8f]*/
6991{
6992 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00006993 char **argvlist;
6994 char **envlist;
6995 PyObject *res = NULL;
Antoine Pitrou22e41552010-08-15 18:07:50 +00006996 Py_ssize_t argc, i, envc;
Victor Stinner8c62be82010-05-06 00:08:46 +00006997 Py_intptr_t spawnval;
6998 PyObject *(*getitem)(PyObject *, Py_ssize_t);
6999 Py_ssize_t lastarg = 0;
Guido van Rossuma1065681999-01-25 23:20:23 +00007000
Victor Stinner8c62be82010-05-06 00:08:46 +00007001 /* spawnve has four arguments: (mode, path, argv, env), where
7002 argv is a list or tuple of strings and env is a dictionary
7003 like posix.environ. */
Guido van Rossuma1065681999-01-25 23:20:23 +00007004
Larry Hastings2f936352014-08-05 14:04:04 +10007005 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00007006 if (PyList_Check(argv)) {
7007 argc = PyList_Size(argv);
7008 getitem = PyList_GetItem;
7009 }
7010 else if (PyTuple_Check(argv)) {
7011 argc = PyTuple_Size(argv);
7012 getitem = PyTuple_GetItem;
7013 }
7014 else {
7015 PyErr_SetString(PyExc_TypeError,
7016 "spawnve() arg 2 must be a tuple or list");
7017 goto fail_0;
7018 }
7019 if (!PyMapping_Check(env)) {
7020 PyErr_SetString(PyExc_TypeError,
7021 "spawnve() arg 3 must be a mapping object");
7022 goto fail_0;
7023 }
Guido van Rossuma1065681999-01-25 23:20:23 +00007024
Victor Stinner8c62be82010-05-06 00:08:46 +00007025 argvlist = PyMem_NEW(char *, argc+1);
7026 if (argvlist == NULL) {
7027 PyErr_NoMemory();
7028 goto fail_0;
7029 }
7030 for (i = 0; i < argc; i++) {
7031 if (!fsconvert_strdup((*getitem)(argv, i),
7032 &argvlist[i]))
7033 {
7034 lastarg = i;
7035 goto fail_1;
7036 }
7037 }
7038 lastarg = argc;
7039 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00007040
Victor Stinner8c62be82010-05-06 00:08:46 +00007041 envlist = parse_envlist(env, &envc);
7042 if (envlist == NULL)
7043 goto fail_1;
Guido van Rossuma1065681999-01-25 23:20:23 +00007044
Victor Stinner8c62be82010-05-06 00:08:46 +00007045 if (mode == _OLD_P_OVERLAY)
7046 mode = _P_OVERLAY;
Tim Peters25059d32001-12-07 20:35:43 +00007047
Victor Stinner8c62be82010-05-06 00:08:46 +00007048 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007049 spawnval = _spawnve(mode, path_char, argvlist, envlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00007050 Py_END_ALLOW_THREADS
Tim Peters25059d32001-12-07 20:35:43 +00007051
Victor Stinner8c62be82010-05-06 00:08:46 +00007052 if (spawnval == -1)
7053 (void) posix_error();
7054 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01007055 res = Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00007056
Victor Stinner8c62be82010-05-06 00:08:46 +00007057 while (--envc >= 0)
7058 PyMem_DEL(envlist[envc]);
7059 PyMem_DEL(envlist);
Guido van Rossum0847c5c2002-12-13 18:36:22 +00007060 fail_1:
Victor Stinner8c62be82010-05-06 00:08:46 +00007061 free_string_array(argvlist, lastarg);
Martin v. Löwis114619e2002-10-07 06:44:21 +00007062 fail_0:
Victor Stinner8c62be82010-05-06 00:08:46 +00007063 return res;
Guido van Rossuma1065681999-01-25 23:20:23 +00007064}
Andrew MacIntyre69e18c92004-04-04 07:11:43 +00007065
Guido van Rossuma1065681999-01-25 23:20:23 +00007066#endif /* HAVE_SPAWNV */
7067
7068
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007069#ifdef HAVE_FORK1
Larry Hastings2f936352014-08-05 14:04:04 +10007070/*[clinic input]
7071os.fork1
7072
7073Fork a child process with a single multiplexed (i.e., not bound) thread.
7074
7075Return 0 to child process and PID of child to parent process.
7076[clinic start generated code]*/
7077
7078PyDoc_STRVAR(os_fork1__doc__,
7079"fork1($module, /)\n"
7080"--\n"
7081"\n"
7082"Fork a child process with a single multiplexed (i.e., not bound) thread.\n"
7083"\n"
7084"Return 0 to child process and PID of child to parent process.");
7085
7086#define OS_FORK1_METHODDEF \
7087 {"fork1", (PyCFunction)os_fork1, METH_NOARGS, os_fork1__doc__},
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007088
7089static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007090os_fork1_impl(PyModuleDef *module);
7091
7092static PyObject *
7093os_fork1(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7094{
7095 return os_fork1_impl(module);
7096}
7097
7098static PyObject *
7099os_fork1_impl(PyModuleDef *module)
7100/*[clinic end generated code: output=fa04088d6bc02efa input=12db02167893926e]*/
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007101{
Victor Stinner8c62be82010-05-06 00:08:46 +00007102 pid_t pid;
7103 int result = 0;
7104 _PyImport_AcquireLock();
7105 pid = fork1();
7106 if (pid == 0) {
7107 /* child: this clobbers and resets the import lock. */
7108 PyOS_AfterFork();
7109 } else {
7110 /* parent: release the import lock. */
7111 result = _PyImport_ReleaseLock();
7112 }
7113 if (pid == -1)
7114 return posix_error();
7115 if (result < 0) {
7116 /* Don't clobber the OSError if the fork failed. */
7117 PyErr_SetString(PyExc_RuntimeError,
7118 "not holding the import lock");
7119 return NULL;
7120 }
7121 return PyLong_FromPid(pid);
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007122}
Larry Hastings2f936352014-08-05 14:04:04 +10007123#endif /* HAVE_FORK1 */
Guido van Rossum2242f2f2001-04-11 20:58:20 +00007124
7125
Guido van Rossumad0ee831995-03-01 10:34:45 +00007126#ifdef HAVE_FORK
Larry Hastings2f936352014-08-05 14:04:04 +10007127/*[clinic input]
7128os.fork
7129
7130Fork a child process.
7131
7132Return 0 to child process and PID of child to parent process.
7133[clinic start generated code]*/
7134
7135PyDoc_STRVAR(os_fork__doc__,
7136"fork($module, /)\n"
7137"--\n"
7138"\n"
7139"Fork a child process.\n"
7140"\n"
7141"Return 0 to child process and PID of child to parent process.");
7142
7143#define OS_FORK_METHODDEF \
7144 {"fork", (PyCFunction)os_fork, METH_NOARGS, os_fork__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007145
Barry Warsaw53699e91996-12-10 23:23:01 +00007146static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007147os_fork_impl(PyModuleDef *module);
7148
7149static PyObject *
7150os_fork(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7151{
7152 return os_fork_impl(module);
7153}
7154
7155static PyObject *
7156os_fork_impl(PyModuleDef *module)
7157/*[clinic end generated code: output=b3c8e6bdc11eedc6 input=13c956413110eeaa]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00007158{
Victor Stinner8c62be82010-05-06 00:08:46 +00007159 pid_t pid;
7160 int result = 0;
7161 _PyImport_AcquireLock();
7162 pid = fork();
7163 if (pid == 0) {
7164 /* child: this clobbers and resets the import lock. */
7165 PyOS_AfterFork();
7166 } else {
7167 /* parent: release the import lock. */
7168 result = _PyImport_ReleaseLock();
7169 }
7170 if (pid == -1)
7171 return posix_error();
7172 if (result < 0) {
7173 /* Don't clobber the OSError if the fork failed. */
7174 PyErr_SetString(PyExc_RuntimeError,
7175 "not holding the import lock");
7176 return NULL;
7177 }
7178 return PyLong_FromPid(pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00007179}
Larry Hastings2f936352014-08-05 14:04:04 +10007180#endif /* HAVE_FORK */
7181
Guido van Rossum85e3b011991-06-03 12:42:10 +00007182
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007183#ifdef HAVE_SCHED_H
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007184#ifdef HAVE_SCHED_GET_PRIORITY_MAX
Larry Hastings2f936352014-08-05 14:04:04 +10007185/*[clinic input]
7186os.sched_get_priority_max
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007187
Larry Hastings2f936352014-08-05 14:04:04 +10007188 policy: int
7189
7190Get the maximum scheduling priority for policy.
7191[clinic start generated code]*/
7192
7193PyDoc_STRVAR(os_sched_get_priority_max__doc__,
7194"sched_get_priority_max($module, /, policy)\n"
7195"--\n"
7196"\n"
7197"Get the maximum scheduling priority for policy.");
7198
7199#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF \
7200 {"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 -05007201
7202static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007203os_sched_get_priority_max_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007204
Larry Hastings2f936352014-08-05 14:04:04 +10007205static PyObject *
7206os_sched_get_priority_max(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7207{
7208 PyObject *return_value = NULL;
7209 static char *_keywords[] = {"policy", NULL};
7210 int policy;
7211
7212 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7213 "i:sched_get_priority_max", _keywords,
7214 &policy))
7215 goto exit;
7216 return_value = os_sched_get_priority_max_impl(module, policy);
7217
7218exit:
7219 return return_value;
7220}
7221
7222static PyObject *
7223os_sched_get_priority_max_impl(PyModuleDef *module, int policy)
7224/*[clinic end generated code: output=a580a52f25238c1f input=2097b7998eca6874]*/
7225{
7226 int max;
7227
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007228 max = sched_get_priority_max(policy);
7229 if (max < 0)
7230 return posix_error();
7231 return PyLong_FromLong(max);
7232}
7233
Larry Hastings2f936352014-08-05 14:04:04 +10007234
7235/*[clinic input]
7236os.sched_get_priority_min
7237
7238 policy: int
7239
7240Get the minimum scheduling priority for policy.
7241[clinic start generated code]*/
7242
7243PyDoc_STRVAR(os_sched_get_priority_min__doc__,
7244"sched_get_priority_min($module, /, policy)\n"
7245"--\n"
7246"\n"
7247"Get the minimum scheduling priority for policy.");
7248
7249#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF \
7250 {"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 -05007251
7252static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007253os_sched_get_priority_min_impl(PyModuleDef *module, int policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007254
Larry Hastings2f936352014-08-05 14:04:04 +10007255static PyObject *
7256os_sched_get_priority_min(PyModuleDef *module, PyObject *args, PyObject *kwargs)
7257{
7258 PyObject *return_value = NULL;
7259 static char *_keywords[] = {"policy", NULL};
7260 int policy;
7261
7262 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7263 "i:sched_get_priority_min", _keywords,
7264 &policy))
7265 goto exit;
7266 return_value = os_sched_get_priority_min_impl(module, policy);
7267
7268exit:
7269 return return_value;
7270}
7271
7272static PyObject *
7273os_sched_get_priority_min_impl(PyModuleDef *module, int policy)
7274/*[clinic end generated code: output=bad8ba10e7d0e977 input=21bc8fa0d70983bf]*/
7275{
7276 int min = sched_get_priority_min(policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007277 if (min < 0)
7278 return posix_error();
7279 return PyLong_FromLong(min);
7280}
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02007281#endif /* HAVE_SCHED_GET_PRIORITY_MAX */
7282
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007283
Larry Hastings2f936352014-08-05 14:04:04 +10007284#ifdef HAVE_SCHED_SETSCHEDULER
7285/*[clinic input]
7286os.sched_getscheduler
7287 pid: pid_t
7288 /
7289
7290Get the scheduling policy for the process identifiedy by pid.
7291
7292Passing 0 for pid returns the scheduling policy for the calling process.
7293[clinic start generated code]*/
7294
7295PyDoc_STRVAR(os_sched_getscheduler__doc__,
7296"sched_getscheduler($module, pid, /)\n"
7297"--\n"
7298"\n"
7299"Get the scheduling policy for the process identifiedy by pid.\n"
7300"\n"
7301"Passing 0 for pid returns the scheduling policy for the calling process.");
7302
7303#define OS_SCHED_GETSCHEDULER_METHODDEF \
7304 {"sched_getscheduler", (PyCFunction)os_sched_getscheduler, METH_VARARGS, os_sched_getscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007305
7306static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007307os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid);
7308
7309static PyObject *
7310os_sched_getscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007311{
Larry Hastings2f936352014-08-05 14:04:04 +10007312 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007313 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007314
7315 if (!PyArg_ParseTuple(args,
7316 "" _Py_PARSE_PID ":sched_getscheduler",
7317 &pid))
7318 goto exit;
7319 return_value = os_sched_getscheduler_impl(module, pid);
7320
7321exit:
7322 return return_value;
7323}
7324
7325static PyObject *
7326os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid)
7327/*[clinic end generated code: output=e0d6244207b1d828 input=5f14cfd1f189e1a0]*/
7328{
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007329 int policy;
7330
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007331 policy = sched_getscheduler(pid);
7332 if (policy < 0)
7333 return posix_error();
7334 return PyLong_FromLong(policy);
7335}
Larry Hastings2f936352014-08-05 14:04:04 +10007336#endif /* HAVE_SCHED_SETSCHEDULER */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007337
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007338
7339#if defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM)
Larry Hastings2f936352014-08-05 14:04:04 +10007340/*[clinic input]
7341class os.sched_param "PyObject *" "&SchedParamType"
7342
7343@classmethod
7344os.sched_param.__new__
7345
7346 sched_priority: object
7347 A scheduling parameter.
7348
7349Current has only one field: sched_priority");
7350[clinic start generated code]*/
7351
7352PyDoc_STRVAR(os_sched_param__doc__,
7353"sched_param(sched_priority)\n"
7354"--\n"
7355"\n"
7356"Current has only one field: sched_priority\");\n"
7357"\n"
7358" sched_priority\n"
7359" A scheduling parameter.");
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007360
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007361static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007362os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007363
Larry Hastings2f936352014-08-05 14:04:04 +10007364static PyObject *
7365os_sched_param(PyTypeObject *type, PyObject *args, PyObject *kwargs)
7366{
7367 PyObject *return_value = NULL;
7368 static char *_keywords[] = {"sched_priority", NULL};
7369 PyObject *sched_priority;
7370
7371 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
7372 "O:sched_param", _keywords,
7373 &sched_priority))
7374 goto exit;
7375 return_value = os_sched_param_impl(type, sched_priority);
7376
7377exit:
7378 return return_value;
7379}
7380
7381static PyObject *
7382os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority)
7383/*[clinic end generated code: output=d3791e345f7fe573 input=73a4c22f7071fc62]*/
7384{
7385 PyObject *res;
7386
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007387 res = PyStructSequence_New(type);
7388 if (!res)
7389 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10007390 Py_INCREF(sched_priority);
7391 PyStructSequence_SET_ITEM(res, 0, sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007392 return res;
7393}
7394
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007395
7396static PyStructSequence_Field sched_param_fields[] = {
7397 {"sched_priority", "the scheduling priority"},
7398 {0}
7399};
7400
7401static PyStructSequence_Desc sched_param_desc = {
7402 "sched_param", /* name */
Larry Hastings2f936352014-08-05 14:04:04 +10007403 os_sched_param__doc__, /* doc */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007404 sched_param_fields,
7405 1
7406};
7407
7408static int
7409convert_sched_param(PyObject *param, struct sched_param *res)
7410{
7411 long priority;
7412
7413 if (Py_TYPE(param) != &SchedParamType) {
7414 PyErr_SetString(PyExc_TypeError, "must have a sched_param object");
7415 return 0;
7416 }
7417 priority = PyLong_AsLong(PyStructSequence_GET_ITEM(param, 0));
7418 if (priority == -1 && PyErr_Occurred())
7419 return 0;
7420 if (priority > INT_MAX || priority < INT_MIN) {
7421 PyErr_SetString(PyExc_OverflowError, "sched_priority out of range");
7422 return 0;
7423 }
7424 res->sched_priority = Py_SAFE_DOWNCAST(priority, long, int);
7425 return 1;
7426}
Larry Hastings2f936352014-08-05 14:04:04 +10007427#endif /* defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM) */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007428
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007429
7430#ifdef HAVE_SCHED_SETSCHEDULER
Larry Hastings2f936352014-08-05 14:04:04 +10007431/*[clinic input]
7432os.sched_setscheduler
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007433
Larry Hastings2f936352014-08-05 14:04:04 +10007434 pid: pid_t
7435 policy: int
7436 param: sched_param
7437 /
7438
7439Set the scheduling policy for the process identified by pid.
7440
7441If pid is 0, the calling process is changed.
7442param is an instance of sched_param.
7443[clinic start generated code]*/
7444
7445PyDoc_STRVAR(os_sched_setscheduler__doc__,
7446"sched_setscheduler($module, pid, policy, param, /)\n"
7447"--\n"
7448"\n"
7449"Set the scheduling policy for the process identified by pid.\n"
7450"\n"
7451"If pid is 0, the calling process is changed.\n"
7452"param is an instance of sched_param.");
7453
7454#define OS_SCHED_SETSCHEDULER_METHODDEF \
7455 {"sched_setscheduler", (PyCFunction)os_sched_setscheduler, METH_VARARGS, os_sched_setscheduler__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007456
7457static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007458os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param);
7459
7460static PyObject *
7461os_sched_setscheduler(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007462{
Larry Hastings2f936352014-08-05 14:04:04 +10007463 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007464 pid_t pid;
7465 int policy;
7466 struct sched_param param;
7467
Larry Hastings2f936352014-08-05 14:04:04 +10007468 if (!PyArg_ParseTuple(args,
7469 "" _Py_PARSE_PID "iO&:sched_setscheduler",
7470 &pid, &policy, convert_sched_param, &param))
7471 goto exit;
7472 return_value = os_sched_setscheduler_impl(module, pid, policy, &param);
Jesus Cea9c822272011-09-10 01:40:52 +02007473
Larry Hastings2f936352014-08-05 14:04:04 +10007474exit:
7475 return return_value;
7476}
7477
7478static PyObject *
7479os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy, struct sched_param *param)
7480/*[clinic end generated code: output=36abdb73f81c224f input=c581f9469a5327dd]*/
7481{
Jesus Cea9c822272011-09-10 01:40:52 +02007482 /*
Jesus Cea54b01492011-09-10 01:53:19 +02007483 ** sched_setscheduler() returns 0 in Linux, but the previous
7484 ** scheduling policy under Solaris/Illumos, and others.
7485 ** On error, -1 is returned in all Operating Systems.
Jesus Cea9c822272011-09-10 01:40:52 +02007486 */
Larry Hastings2f936352014-08-05 14:04:04 +10007487 if (sched_setscheduler(pid, policy, param) == -1)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007488 return posix_error();
7489 Py_RETURN_NONE;
7490}
Larry Hastings2f936352014-08-05 14:04:04 +10007491#endif /* HAVE_SCHED_SETSCHEDULER*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007492
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007493
7494#ifdef HAVE_SCHED_SETPARAM
Larry Hastings2f936352014-08-05 14:04:04 +10007495/*[clinic input]
7496os.sched_getparam
7497 pid: pid_t
7498 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007499
Larry Hastings2f936352014-08-05 14:04:04 +10007500Returns scheduling parameters for the process identified by pid.
7501
7502If pid is 0, returns parameters for the calling process.
7503Return value is an instance of sched_param.
7504[clinic start generated code]*/
7505
7506PyDoc_STRVAR(os_sched_getparam__doc__,
7507"sched_getparam($module, pid, /)\n"
7508"--\n"
7509"\n"
7510"Returns scheduling parameters for the process identified by pid.\n"
7511"\n"
7512"If pid is 0, returns parameters for the calling process.\n"
7513"Return value is an instance of sched_param.");
7514
7515#define OS_SCHED_GETPARAM_METHODDEF \
7516 {"sched_getparam", (PyCFunction)os_sched_getparam, METH_VARARGS, os_sched_getparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007517
7518static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007519os_sched_getparam_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007520
Larry Hastings2f936352014-08-05 14:04:04 +10007521static PyObject *
7522os_sched_getparam(PyModuleDef *module, PyObject *args)
7523{
7524 PyObject *return_value = NULL;
7525 pid_t pid;
7526
7527 if (!PyArg_ParseTuple(args,
7528 "" _Py_PARSE_PID ":sched_getparam",
7529 &pid))
7530 goto exit;
7531 return_value = os_sched_getparam_impl(module, pid);
7532
7533exit:
7534 return return_value;
7535}
7536
7537static PyObject *
7538os_sched_getparam_impl(PyModuleDef *module, pid_t pid)
7539/*[clinic end generated code: output=b33acc8db004a8c9 input=18a1ef9c2efae296]*/
7540{
7541 struct sched_param param;
7542 PyObject *result;
7543 PyObject *priority;
7544
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007545 if (sched_getparam(pid, &param))
7546 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007547 result = PyStructSequence_New(&SchedParamType);
7548 if (!result)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007549 return NULL;
7550 priority = PyLong_FromLong(param.sched_priority);
7551 if (!priority) {
Larry Hastings2f936352014-08-05 14:04:04 +10007552 Py_DECREF(result);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007553 return NULL;
7554 }
Larry Hastings2f936352014-08-05 14:04:04 +10007555 PyStructSequence_SET_ITEM(result, 0, priority);
7556 return result;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007557}
7558
Larry Hastings2f936352014-08-05 14:04:04 +10007559
7560/*[clinic input]
7561os.sched_setparam
7562 pid: pid_t
7563 param: sched_param
7564 /
7565
7566Set scheduling parameters for the process identified by pid.
7567
7568If pid is 0, sets parameters for the calling process.
7569param should be an instance of sched_param.
7570[clinic start generated code]*/
7571
7572PyDoc_STRVAR(os_sched_setparam__doc__,
7573"sched_setparam($module, pid, param, /)\n"
7574"--\n"
7575"\n"
7576"Set scheduling parameters for the process identified by pid.\n"
7577"\n"
7578"If pid is 0, sets parameters for the calling process.\n"
7579"param should be an instance of sched_param.");
7580
7581#define OS_SCHED_SETPARAM_METHODDEF \
7582 {"sched_setparam", (PyCFunction)os_sched_setparam, METH_VARARGS, os_sched_setparam__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007583
7584static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007585os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param);
7586
7587static PyObject *
7588os_sched_setparam(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007589{
Larry Hastings2f936352014-08-05 14:04:04 +10007590 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007591 pid_t pid;
7592 struct sched_param param;
7593
Larry Hastings2f936352014-08-05 14:04:04 +10007594 if (!PyArg_ParseTuple(args,
7595 "" _Py_PARSE_PID "O&:sched_setparam",
7596 &pid, convert_sched_param, &param))
7597 goto exit;
7598 return_value = os_sched_setparam_impl(module, pid, &param);
7599
7600exit:
7601 return return_value;
7602}
7603
7604static PyObject *
7605os_sched_setparam_impl(PyModuleDef *module, pid_t pid, struct sched_param *param)
7606/*[clinic end generated code: output=488bdf5bcbe0d4e8 input=6b8d6dfcecdc21bd]*/
7607{
7608 if (sched_setparam(pid, param))
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007609 return posix_error();
7610 Py_RETURN_NONE;
7611}
Larry Hastings2f936352014-08-05 14:04:04 +10007612#endif /* HAVE_SCHED_SETPARAM */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007613
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007614
7615#ifdef HAVE_SCHED_RR_GET_INTERVAL
Larry Hastings2f936352014-08-05 14:04:04 +10007616/*[clinic input]
7617os.sched_rr_get_interval -> double
7618 pid: pid_t
7619 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007620
Larry Hastings2f936352014-08-05 14:04:04 +10007621Return the round-robin quantum for the process identified by pid, in seconds.
7622
7623Value returned is a float.
7624[clinic start generated code]*/
7625
7626PyDoc_STRVAR(os_sched_rr_get_interval__doc__,
7627"sched_rr_get_interval($module, pid, /)\n"
7628"--\n"
7629"\n"
7630"Return the round-robin quantum for the process identified by pid, in seconds.\n"
7631"\n"
7632"Value returned is a float.");
7633
7634#define OS_SCHED_RR_GET_INTERVAL_METHODDEF \
7635 {"sched_rr_get_interval", (PyCFunction)os_sched_rr_get_interval, METH_VARARGS, os_sched_rr_get_interval__doc__},
7636
7637static double
7638os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007639
7640static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007641os_sched_rr_get_interval(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007642{
Larry Hastings2f936352014-08-05 14:04:04 +10007643 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007644 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007645 double _return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007646
Larry Hastings2f936352014-08-05 14:04:04 +10007647 if (!PyArg_ParseTuple(args,
7648 "" _Py_PARSE_PID ":sched_rr_get_interval",
7649 &pid))
7650 goto exit;
7651 _return_value = os_sched_rr_get_interval_impl(module, pid);
7652 if ((_return_value == -1.0) && PyErr_Occurred())
7653 goto exit;
7654 return_value = PyFloat_FromDouble(_return_value);
7655
7656exit:
7657 return return_value;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007658}
7659
Larry Hastings2f936352014-08-05 14:04:04 +10007660static double
7661os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid)
7662/*[clinic end generated code: output=5b3b8d1f27fb2c0a input=2a973da15cca6fae]*/
7663{
7664 struct timespec interval;
7665 if (sched_rr_get_interval(pid, &interval)) {
7666 posix_error();
7667 return -1.0;
7668 }
7669 return (double)interval.tv_sec + 1e-9*interval.tv_nsec;
7670}
7671#endif /* HAVE_SCHED_RR_GET_INTERVAL */
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05007672
Larry Hastings2f936352014-08-05 14:04:04 +10007673
7674/*[clinic input]
7675os.sched_yield
7676
7677Voluntarily relinquish the CPU.
7678[clinic start generated code]*/
7679
7680PyDoc_STRVAR(os_sched_yield__doc__,
7681"sched_yield($module, /)\n"
7682"--\n"
7683"\n"
7684"Voluntarily relinquish the CPU.");
7685
7686#define OS_SCHED_YIELD_METHODDEF \
7687 {"sched_yield", (PyCFunction)os_sched_yield, METH_NOARGS, os_sched_yield__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007688
7689static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007690os_sched_yield_impl(PyModuleDef *module);
7691
7692static PyObject *
7693os_sched_yield(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
7694{
7695 return os_sched_yield_impl(module);
7696}
7697
7698static PyObject *
7699os_sched_yield_impl(PyModuleDef *module)
7700/*[clinic end generated code: output=9d2e5f29f1370324 input=e54d6f98189391d4]*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007701{
7702 if (sched_yield())
7703 return posix_error();
7704 Py_RETURN_NONE;
7705}
7706
Benjamin Peterson2740af82011-08-02 17:41:34 -05007707#ifdef HAVE_SCHED_SETAFFINITY
Antoine Pitrou84869872012-08-04 16:16:35 +02007708/* The minimum number of CPUs allocated in a cpu_set_t */
7709static const int NCPUS_START = sizeof(unsigned long) * CHAR_BIT;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007710
Larry Hastings2f936352014-08-05 14:04:04 +10007711/*[clinic input]
7712os.sched_setaffinity
7713 pid: pid_t
7714 mask : object
7715 /
7716
7717Set the CPU affinity of the process identified by pid to mask.
7718
7719mask should be an iterable of integers identifying CPUs.
7720[clinic start generated code]*/
7721
7722PyDoc_STRVAR(os_sched_setaffinity__doc__,
7723"sched_setaffinity($module, pid, mask, /)\n"
7724"--\n"
7725"\n"
7726"Set the CPU affinity of the process identified by pid to mask.\n"
7727"\n"
7728"mask should be an iterable of integers identifying CPUs.");
7729
7730#define OS_SCHED_SETAFFINITY_METHODDEF \
7731 {"sched_setaffinity", (PyCFunction)os_sched_setaffinity, METH_VARARGS, os_sched_setaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007732
7733static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007734os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask);
7735
7736static PyObject *
7737os_sched_setaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007738{
Larry Hastings2f936352014-08-05 14:04:04 +10007739 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007740 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007741 PyObject *mask;
7742
7743 if (!PyArg_ParseTuple(args,
7744 "" _Py_PARSE_PID "O:sched_setaffinity",
7745 &pid, &mask))
7746 goto exit;
7747 return_value = os_sched_setaffinity_impl(module, pid, mask);
7748
7749exit:
7750 return return_value;
7751}
7752
7753static PyObject *
7754os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask)
7755/*[clinic end generated code: output=5199929738130196 input=a0791a597c7085ba]*/
7756{
Antoine Pitrou84869872012-08-04 16:16:35 +02007757 int ncpus;
7758 size_t setsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007759 cpu_set_t *cpu_set = NULL;
7760 PyObject *iterator = NULL, *item;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007761
Larry Hastings2f936352014-08-05 14:04:04 +10007762 iterator = PyObject_GetIter(mask);
Antoine Pitrou84869872012-08-04 16:16:35 +02007763 if (iterator == NULL)
7764 return NULL;
7765
7766 ncpus = NCPUS_START;
7767 setsize = CPU_ALLOC_SIZE(ncpus);
Larry Hastings2f936352014-08-05 14:04:04 +10007768 cpu_set = CPU_ALLOC(ncpus);
7769 if (cpu_set == NULL) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007770 PyErr_NoMemory();
7771 goto error;
7772 }
Larry Hastings2f936352014-08-05 14:04:04 +10007773 CPU_ZERO_S(setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007774
7775 while ((item = PyIter_Next(iterator))) {
7776 long cpu;
7777 if (!PyLong_Check(item)) {
7778 PyErr_Format(PyExc_TypeError,
7779 "expected an iterator of ints, "
7780 "but iterator yielded %R",
7781 Py_TYPE(item));
7782 Py_DECREF(item);
7783 goto error;
7784 }
7785 cpu = PyLong_AsLong(item);
7786 Py_DECREF(item);
7787 if (cpu < 0) {
7788 if (!PyErr_Occurred())
7789 PyErr_SetString(PyExc_ValueError, "negative CPU number");
7790 goto error;
7791 }
7792 if (cpu > INT_MAX - 1) {
7793 PyErr_SetString(PyExc_OverflowError, "CPU number too large");
7794 goto error;
7795 }
7796 if (cpu >= ncpus) {
7797 /* Grow CPU mask to fit the CPU number */
7798 int newncpus = ncpus;
7799 cpu_set_t *newmask;
7800 size_t newsetsize;
7801 while (newncpus <= cpu) {
7802 if (newncpus > INT_MAX / 2)
7803 newncpus = cpu + 1;
7804 else
7805 newncpus = newncpus * 2;
7806 }
7807 newmask = CPU_ALLOC(newncpus);
7808 if (newmask == NULL) {
7809 PyErr_NoMemory();
7810 goto error;
7811 }
7812 newsetsize = CPU_ALLOC_SIZE(newncpus);
7813 CPU_ZERO_S(newsetsize, newmask);
Larry Hastings2f936352014-08-05 14:04:04 +10007814 memcpy(newmask, cpu_set, setsize);
7815 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007816 setsize = newsetsize;
Larry Hastings2f936352014-08-05 14:04:04 +10007817 cpu_set = newmask;
Antoine Pitrou84869872012-08-04 16:16:35 +02007818 ncpus = newncpus;
7819 }
Larry Hastings2f936352014-08-05 14:04:04 +10007820 CPU_SET_S(cpu, setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007821 }
7822 Py_CLEAR(iterator);
7823
Larry Hastings2f936352014-08-05 14:04:04 +10007824 if (sched_setaffinity(pid, setsize, cpu_set)) {
Antoine Pitrou84869872012-08-04 16:16:35 +02007825 posix_error();
7826 goto error;
7827 }
Larry Hastings2f936352014-08-05 14:04:04 +10007828 CPU_FREE(cpu_set);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007829 Py_RETURN_NONE;
Antoine Pitrou84869872012-08-04 16:16:35 +02007830
7831error:
Larry Hastings2f936352014-08-05 14:04:04 +10007832 if (cpu_set)
7833 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02007834 Py_XDECREF(iterator);
7835 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007836}
7837
Larry Hastings2f936352014-08-05 14:04:04 +10007838
7839/*[clinic input]
7840os.sched_getaffinity
7841 pid: pid_t
7842 /
7843
7844Return the affinity of the process identified by pid.
7845
7846The affinity is returned as a set of CPU identifiers.
7847[clinic start generated code]*/
7848
7849PyDoc_STRVAR(os_sched_getaffinity__doc__,
7850"sched_getaffinity($module, pid, /)\n"
7851"--\n"
7852"\n"
7853"Return the affinity of the process identified by pid.\n"
7854"\n"
7855"The affinity is returned as a set of CPU identifiers.");
7856
7857#define OS_SCHED_GETAFFINITY_METHODDEF \
7858 {"sched_getaffinity", (PyCFunction)os_sched_getaffinity, METH_VARARGS, os_sched_getaffinity__doc__},
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007859
7860static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007861os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid);
7862
7863static PyObject *
7864os_sched_getaffinity(PyModuleDef *module, PyObject *args)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007865{
Larry Hastings2f936352014-08-05 14:04:04 +10007866 PyObject *return_value = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007867 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +10007868
7869 if (!PyArg_ParseTuple(args,
7870 "" _Py_PARSE_PID ":sched_getaffinity",
7871 &pid))
7872 goto exit;
7873 return_value = os_sched_getaffinity_impl(module, pid);
7874
7875exit:
7876 return return_value;
7877}
7878
7879static PyObject *
7880os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid)
7881/*[clinic end generated code: output=7b273b0fca9830f0 input=eaf161936874b8a1]*/
7882{
Antoine Pitrou84869872012-08-04 16:16:35 +02007883 int cpu, ncpus, count;
7884 size_t setsize;
7885 cpu_set_t *mask = NULL;
7886 PyObject *res = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007887
Antoine Pitrou84869872012-08-04 16:16:35 +02007888 ncpus = NCPUS_START;
7889 while (1) {
7890 setsize = CPU_ALLOC_SIZE(ncpus);
7891 mask = CPU_ALLOC(ncpus);
7892 if (mask == NULL)
7893 return PyErr_NoMemory();
7894 if (sched_getaffinity(pid, setsize, mask) == 0)
7895 break;
7896 CPU_FREE(mask);
7897 if (errno != EINVAL)
7898 return posix_error();
7899 if (ncpus > INT_MAX / 2) {
7900 PyErr_SetString(PyExc_OverflowError, "could not allocate "
7901 "a large enough CPU set");
7902 return NULL;
7903 }
7904 ncpus = ncpus * 2;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007905 }
Antoine Pitrou84869872012-08-04 16:16:35 +02007906
7907 res = PySet_New(NULL);
7908 if (res == NULL)
7909 goto error;
7910 for (cpu = 0, count = CPU_COUNT_S(setsize, mask); count; cpu++) {
7911 if (CPU_ISSET_S(cpu, setsize, mask)) {
7912 PyObject *cpu_num = PyLong_FromLong(cpu);
7913 --count;
7914 if (cpu_num == NULL)
7915 goto error;
7916 if (PySet_Add(res, cpu_num)) {
7917 Py_DECREF(cpu_num);
7918 goto error;
7919 }
7920 Py_DECREF(cpu_num);
7921 }
7922 }
7923 CPU_FREE(mask);
7924 return res;
7925
7926error:
7927 if (mask)
7928 CPU_FREE(mask);
7929 Py_XDECREF(res);
7930 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007931}
7932
Benjamin Peterson2740af82011-08-02 17:41:34 -05007933#endif /* HAVE_SCHED_SETAFFINITY */
7934
Benjamin Peterson94b580d2011-08-02 17:30:04 -05007935#endif /* HAVE_SCHED_H */
7936
Larry Hastings2f936352014-08-05 14:04:04 +10007937#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7938#define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
7939#endif /* OS_SCHED_GET_PRIORITY_MAX_METHODDEF */
7940
7941#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7942#define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
7943#endif /* OS_SCHED_GET_PRIORITY_MIN_METHODDEF */
7944
7945#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
7946#define OS_SCHED_GETSCHEDULER_METHODDEF
7947#endif /* OS_SCHED_GETSCHEDULER_METHODDEF */
7948
7949#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
7950#define OS_SCHED_SETSCHEDULER_METHODDEF
7951#endif /* OS_SCHED_SETSCHEDULER_METHODDEF */
7952
7953#ifndef OS_SCHED_GETPARAM_METHODDEF
7954#define OS_SCHED_GETPARAM_METHODDEF
7955#endif /* OS_SCHED_GETPARAM_METHODDEF */
7956
7957#ifndef OS_SCHED_SETPARAM_METHODDEF
7958#define OS_SCHED_SETPARAM_METHODDEF
7959#endif /* OS_SCHED_SETPARAM_METHODDEF */
7960
7961#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
7962#define OS_SCHED_RR_GET_INTERVAL_METHODDEF
7963#endif /* OS_SCHED_RR_GET_INTERVAL_METHODDEF */
7964
7965#ifndef OS_SCHED_YIELD_METHODDEF
7966#define OS_SCHED_YIELD_METHODDEF
7967#endif /* OS_SCHED_YIELD_METHODDEF */
7968
7969#ifndef OS_SCHED_SETAFFINITY_METHODDEF
7970#define OS_SCHED_SETAFFINITY_METHODDEF
7971#endif /* OS_SCHED_SETAFFINITY_METHODDEF */
7972
7973#ifndef OS_SCHED_GETAFFINITY_METHODDEF
7974#define OS_SCHED_GETAFFINITY_METHODDEF
7975#endif /* OS_SCHED_GETAFFINITY_METHODDEF */
7976
7977
Neal Norwitzb59798b2003-03-21 01:43:31 +00007978/* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
Neal Norwitz2deaddb2003-03-21 03:08:31 +00007979/* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
7980#if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
Neal Norwitzb59798b2003-03-21 01:43:31 +00007981#define DEV_PTY_FILE "/dev/ptc"
7982#define HAVE_DEV_PTMX
7983#else
7984#define DEV_PTY_FILE "/dev/ptmx"
7985#endif
7986
Martin v. Löwis24a880b2002-12-31 12:55:15 +00007987#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
Fred Drake8cef4cf2000-06-28 16:40:38 +00007988#ifdef HAVE_PTY_H
7989#include <pty.h>
7990#else
7991#ifdef HAVE_LIBUTIL_H
7992#include <libutil.h>
Ronald Oussoren755740f2010-02-07 19:56:39 +00007993#else
7994#ifdef HAVE_UTIL_H
7995#include <util.h>
7996#endif /* HAVE_UTIL_H */
Fred Drake8cef4cf2000-06-28 16:40:38 +00007997#endif /* HAVE_LIBUTIL_H */
7998#endif /* HAVE_PTY_H */
Martin v. Löwis14e73b12003-01-01 09:51:12 +00007999#ifdef HAVE_STROPTS_H
8000#include <stropts.h>
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008001#endif
8002#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008003
Larry Hastings2f936352014-08-05 14:04:04 +10008004
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008005#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
Larry Hastings2f936352014-08-05 14:04:04 +10008006/*[clinic input]
8007os.openpty
8008
8009Open a pseudo-terminal.
8010
8011Return a tuple of (master_fd, slave_fd) containing open file descriptors
8012for both the master and slave ends.
8013[clinic start generated code]*/
8014
8015PyDoc_STRVAR(os_openpty__doc__,
8016"openpty($module, /)\n"
8017"--\n"
8018"\n"
8019"Open a pseudo-terminal.\n"
8020"\n"
8021"Return a tuple of (master_fd, slave_fd) containing open file descriptors\n"
8022"for both the master and slave ends.");
8023
8024#define OS_OPENPTY_METHODDEF \
8025 {"openpty", (PyCFunction)os_openpty, METH_NOARGS, os_openpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008026
8027static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008028os_openpty_impl(PyModuleDef *module);
8029
8030static PyObject *
8031os_openpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8032{
8033 return os_openpty_impl(module);
8034}
8035
8036static PyObject *
8037os_openpty_impl(PyModuleDef *module)
8038/*[clinic end generated code: output=b12d3c1735468464 input=f3d99fd99e762907]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008039{
Victor Stinnerdaf45552013-08-28 00:53:59 +02008040 int master_fd = -1, slave_fd = -1;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008041#ifndef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008042 char * slave_name;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008043#endif
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008044#if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008045 PyOS_sighandler_t sig_saved;
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008046#ifdef sun
Victor Stinner8c62be82010-05-06 00:08:46 +00008047 extern char *ptsname(int fildes);
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008048#endif
8049#endif
Thomas Wouters70c21a12000-07-14 14:28:33 +00008050
Thomas Wouters70c21a12000-07-14 14:28:33 +00008051#ifdef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00008052 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008053 goto posix_error;
8054
8055 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8056 goto error;
8057 if (_Py_set_inheritable(slave_fd, 0, NULL) < 0)
8058 goto error;
8059
Neal Norwitzb59798b2003-03-21 01:43:31 +00008060#elif defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00008061 slave_name = _getpty(&master_fd, O_RDWR, 0666, 0);
8062 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008063 goto posix_error;
8064 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8065 goto error;
Thomas Wouters70c21a12000-07-14 14:28:33 +00008066
Victor Stinnerdaf45552013-08-28 00:53:59 +02008067 slave_fd = _Py_open(slave_name, O_RDWR);
Victor Stinner8c62be82010-05-06 00:08:46 +00008068 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008069 goto posix_error;
8070
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008071#else
Victor Stinner000de532013-11-25 23:19:58 +01008072 master_fd = open(DEV_PTY_FILE, O_RDWR | O_NOCTTY); /* open master */
Victor Stinner8c62be82010-05-06 00:08:46 +00008073 if (master_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008074 goto posix_error;
8075
Victor Stinner8c62be82010-05-06 00:08:46 +00008076 sig_saved = PyOS_setsig(SIGCHLD, SIG_DFL);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008077
Victor Stinner8c62be82010-05-06 00:08:46 +00008078 /* change permission of slave */
8079 if (grantpt(master_fd) < 0) {
8080 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008081 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008082 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008083
Victor Stinner8c62be82010-05-06 00:08:46 +00008084 /* unlock slave */
8085 if (unlockpt(master_fd) < 0) {
8086 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008087 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00008088 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02008089
Victor Stinner8c62be82010-05-06 00:08:46 +00008090 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008091
Victor Stinner8c62be82010-05-06 00:08:46 +00008092 slave_name = ptsname(master_fd); /* get name of slave */
8093 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008094 goto posix_error;
8095
8096 slave_fd = _Py_open(slave_name, O_RDWR | O_NOCTTY); /* open slave */
Victor Stinner8c62be82010-05-06 00:08:46 +00008097 if (slave_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008098 goto posix_error;
Victor Stinner000de532013-11-25 23:19:58 +01008099
8100 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
8101 goto posix_error;
8102
Neal Norwitzb59798b2003-03-21 01:43:31 +00008103#if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
Victor Stinner8c62be82010-05-06 00:08:46 +00008104 ioctl(slave_fd, I_PUSH, "ptem"); /* push ptem */
8105 ioctl(slave_fd, I_PUSH, "ldterm"); /* push ldterm */
Neal Norwitz6700e472002-12-31 16:16:07 +00008106#ifndef __hpux
Victor Stinner8c62be82010-05-06 00:08:46 +00008107 ioctl(slave_fd, I_PUSH, "ttcompat"); /* push ttcompat */
Neal Norwitz6700e472002-12-31 16:16:07 +00008108#endif /* __hpux */
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008109#endif /* HAVE_CYGWIN */
Thomas Wouters1e0c2f42000-07-24 16:06:23 +00008110#endif /* HAVE_OPENPTY */
Thomas Wouters70c21a12000-07-14 14:28:33 +00008111
Victor Stinner8c62be82010-05-06 00:08:46 +00008112 return Py_BuildValue("(ii)", master_fd, slave_fd);
Thomas Wouters70c21a12000-07-14 14:28:33 +00008113
Victor Stinnerdaf45552013-08-28 00:53:59 +02008114posix_error:
8115 posix_error();
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008116#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY)
Victor Stinnerdaf45552013-08-28 00:53:59 +02008117error:
Victor Stinnerb9981ba2013-08-28 01:51:06 +02008118#endif
Victor Stinnerdaf45552013-08-28 00:53:59 +02008119 if (master_fd != -1)
8120 close(master_fd);
8121 if (slave_fd != -1)
8122 close(slave_fd);
8123 return NULL;
Fred Drake8cef4cf2000-06-28 16:40:38 +00008124}
Martin v. Löwis24a880b2002-12-31 12:55:15 +00008125#endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
Fred Drake8cef4cf2000-06-28 16:40:38 +00008126
Larry Hastings2f936352014-08-05 14:04:04 +10008127
Fred Drake8cef4cf2000-06-28 16:40:38 +00008128#ifdef HAVE_FORKPTY
Larry Hastings2f936352014-08-05 14:04:04 +10008129/*[clinic input]
8130os.forkpty
8131
8132Fork a new process with a new pseudo-terminal as controlling tty.
8133
8134Returns a tuple of (pid, master_fd).
8135Like fork(), return pid of 0 to the child process,
8136and pid of child to the parent process.
8137To both, return fd of newly opened pseudo-terminal.
8138[clinic start generated code]*/
8139
8140PyDoc_STRVAR(os_forkpty__doc__,
8141"forkpty($module, /)\n"
8142"--\n"
8143"\n"
8144"Fork a new process with a new pseudo-terminal as controlling tty.\n"
8145"\n"
8146"Returns a tuple of (pid, master_fd).\n"
8147"Like fork(), return pid of 0 to the child process,\n"
8148"and pid of child to the parent process.\n"
8149"To both, return fd of newly opened pseudo-terminal.");
8150
8151#define OS_FORKPTY_METHODDEF \
8152 {"forkpty", (PyCFunction)os_forkpty, METH_NOARGS, os_forkpty__doc__},
Fred Drake8cef4cf2000-06-28 16:40:38 +00008153
8154static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008155os_forkpty_impl(PyModuleDef *module);
8156
8157static PyObject *
8158os_forkpty(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8159{
8160 return os_forkpty_impl(module);
8161}
8162
8163static PyObject *
8164os_forkpty_impl(PyModuleDef *module)
8165/*[clinic end generated code: output=d4f82958d2ed5cad input=f1f7f4bae3966010]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00008166{
Victor Stinner8c62be82010-05-06 00:08:46 +00008167 int master_fd = -1, result = 0;
8168 pid_t pid;
Tim Peters5aa91602002-01-30 05:46:57 +00008169
Victor Stinner8c62be82010-05-06 00:08:46 +00008170 _PyImport_AcquireLock();
8171 pid = forkpty(&master_fd, NULL, NULL, NULL);
8172 if (pid == 0) {
8173 /* child: this clobbers and resets the import lock. */
8174 PyOS_AfterFork();
8175 } else {
8176 /* parent: release the import lock. */
8177 result = _PyImport_ReleaseLock();
8178 }
8179 if (pid == -1)
8180 return posix_error();
8181 if (result < 0) {
8182 /* Don't clobber the OSError if the fork failed. */
8183 PyErr_SetString(PyExc_RuntimeError,
8184 "not holding the import lock");
8185 return NULL;
8186 }
8187 return Py_BuildValue("(Ni)", PyLong_FromPid(pid), master_fd);
Fred Drake8cef4cf2000-06-28 16:40:38 +00008188}
Larry Hastings2f936352014-08-05 14:04:04 +10008189#endif /* HAVE_FORKPTY */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008190
Ross Lagerwall7807c352011-03-17 20:20:30 +02008191
Guido van Rossumad0ee831995-03-01 10:34:45 +00008192#ifdef HAVE_GETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10008193/*[clinic input]
8194os.getegid
8195
8196Return the current process's effective group id.
8197[clinic start generated code]*/
8198
8199PyDoc_STRVAR(os_getegid__doc__,
8200"getegid($module, /)\n"
8201"--\n"
8202"\n"
8203"Return the current process\'s effective group id.");
8204
8205#define OS_GETEGID_METHODDEF \
8206 {"getegid", (PyCFunction)os_getegid, METH_NOARGS, os_getegid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008207
Barry Warsaw53699e91996-12-10 23:23:01 +00008208static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008209os_getegid_impl(PyModuleDef *module);
8210
8211static PyObject *
8212os_getegid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8213{
8214 return os_getegid_impl(module);
8215}
8216
8217static PyObject *
8218os_getegid_impl(PyModuleDef *module)
8219/*[clinic end generated code: output=fd12c346fa41cccb input=1596f79ad1107d5d]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008220{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008221 return _PyLong_FromGid(getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008222}
Larry Hastings2f936352014-08-05 14:04:04 +10008223#endif /* HAVE_GETEGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008224
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008225
Guido van Rossumad0ee831995-03-01 10:34:45 +00008226#ifdef HAVE_GETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10008227/*[clinic input]
8228os.geteuid
8229
8230Return the current process's effective user id.
8231[clinic start generated code]*/
8232
8233PyDoc_STRVAR(os_geteuid__doc__,
8234"geteuid($module, /)\n"
8235"--\n"
8236"\n"
8237"Return the current process\'s effective user id.");
8238
8239#define OS_GETEUID_METHODDEF \
8240 {"geteuid", (PyCFunction)os_geteuid, METH_NOARGS, os_geteuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008241
Barry Warsaw53699e91996-12-10 23:23:01 +00008242static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008243os_geteuid_impl(PyModuleDef *module);
8244
8245static PyObject *
8246os_geteuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8247{
8248 return os_geteuid_impl(module);
8249}
8250
8251static PyObject *
8252os_geteuid_impl(PyModuleDef *module)
8253/*[clinic end generated code: output=03d98e07f4bc03d4 input=4644c662d3bd9f19]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008254{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008255 return _PyLong_FromUid(geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008256}
Larry Hastings2f936352014-08-05 14:04:04 +10008257#endif /* HAVE_GETEUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008258
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008259
Guido van Rossumad0ee831995-03-01 10:34:45 +00008260#ifdef HAVE_GETGID
Larry Hastings2f936352014-08-05 14:04:04 +10008261/*[clinic input]
8262os.getgid
8263
8264Return the current process's group id.
8265[clinic start generated code]*/
8266
8267PyDoc_STRVAR(os_getgid__doc__,
8268"getgid($module, /)\n"
8269"--\n"
8270"\n"
8271"Return the current process\'s group id.");
8272
8273#define OS_GETGID_METHODDEF \
8274 {"getgid", (PyCFunction)os_getgid, METH_NOARGS, os_getgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008275
Barry Warsaw53699e91996-12-10 23:23:01 +00008276static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008277os_getgid_impl(PyModuleDef *module);
8278
8279static PyObject *
8280os_getgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8281{
8282 return os_getgid_impl(module);
8283}
8284
8285static PyObject *
8286os_getgid_impl(PyModuleDef *module)
8287/*[clinic end generated code: output=07b0356121b8098d input=58796344cd87c0f6]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008288{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008289 return _PyLong_FromGid(getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008290}
Larry Hastings2f936352014-08-05 14:04:04 +10008291#endif /* HAVE_GETGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008292
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008293
Larry Hastings2f936352014-08-05 14:04:04 +10008294/*[clinic input]
8295os.getpid
8296
8297Return the current process id.
8298[clinic start generated code]*/
8299
8300PyDoc_STRVAR(os_getpid__doc__,
8301"getpid($module, /)\n"
8302"--\n"
8303"\n"
8304"Return the current process id.");
8305
8306#define OS_GETPID_METHODDEF \
8307 {"getpid", (PyCFunction)os_getpid, METH_NOARGS, os_getpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008308
Barry Warsaw53699e91996-12-10 23:23:01 +00008309static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008310os_getpid_impl(PyModuleDef *module);
8311
8312static PyObject *
8313os_getpid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8314{
8315 return os_getpid_impl(module);
8316}
8317
8318static PyObject *
8319os_getpid_impl(PyModuleDef *module)
8320/*[clinic end generated code: output=d63a01a3cebc573d input=5a9a00f0ab68aa00]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008321{
Victor Stinner8c62be82010-05-06 00:08:46 +00008322 return PyLong_FromPid(getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00008323}
8324
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008325#ifdef HAVE_GETGROUPLIST
Larry Hastings2f936352014-08-05 14:04:04 +10008326
8327/* AC 3.5: funny apple logic below */
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008328PyDoc_STRVAR(posix_getgrouplist__doc__,
8329"getgrouplist(user, group) -> list of groups to which a user belongs\n\n\
8330Returns a list of groups to which a user belongs.\n\n\
8331 user: username to lookup\n\
8332 group: base group id of the user");
8333
8334static PyObject *
8335posix_getgrouplist(PyObject *self, PyObject *args)
8336{
8337#ifdef NGROUPS_MAX
8338#define MAX_GROUPS NGROUPS_MAX
8339#else
8340 /* defined to be 16 on Solaris7, so this should be a small number */
8341#define MAX_GROUPS 64
8342#endif
8343
8344 const char *user;
8345 int i, ngroups;
8346 PyObject *list;
8347#ifdef __APPLE__
8348 int *groups, basegid;
8349#else
8350 gid_t *groups, basegid;
8351#endif
8352 ngroups = MAX_GROUPS;
8353
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008354#ifdef __APPLE__
8355 if (!PyArg_ParseTuple(args, "si:getgrouplist", &user, &basegid))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008356 return NULL;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008357#else
8358 if (!PyArg_ParseTuple(args, "sO&:getgrouplist", &user,
8359 _Py_Gid_Converter, &basegid))
8360 return NULL;
8361#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008362
8363#ifdef __APPLE__
8364 groups = PyMem_Malloc(ngroups * sizeof(int));
8365#else
8366 groups = PyMem_Malloc(ngroups * sizeof(gid_t));
8367#endif
8368 if (groups == NULL)
8369 return PyErr_NoMemory();
8370
8371 if (getgrouplist(user, basegid, groups, &ngroups) == -1) {
8372 PyMem_Del(groups);
8373 return posix_error();
8374 }
8375
8376 list = PyList_New(ngroups);
8377 if (list == NULL) {
8378 PyMem_Del(groups);
8379 return NULL;
8380 }
8381
8382 for (i = 0; i < ngroups; i++) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008383#ifdef __APPLE__
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008384 PyObject *o = PyLong_FromUnsignedLong((unsigned long)groups[i]);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008385#else
8386 PyObject *o = _PyLong_FromGid(groups[i]);
8387#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02008388 if (o == NULL) {
8389 Py_DECREF(list);
8390 PyMem_Del(groups);
8391 return NULL;
8392 }
8393 PyList_SET_ITEM(list, i, o);
8394 }
8395
8396 PyMem_Del(groups);
8397
8398 return list;
8399}
Larry Hastings2f936352014-08-05 14:04:04 +10008400#endif /* HAVE_GETGROUPLIST */
8401
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008402
Fred Drakec9680921999-12-13 16:37:25 +00008403#ifdef HAVE_GETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10008404/*[clinic input]
8405os.getgroups
8406
8407Return list of supplemental group IDs for the process.
8408[clinic start generated code]*/
8409
8410PyDoc_STRVAR(os_getgroups__doc__,
8411"getgroups($module, /)\n"
8412"--\n"
8413"\n"
8414"Return list of supplemental group IDs for the process.");
8415
8416#define OS_GETGROUPS_METHODDEF \
8417 {"getgroups", (PyCFunction)os_getgroups, METH_NOARGS, os_getgroups__doc__},
Fred Drakec9680921999-12-13 16:37:25 +00008418
8419static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008420os_getgroups_impl(PyModuleDef *module);
8421
8422static PyObject *
8423os_getgroups(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8424{
8425 return os_getgroups_impl(module);
8426}
8427
8428static PyObject *
8429os_getgroups_impl(PyModuleDef *module)
8430/*[clinic end generated code: output=d9a3559b2e6f4ab8 input=d3f109412e6a155c]*/
Fred Drakec9680921999-12-13 16:37:25 +00008431{
8432 PyObject *result = NULL;
8433
Fred Drakec9680921999-12-13 16:37:25 +00008434#ifdef NGROUPS_MAX
8435#define MAX_GROUPS NGROUPS_MAX
8436#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008437 /* defined to be 16 on Solaris7, so this should be a small number */
Fred Drakec9680921999-12-13 16:37:25 +00008438#define MAX_GROUPS 64
8439#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008440 gid_t grouplist[MAX_GROUPS];
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008441
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008442 /* On MacOSX getgroups(2) can return more than MAX_GROUPS results
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008443 * This is a helper variable to store the intermediate result when
8444 * that happens.
8445 *
8446 * To keep the code readable the OSX behaviour is unconditional,
8447 * according to the POSIX spec this should be safe on all unix-y
8448 * systems.
8449 */
8450 gid_t* alt_grouplist = grouplist;
Victor Stinner8c62be82010-05-06 00:08:46 +00008451 int n;
Fred Drakec9680921999-12-13 16:37:25 +00008452
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008453#ifdef __APPLE__
8454 /* Issue #17557: As of OS X 10.8, getgroups(2) no longer raises EINVAL if
8455 * there are more groups than can fit in grouplist. Therefore, on OS X
8456 * always first call getgroups with length 0 to get the actual number
8457 * of groups.
8458 */
8459 n = getgroups(0, NULL);
8460 if (n < 0) {
8461 return posix_error();
8462 } else if (n <= MAX_GROUPS) {
8463 /* groups will fit in existing array */
8464 alt_grouplist = grouplist;
8465 } else {
8466 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8467 if (alt_grouplist == NULL) {
8468 errno = EINVAL;
8469 return posix_error();
8470 }
8471 }
8472
8473 n = getgroups(n, alt_grouplist);
8474 if (n == -1) {
8475 if (alt_grouplist != grouplist) {
8476 PyMem_Free(alt_grouplist);
8477 }
8478 return posix_error();
8479 }
8480#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008481 n = getgroups(MAX_GROUPS, grouplist);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008482 if (n < 0) {
8483 if (errno == EINVAL) {
8484 n = getgroups(0, NULL);
8485 if (n == -1) {
8486 return posix_error();
8487 }
8488 if (n == 0) {
8489 /* Avoid malloc(0) */
8490 alt_grouplist = grouplist;
8491 } else {
8492 alt_grouplist = PyMem_Malloc(n * sizeof(gid_t));
8493 if (alt_grouplist == NULL) {
8494 errno = EINVAL;
8495 return posix_error();
8496 }
8497 n = getgroups(n, alt_grouplist);
8498 if (n == -1) {
8499 PyMem_Free(alt_grouplist);
8500 return posix_error();
8501 }
8502 }
8503 } else {
8504 return posix_error();
8505 }
8506 }
Ned Deilyb5dd6d22013-08-01 21:21:15 -07008507#endif
8508
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008509 result = PyList_New(n);
8510 if (result != NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008511 int i;
8512 for (i = 0; i < n; ++i) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008513 PyObject *o = _PyLong_FromGid(alt_grouplist[i]);
Victor Stinner8c62be82010-05-06 00:08:46 +00008514 if (o == NULL) {
Stefan Krah0e803b32010-11-26 16:16:47 +00008515 Py_DECREF(result);
8516 result = NULL;
8517 break;
Fred Drakec9680921999-12-13 16:37:25 +00008518 }
Victor Stinner8c62be82010-05-06 00:08:46 +00008519 PyList_SET_ITEM(result, i, o);
Fred Drakec9680921999-12-13 16:37:25 +00008520 }
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00008521 }
8522
8523 if (alt_grouplist != grouplist) {
8524 PyMem_Free(alt_grouplist);
Victor Stinner8c62be82010-05-06 00:08:46 +00008525 }
Neal Norwitze241ce82003-02-17 18:17:05 +00008526
Fred Drakec9680921999-12-13 16:37:25 +00008527 return result;
8528}
Larry Hastings2f936352014-08-05 14:04:04 +10008529#endif /* HAVE_GETGROUPS */
Fred Drakec9680921999-12-13 16:37:25 +00008530
Antoine Pitroub7572f02009-12-02 20:46:48 +00008531#ifdef HAVE_INITGROUPS
8532PyDoc_STRVAR(posix_initgroups__doc__,
8533"initgroups(username, gid) -> None\n\n\
8534Call the system initgroups() to initialize the group access list with all of\n\
8535the groups of which the specified username is a member, plus the specified\n\
8536group id.");
8537
Larry Hastings2f936352014-08-05 14:04:04 +10008538/* AC 3.5: funny apple logic */
Antoine Pitroub7572f02009-12-02 20:46:48 +00008539static PyObject *
8540posix_initgroups(PyObject *self, PyObject *args)
8541{
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008542 PyObject *oname;
Victor Stinner8c62be82010-05-06 00:08:46 +00008543 char *username;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008544 int res;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008545#ifdef __APPLE__
8546 int gid;
8547#else
8548 gid_t gid;
8549#endif
Antoine Pitroub7572f02009-12-02 20:46:48 +00008550
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008551#ifdef __APPLE__
8552 if (!PyArg_ParseTuple(args, "O&i:initgroups",
8553 PyUnicode_FSConverter, &oname,
8554 &gid))
8555#else
8556 if (!PyArg_ParseTuple(args, "O&O&:initgroups",
8557 PyUnicode_FSConverter, &oname,
8558 _Py_Gid_Converter, &gid))
8559#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008560 return NULL;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008561 username = PyBytes_AS_STRING(oname);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008562
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008563 res = initgroups(username, gid);
Victor Stinner61ec5dc2010-08-15 09:22:44 +00008564 Py_DECREF(oname);
8565 if (res == -1)
Victor Stinner8c62be82010-05-06 00:08:46 +00008566 return PyErr_SetFromErrno(PyExc_OSError);
Antoine Pitroub7572f02009-12-02 20:46:48 +00008567
Victor Stinner8c62be82010-05-06 00:08:46 +00008568 Py_INCREF(Py_None);
8569 return Py_None;
Antoine Pitroub7572f02009-12-02 20:46:48 +00008570}
Larry Hastings2f936352014-08-05 14:04:04 +10008571#endif /* HAVE_INITGROUPS */
8572
Antoine Pitroub7572f02009-12-02 20:46:48 +00008573
Martin v. Löwis606edc12002-06-13 21:09:11 +00008574#ifdef HAVE_GETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10008575/*[clinic input]
8576os.getpgid
8577
8578 pid: pid_t
8579
8580Call the system call getpgid(), and return the result.
8581[clinic start generated code]*/
8582
8583PyDoc_STRVAR(os_getpgid__doc__,
8584"getpgid($module, /, pid)\n"
8585"--\n"
8586"\n"
8587"Call the system call getpgid(), and return the result.");
8588
8589#define OS_GETPGID_METHODDEF \
8590 {"getpgid", (PyCFunction)os_getpgid, METH_VARARGS|METH_KEYWORDS, os_getpgid__doc__},
Martin v. Löwis606edc12002-06-13 21:09:11 +00008591
8592static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008593os_getpgid_impl(PyModuleDef *module, pid_t pid);
8594
8595static PyObject *
8596os_getpgid(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwis606edc12002-06-13 21:09:11 +00008597{
Larry Hastings2f936352014-08-05 14:04:04 +10008598 PyObject *return_value = NULL;
8599 static char *_keywords[] = {"pid", NULL};
8600 pid_t pid;
8601
8602 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
8603 "" _Py_PARSE_PID ":getpgid", _keywords,
8604 &pid))
8605 goto exit;
8606 return_value = os_getpgid_impl(module, pid);
8607
8608exit:
8609 return return_value;
8610}
8611
8612static PyObject *
8613os_getpgid_impl(PyModuleDef *module, pid_t pid)
8614/*[clinic end generated code: output=3db4ed686179160d input=39d710ae3baaf1c7]*/
8615{
8616 pid_t pgid = getpgid(pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00008617 if (pgid < 0)
8618 return posix_error();
8619 return PyLong_FromPid(pgid);
Martin v. Löwis606edc12002-06-13 21:09:11 +00008620}
8621#endif /* HAVE_GETPGID */
8622
8623
Guido van Rossumb6775db1994-08-01 11:34:53 +00008624#ifdef HAVE_GETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008625/*[clinic input]
8626os.getpgrp
8627
8628Return the current process group id.
8629[clinic start generated code]*/
8630
8631PyDoc_STRVAR(os_getpgrp__doc__,
8632"getpgrp($module, /)\n"
8633"--\n"
8634"\n"
8635"Return the current process group id.");
8636
8637#define OS_GETPGRP_METHODDEF \
8638 {"getpgrp", (PyCFunction)os_getpgrp, METH_NOARGS, os_getpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008639
Barry Warsaw53699e91996-12-10 23:23:01 +00008640static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008641os_getpgrp_impl(PyModuleDef *module);
8642
8643static PyObject *
8644os_getpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8645{
8646 return os_getpgrp_impl(module);
8647}
8648
8649static PyObject *
8650os_getpgrp_impl(PyModuleDef *module)
8651/*[clinic end generated code: output=3b0d3663ea054277 input=6846fb2bb9a3705e]*/
Guido van Rossum04814471991-06-04 20:23:49 +00008652{
Guido van Rossumb6775db1994-08-01 11:34:53 +00008653#ifdef GETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008654 return PyLong_FromPid(getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008655#else /* GETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008656 return PyLong_FromPid(getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00008657#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00008658}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008659#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00008660
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008661
Guido van Rossumb6775db1994-08-01 11:34:53 +00008662#ifdef HAVE_SETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10008663/*[clinic input]
8664os.setpgrp
8665
8666Make the current process the leader of its process group.
8667[clinic start generated code]*/
8668
8669PyDoc_STRVAR(os_setpgrp__doc__,
8670"setpgrp($module, /)\n"
8671"--\n"
8672"\n"
8673"Make the current process the leader of its process group.");
8674
8675#define OS_SETPGRP_METHODDEF \
8676 {"setpgrp", (PyCFunction)os_setpgrp, METH_NOARGS, os_setpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008677
Barry Warsaw53699e91996-12-10 23:23:01 +00008678static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008679os_setpgrp_impl(PyModuleDef *module);
8680
8681static PyObject *
8682os_setpgrp(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8683{
8684 return os_setpgrp_impl(module);
8685}
8686
8687static PyObject *
8688os_setpgrp_impl(PyModuleDef *module)
8689/*[clinic end generated code: output=8fbb0ee29ef6fb2d input=1f0619fcb5731e7e]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00008690{
Guido van Rossum64933891994-10-20 21:56:42 +00008691#ifdef SETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00008692 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008693#else /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008694 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00008695#endif /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00008696 return posix_error();
8697 Py_INCREF(Py_None);
8698 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00008699}
Guido van Rossumb6775db1994-08-01 11:34:53 +00008700#endif /* HAVE_SETPGRP */
8701
Guido van Rossumad0ee831995-03-01 10:34:45 +00008702#ifdef HAVE_GETPPID
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008703
8704#ifdef MS_WINDOWS
8705#include <tlhelp32.h>
8706
8707static PyObject*
8708win32_getppid()
8709{
8710 HANDLE snapshot;
8711 pid_t mypid;
8712 PyObject* result = NULL;
8713 BOOL have_record;
8714 PROCESSENTRY32 pe;
8715
8716 mypid = getpid(); /* This function never fails */
8717
8718 snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
8719 if (snapshot == INVALID_HANDLE_VALUE)
8720 return PyErr_SetFromWindowsErr(GetLastError());
8721
8722 pe.dwSize = sizeof(pe);
8723 have_record = Process32First(snapshot, &pe);
8724 while (have_record) {
8725 if (mypid == (pid_t)pe.th32ProcessID) {
8726 /* We could cache the ulong value in a static variable. */
8727 result = PyLong_FromPid((pid_t)pe.th32ParentProcessID);
8728 break;
8729 }
8730
8731 have_record = Process32Next(snapshot, &pe);
8732 }
8733
8734 /* If our loop exits and our pid was not found (result will be NULL)
8735 * then GetLastError will return ERROR_NO_MORE_FILES. This is an
8736 * error anyway, so let's raise it. */
8737 if (!result)
8738 result = PyErr_SetFromWindowsErr(GetLastError());
8739
8740 CloseHandle(snapshot);
8741
8742 return result;
8743}
8744#endif /*MS_WINDOWS*/
8745
Larry Hastings2f936352014-08-05 14:04:04 +10008746
8747/*[clinic input]
8748os.getppid
8749
8750Return the parent's process id.
8751
8752If the parent process has already exited, Windows machines will still
8753return its id; others systems will return the id of the 'init' process (1).
8754[clinic start generated code]*/
8755
8756PyDoc_STRVAR(os_getppid__doc__,
8757"getppid($module, /)\n"
8758"--\n"
8759"\n"
8760"Return the parent\'s process id.\n"
8761"\n"
8762"If the parent process has already exited, Windows machines will still\n"
8763"return its id; others systems will return the id of the \'init\' process (1).");
8764
8765#define OS_GETPPID_METHODDEF \
8766 {"getppid", (PyCFunction)os_getppid, METH_NOARGS, os_getppid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008767
Barry Warsaw53699e91996-12-10 23:23:01 +00008768static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008769os_getppid_impl(PyModuleDef *module);
8770
8771static PyObject *
8772os_getppid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8773{
8774 return os_getppid_impl(module);
8775}
8776
8777static PyObject *
8778os_getppid_impl(PyModuleDef *module)
8779/*[clinic end generated code: output=9ff3b387781edf3a input=e637cb87539c030e]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00008780{
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008781#ifdef MS_WINDOWS
8782 return win32_getppid();
8783#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008784 return PyLong_FromPid(getppid());
Guido van Rossumad0ee831995-03-01 10:34:45 +00008785#endif
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00008786}
8787#endif /* HAVE_GETPPID */
Guido van Rossum85e3b011991-06-03 12:42:10 +00008788
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008789
Fred Drake12c6e2d1999-12-14 21:25:03 +00008790#ifdef HAVE_GETLOGIN
Larry Hastings2f936352014-08-05 14:04:04 +10008791/*[clinic input]
8792os.getlogin
8793
8794Return the actual login name.
8795[clinic start generated code]*/
8796
8797PyDoc_STRVAR(os_getlogin__doc__,
8798"getlogin($module, /)\n"
8799"--\n"
8800"\n"
8801"Return the actual login name.");
8802
8803#define OS_GETLOGIN_METHODDEF \
8804 {"getlogin", (PyCFunction)os_getlogin, METH_NOARGS, os_getlogin__doc__},
Fred Drake12c6e2d1999-12-14 21:25:03 +00008805
8806static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008807os_getlogin_impl(PyModuleDef *module);
8808
8809static PyObject *
8810os_getlogin(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8811{
8812 return os_getlogin_impl(module);
8813}
8814
8815static PyObject *
8816os_getlogin_impl(PyModuleDef *module)
8817/*[clinic end generated code: output=ab6211dab104cbb2 input=2a21ab1e917163df]*/
Fred Drake12c6e2d1999-12-14 21:25:03 +00008818{
Victor Stinner8c62be82010-05-06 00:08:46 +00008819 PyObject *result = NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008820#ifdef MS_WINDOWS
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008821 wchar_t user_name[UNLEN + 1];
Victor Stinner63941882011-09-29 00:42:28 +02008822 DWORD num_chars = Py_ARRAY_LENGTH(user_name);
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008823
8824 if (GetUserNameW(user_name, &num_chars)) {
8825 /* num_chars is the number of unicode chars plus null terminator */
8826 result = PyUnicode_FromWideChar(user_name, num_chars - 1);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008827 }
8828 else
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008829 result = PyErr_SetFromWindowsErr(GetLastError());
8830#else
Victor Stinner8c62be82010-05-06 00:08:46 +00008831 char *name;
8832 int old_errno = errno;
Fred Drake12c6e2d1999-12-14 21:25:03 +00008833
Victor Stinner8c62be82010-05-06 00:08:46 +00008834 errno = 0;
8835 name = getlogin();
8836 if (name == NULL) {
8837 if (errno)
Victor Stinnere039ffe2010-08-15 09:33:08 +00008838 posix_error();
Fred Drake12c6e2d1999-12-14 21:25:03 +00008839 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008840 PyErr_SetString(PyExc_OSError, "unable to determine login name");
Victor Stinner8c62be82010-05-06 00:08:46 +00008841 }
8842 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00008843 result = PyUnicode_DecodeFSDefault(name);
Victor Stinner8c62be82010-05-06 00:08:46 +00008844 errno = old_errno;
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008845#endif
Fred Drake12c6e2d1999-12-14 21:25:03 +00008846 return result;
8847}
Brian Curtine8e4b3b2010-09-23 20:04:14 +00008848#endif /* HAVE_GETLOGIN */
Fred Drake12c6e2d1999-12-14 21:25:03 +00008849
Larry Hastings2f936352014-08-05 14:04:04 +10008850
Guido van Rossumad0ee831995-03-01 10:34:45 +00008851#ifdef HAVE_GETUID
Larry Hastings2f936352014-08-05 14:04:04 +10008852/*[clinic input]
8853os.getuid
8854
8855Return the current process's user id.
8856[clinic start generated code]*/
8857
8858PyDoc_STRVAR(os_getuid__doc__,
8859"getuid($module, /)\n"
8860"--\n"
8861"\n"
8862"Return the current process\'s user id.");
8863
8864#define OS_GETUID_METHODDEF \
8865 {"getuid", (PyCFunction)os_getuid, METH_NOARGS, os_getuid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008866
Barry Warsaw53699e91996-12-10 23:23:01 +00008867static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008868os_getuid_impl(PyModuleDef *module);
8869
8870static PyObject *
8871os_getuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
8872{
8873 return os_getuid_impl(module);
8874}
8875
8876static PyObject *
8877os_getuid_impl(PyModuleDef *module)
8878/*[clinic end generated code: output=77e0dcf2e37d1e89 input=b53c8b35f110a516]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00008879{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02008880 return _PyLong_FromUid(getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00008881}
Larry Hastings2f936352014-08-05 14:04:04 +10008882#endif /* HAVE_GETUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00008883
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008884
Brian Curtineb24d742010-04-12 17:16:38 +00008885#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008886#define HAVE_KILL
8887#endif /* MS_WINDOWS */
8888
8889#ifdef HAVE_KILL
8890/*[clinic input]
8891os.kill
8892
8893 pid: pid_t
8894 signal: Py_ssize_t
8895 /
8896
8897Kill a process with a signal.
8898[clinic start generated code]*/
8899
8900PyDoc_STRVAR(os_kill__doc__,
8901"kill($module, pid, signal, /)\n"
8902"--\n"
8903"\n"
8904"Kill a process with a signal.");
8905
8906#define OS_KILL_METHODDEF \
8907 {"kill", (PyCFunction)os_kill, METH_VARARGS, os_kill__doc__},
Brian Curtineb24d742010-04-12 17:16:38 +00008908
8909static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10008910os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal);
8911
8912static PyObject *
8913os_kill(PyModuleDef *module, PyObject *args)
8914{
8915 PyObject *return_value = NULL;
8916 pid_t pid;
8917 Py_ssize_t signal;
8918
8919 if (!PyArg_ParseTuple(args,
8920 "" _Py_PARSE_PID "n:kill",
8921 &pid, &signal))
8922 goto exit;
8923 return_value = os_kill_impl(module, pid, signal);
8924
8925exit:
8926 return return_value;
8927}
8928
8929static PyObject *
8930os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal)
8931/*[clinic end generated code: output=2f5c77920ed575e6 input=61a36b86ca275ab9]*/
8932#ifndef MS_WINDOWS
8933{
8934 if (kill(pid, (int)signal) == -1)
8935 return posix_error();
8936 Py_RETURN_NONE;
8937}
8938#else /* !MS_WINDOWS */
Brian Curtineb24d742010-04-12 17:16:38 +00008939{
Amaury Forgeot d'Arc0a589c92010-05-15 20:35:12 +00008940 PyObject *result;
Larry Hastings2f936352014-08-05 14:04:04 +10008941 DWORD sig = (DWORD)signal;
8942 DWORD err;
Victor Stinner8c62be82010-05-06 00:08:46 +00008943 HANDLE handle;
Brian Curtineb24d742010-04-12 17:16:38 +00008944
Victor Stinner8c62be82010-05-06 00:08:46 +00008945 /* Console processes which share a common console can be sent CTRL+C or
8946 CTRL+BREAK events, provided they handle said events. */
8947 if (sig == CTRL_C_EVENT || sig == CTRL_BREAK_EVENT) {
Richard Oudkerkac0ad882013-06-05 23:29:30 +01008948 if (GenerateConsoleCtrlEvent(sig, (DWORD)pid) == 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008949 err = GetLastError();
8950 PyErr_SetFromWindowsErr(err);
8951 }
8952 else
8953 Py_RETURN_NONE;
8954 }
Brian Curtineb24d742010-04-12 17:16:38 +00008955
Victor Stinner8c62be82010-05-06 00:08:46 +00008956 /* If the signal is outside of what GenerateConsoleCtrlEvent can use,
8957 attempt to open and terminate the process. */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01008958 handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, (DWORD)pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00008959 if (handle == NULL) {
8960 err = GetLastError();
8961 return PyErr_SetFromWindowsErr(err);
8962 }
Brian Curtineb24d742010-04-12 17:16:38 +00008963
Victor Stinner8c62be82010-05-06 00:08:46 +00008964 if (TerminateProcess(handle, sig) == 0) {
8965 err = GetLastError();
8966 result = PyErr_SetFromWindowsErr(err);
8967 } else {
8968 Py_INCREF(Py_None);
8969 result = Py_None;
8970 }
Brian Curtineb24d742010-04-12 17:16:38 +00008971
Victor Stinner8c62be82010-05-06 00:08:46 +00008972 CloseHandle(handle);
8973 return result;
Brian Curtineb24d742010-04-12 17:16:38 +00008974}
Larry Hastings2f936352014-08-05 14:04:04 +10008975#endif /* !MS_WINDOWS */
8976#endif /* HAVE_KILL */
8977
8978
8979#ifdef HAVE_KILLPG
8980/*[clinic input]
8981os.killpg
8982
8983 pgid: pid_t
8984 signal: int
8985 /
8986
8987Kill a process group with a signal.
8988[clinic start generated code]*/
8989
8990PyDoc_STRVAR(os_killpg__doc__,
8991"killpg($module, pgid, signal, /)\n"
8992"--\n"
8993"\n"
8994"Kill a process group with a signal.");
8995
8996#define OS_KILLPG_METHODDEF \
8997 {"killpg", (PyCFunction)os_killpg, METH_VARARGS, os_killpg__doc__},
8998
8999static PyObject *
9000os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal);
9001
9002static PyObject *
9003os_killpg(PyModuleDef *module, PyObject *args)
9004{
9005 PyObject *return_value = NULL;
9006 pid_t pgid;
9007 int signal;
9008
9009 if (!PyArg_ParseTuple(args,
9010 "" _Py_PARSE_PID "i:killpg",
9011 &pgid, &signal))
9012 goto exit;
9013 return_value = os_killpg_impl(module, pgid, signal);
9014
9015exit:
9016 return return_value;
9017}
9018
9019static PyObject *
9020os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal)
9021/*[clinic end generated code: output=0e05215d1c007e01 input=38b5449eb8faec19]*/
9022{
9023 /* XXX some man pages make the `pgid` parameter an int, others
9024 a pid_t. Since getpgrp() returns a pid_t, we assume killpg should
9025 take the same type. Moreover, pid_t is always at least as wide as
9026 int (else compilation of this module fails), which is safe. */
9027 if (killpg(pgid, signal) == -1)
9028 return posix_error();
9029 Py_RETURN_NONE;
9030}
9031#endif /* HAVE_KILLPG */
9032
Brian Curtineb24d742010-04-12 17:16:38 +00009033
Guido van Rossumc0125471996-06-28 18:55:32 +00009034#ifdef HAVE_PLOCK
Guido van Rossumc0125471996-06-28 18:55:32 +00009035#ifdef HAVE_SYS_LOCK_H
9036#include <sys/lock.h>
9037#endif
9038
Larry Hastings2f936352014-08-05 14:04:04 +10009039/*[clinic input]
9040os.plock
9041 op: int
9042 /
9043
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009044Lock program segments into memory.");
Larry Hastings2f936352014-08-05 14:04:04 +10009045[clinic start generated code]*/
9046
9047PyDoc_STRVAR(os_plock__doc__,
9048"plock($module, op, /)\n"
9049"--\n"
9050"\n"
9051"Lock program segments into memory.\");");
9052
9053#define OS_PLOCK_METHODDEF \
9054 {"plock", (PyCFunction)os_plock, METH_VARARGS, os_plock__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009055
Barry Warsaw53699e91996-12-10 23:23:01 +00009056static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009057os_plock_impl(PyModuleDef *module, int op);
9058
9059static PyObject *
9060os_plock(PyModuleDef *module, PyObject *args)
Guido van Rossumc0125471996-06-28 18:55:32 +00009061{
Larry Hastings2f936352014-08-05 14:04:04 +10009062 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009063 int op;
Larry Hastings2f936352014-08-05 14:04:04 +10009064
9065 if (!PyArg_ParseTuple(args,
9066 "i:plock",
9067 &op))
9068 goto exit;
9069 return_value = os_plock_impl(module, op);
9070
9071exit:
9072 return return_value;
9073}
9074
9075static PyObject *
9076os_plock_impl(PyModuleDef *module, int op)
9077/*[clinic end generated code: output=2744fe4b6e5f4dbc input=e6e5e348e1525f60]*/
9078{
Victor Stinner8c62be82010-05-06 00:08:46 +00009079 if (plock(op) == -1)
9080 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009081 Py_RETURN_NONE;
Guido van Rossumc0125471996-06-28 18:55:32 +00009082}
Larry Hastings2f936352014-08-05 14:04:04 +10009083#endif /* HAVE_PLOCK */
9084
Guido van Rossumc0125471996-06-28 18:55:32 +00009085
Guido van Rossumb6775db1994-08-01 11:34:53 +00009086#ifdef HAVE_SETUID
Larry Hastings2f936352014-08-05 14:04:04 +10009087/*[clinic input]
9088os.setuid
9089
9090 uid: uid_t
9091 /
9092
9093Set the current process's user id.
9094[clinic start generated code]*/
9095
9096PyDoc_STRVAR(os_setuid__doc__,
9097"setuid($module, uid, /)\n"
9098"--\n"
9099"\n"
9100"Set the current process\'s user id.");
9101
9102#define OS_SETUID_METHODDEF \
9103 {"setuid", (PyCFunction)os_setuid, METH_VARARGS, os_setuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009104
Barry Warsaw53699e91996-12-10 23:23:01 +00009105static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009106os_setuid_impl(PyModuleDef *module, uid_t uid);
9107
9108static PyObject *
9109os_setuid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009110{
Larry Hastings2f936352014-08-05 14:04:04 +10009111 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009112 uid_t uid;
Larry Hastings2f936352014-08-05 14:04:04 +10009113
9114 if (!PyArg_ParseTuple(args,
9115 "O&:setuid",
9116 _Py_Uid_Converter, &uid))
9117 goto exit;
9118 return_value = os_setuid_impl(module, uid);
9119
9120exit:
9121 return return_value;
9122}
9123
9124static PyObject *
9125os_setuid_impl(PyModuleDef *module, uid_t uid)
9126/*[clinic end generated code: output=aea344bc22ccf400 input=c921a3285aa22256]*/
9127{
Victor Stinner8c62be82010-05-06 00:08:46 +00009128 if (setuid(uid) < 0)
9129 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009130 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009131}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009132#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009133
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009134
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009135#ifdef HAVE_SETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10009136/*[clinic input]
9137os.seteuid
9138
9139 euid: uid_t
9140 /
9141
9142Set the current process's effective user id.
9143[clinic start generated code]*/
9144
9145PyDoc_STRVAR(os_seteuid__doc__,
9146"seteuid($module, euid, /)\n"
9147"--\n"
9148"\n"
9149"Set the current process\'s effective user id.");
9150
9151#define OS_SETEUID_METHODDEF \
9152 {"seteuid", (PyCFunction)os_seteuid, METH_VARARGS, os_seteuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009153
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009154static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009155os_seteuid_impl(PyModuleDef *module, uid_t euid);
9156
9157static PyObject *
9158os_seteuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009159{
Larry Hastings2f936352014-08-05 14:04:04 +10009160 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009161 uid_t euid;
Larry Hastings2f936352014-08-05 14:04:04 +10009162
9163 if (!PyArg_ParseTuple(args,
9164 "O&:seteuid",
9165 _Py_Uid_Converter, &euid))
9166 goto exit;
9167 return_value = os_seteuid_impl(module, euid);
9168
9169exit:
9170 return return_value;
9171}
9172
9173static PyObject *
9174os_seteuid_impl(PyModuleDef *module, uid_t euid)
9175/*[clinic end generated code: output=6e824cce4f3b8a5d input=ba93d927e4781aa9]*/
9176{
9177 if (seteuid(euid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009178 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009179 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009180}
9181#endif /* HAVE_SETEUID */
9182
Larry Hastings2f936352014-08-05 14:04:04 +10009183
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009184#ifdef HAVE_SETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10009185/*[clinic input]
9186os.setegid
9187
9188 egid: gid_t
9189 /
9190
9191Set the current process's effective group id.
9192[clinic start generated code]*/
9193
9194PyDoc_STRVAR(os_setegid__doc__,
9195"setegid($module, egid, /)\n"
9196"--\n"
9197"\n"
9198"Set the current process\'s effective group id.");
9199
9200#define OS_SETEGID_METHODDEF \
9201 {"setegid", (PyCFunction)os_setegid, METH_VARARGS, os_setegid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009202
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009203static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009204os_setegid_impl(PyModuleDef *module, gid_t egid);
9205
9206static PyObject *
9207os_setegid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009208{
Larry Hastings2f936352014-08-05 14:04:04 +10009209 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009210 gid_t egid;
Larry Hastings2f936352014-08-05 14:04:04 +10009211
9212 if (!PyArg_ParseTuple(args,
9213 "O&:setegid",
9214 _Py_Gid_Converter, &egid))
9215 goto exit;
9216 return_value = os_setegid_impl(module, egid);
9217
9218exit:
9219 return return_value;
9220}
9221
9222static PyObject *
9223os_setegid_impl(PyModuleDef *module, gid_t egid)
9224/*[clinic end generated code: output=80a32263a4d56a9c input=4080526d0ccd6ce3]*/
9225{
9226 if (setegid(egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009227 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009228 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009229}
9230#endif /* HAVE_SETEGID */
9231
Larry Hastings2f936352014-08-05 14:04:04 +10009232
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009233#ifdef HAVE_SETREUID
Larry Hastings2f936352014-08-05 14:04:04 +10009234/*[clinic input]
9235os.setreuid
9236
9237 ruid: uid_t
9238 euid: uid_t
9239 /
9240
9241Set the current process's real and effective user ids.
9242[clinic start generated code]*/
9243
9244PyDoc_STRVAR(os_setreuid__doc__,
9245"setreuid($module, ruid, euid, /)\n"
9246"--\n"
9247"\n"
9248"Set the current process\'s real and effective user ids.");
9249
9250#define OS_SETREUID_METHODDEF \
9251 {"setreuid", (PyCFunction)os_setreuid, METH_VARARGS, os_setreuid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009252
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009253static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009254os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid);
9255
9256static PyObject *
9257os_setreuid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009258{
Larry Hastings2f936352014-08-05 14:04:04 +10009259 PyObject *return_value = NULL;
9260 uid_t ruid;
9261 uid_t euid;
9262
9263 if (!PyArg_ParseTuple(args,
9264 "O&O&:setreuid",
9265 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid))
9266 goto exit;
9267 return_value = os_setreuid_impl(module, ruid, euid);
9268
9269exit:
9270 return return_value;
9271}
9272
9273static PyObject *
9274os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid)
9275/*[clinic end generated code: output=d7f226f943dad739 input=0ca8978de663880c]*/
9276{
Victor Stinner8c62be82010-05-06 00:08:46 +00009277 if (setreuid(ruid, euid) < 0) {
9278 return posix_error();
9279 } else {
9280 Py_INCREF(Py_None);
9281 return Py_None;
9282 }
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009283}
9284#endif /* HAVE_SETREUID */
9285
Larry Hastings2f936352014-08-05 14:04:04 +10009286
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009287#ifdef HAVE_SETREGID
Larry Hastings2f936352014-08-05 14:04:04 +10009288/*[clinic input]
9289os.setregid
9290
9291 rgid: gid_t
9292 egid: gid_t
9293 /
9294
9295Set the current process's real and effective group ids.
9296[clinic start generated code]*/
9297
9298PyDoc_STRVAR(os_setregid__doc__,
9299"setregid($module, rgid, egid, /)\n"
9300"--\n"
9301"\n"
9302"Set the current process\'s real and effective group ids.");
9303
9304#define OS_SETREGID_METHODDEF \
9305 {"setregid", (PyCFunction)os_setregid, METH_VARARGS, os_setregid__doc__},
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00009306
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009307static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009308os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid);
9309
9310static PyObject *
9311os_setregid(PyModuleDef *module, PyObject *args)
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009312{
Larry Hastings2f936352014-08-05 14:04:04 +10009313 PyObject *return_value = NULL;
9314 gid_t rgid;
9315 gid_t egid;
9316
9317 if (!PyArg_ParseTuple(args,
9318 "O&O&:setregid",
9319 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid))
9320 goto exit;
9321 return_value = os_setregid_impl(module, rgid, egid);
9322
9323exit:
9324 return return_value;
9325}
9326
9327static PyObject *
9328os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid)
9329/*[clinic end generated code: output=a82d9ab70f8e6562 input=c59499f72846db78]*/
9330{
9331 if (setregid(rgid, egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00009332 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009333 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00009334}
9335#endif /* HAVE_SETREGID */
9336
Larry Hastings2f936352014-08-05 14:04:04 +10009337
Guido van Rossumb6775db1994-08-01 11:34:53 +00009338#ifdef HAVE_SETGID
Larry Hastings2f936352014-08-05 14:04:04 +10009339/*[clinic input]
9340os.setgid
9341 gid: gid_t
9342 /
9343
9344Set the current process's group id.
9345[clinic start generated code]*/
9346
9347PyDoc_STRVAR(os_setgid__doc__,
9348"setgid($module, gid, /)\n"
9349"--\n"
9350"\n"
9351"Set the current process\'s group id.");
9352
9353#define OS_SETGID_METHODDEF \
9354 {"setgid", (PyCFunction)os_setgid, METH_VARARGS, os_setgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009355
Barry Warsaw53699e91996-12-10 23:23:01 +00009356static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009357os_setgid_impl(PyModuleDef *module, gid_t gid);
9358
9359static PyObject *
9360os_setgid(PyModuleDef *module, PyObject *args)
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009361{
Larry Hastings2f936352014-08-05 14:04:04 +10009362 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009363 gid_t gid;
Larry Hastings2f936352014-08-05 14:04:04 +10009364
9365 if (!PyArg_ParseTuple(args,
9366 "O&:setgid",
9367 _Py_Gid_Converter, &gid))
9368 goto exit;
9369 return_value = os_setgid_impl(module, gid);
9370
9371exit:
9372 return return_value;
9373}
9374
9375static PyObject *
9376os_setgid_impl(PyModuleDef *module, gid_t gid)
9377/*[clinic end generated code: output=08287886db435f23 input=27d30c4059045dc6]*/
9378{
Victor Stinner8c62be82010-05-06 00:08:46 +00009379 if (setgid(gid) < 0)
9380 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10009381 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009382}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00009383#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00009384
Larry Hastings2f936352014-08-05 14:04:04 +10009385
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009386#ifdef HAVE_SETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10009387/*[clinic input]
9388os.setgroups
9389
9390 groups: object
9391 /
9392
9393Set the groups of the current process to list.
9394[clinic start generated code]*/
9395
9396PyDoc_STRVAR(os_setgroups__doc__,
9397"setgroups($module, groups, /)\n"
9398"--\n"
9399"\n"
9400"Set the groups of the current process to list.");
9401
9402#define OS_SETGROUPS_METHODDEF \
9403 {"setgroups", (PyCFunction)os_setgroups, METH_O, os_setgroups__doc__},
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009404
9405static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009406os_setgroups(PyModuleDef *module, PyObject *groups)
9407/*[clinic end generated code: output=0b8de65d5b3cda94 input=fa742ca3daf85a7e]*/
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009408{
Victor Stinner8c62be82010-05-06 00:08:46 +00009409 int i, len;
9410 gid_t grouplist[MAX_GROUPS];
Tim Peters5aa91602002-01-30 05:46:57 +00009411
Victor Stinner8c62be82010-05-06 00:08:46 +00009412 if (!PySequence_Check(groups)) {
9413 PyErr_SetString(PyExc_TypeError, "setgroups argument must be a sequence");
9414 return NULL;
9415 }
9416 len = PySequence_Size(groups);
9417 if (len > MAX_GROUPS) {
9418 PyErr_SetString(PyExc_ValueError, "too many groups");
9419 return NULL;
9420 }
9421 for(i = 0; i < len; i++) {
9422 PyObject *elem;
9423 elem = PySequence_GetItem(groups, i);
9424 if (!elem)
9425 return NULL;
9426 if (!PyLong_Check(elem)) {
9427 PyErr_SetString(PyExc_TypeError,
9428 "groups must be integers");
9429 Py_DECREF(elem);
9430 return NULL;
9431 } else {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009432 if (!_Py_Gid_Converter(elem, &grouplist[i])) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009433 Py_DECREF(elem);
9434 return NULL;
9435 }
9436 }
9437 Py_DECREF(elem);
9438 }
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009439
Victor Stinner8c62be82010-05-06 00:08:46 +00009440 if (setgroups(len, grouplist) < 0)
9441 return posix_error();
9442 Py_INCREF(Py_None);
9443 return Py_None;
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00009444}
9445#endif /* HAVE_SETGROUPS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009446
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009447#if defined(HAVE_WAIT3) || defined(HAVE_WAIT4)
9448static PyObject *
Victor Stinner4195b5c2012-02-08 23:03:19 +01009449wait_helper(pid_t pid, int status, struct rusage *ru)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009450{
Victor Stinner8c62be82010-05-06 00:08:46 +00009451 PyObject *result;
9452 static PyObject *struct_rusage;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02009453 _Py_IDENTIFIER(struct_rusage);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009454
Victor Stinner8c62be82010-05-06 00:08:46 +00009455 if (pid == -1)
9456 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009457
Victor Stinner8c62be82010-05-06 00:08:46 +00009458 if (struct_rusage == NULL) {
9459 PyObject *m = PyImport_ImportModuleNoBlock("resource");
9460 if (m == NULL)
9461 return NULL;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02009462 struct_rusage = _PyObject_GetAttrId(m, &PyId_struct_rusage);
Victor Stinner8c62be82010-05-06 00:08:46 +00009463 Py_DECREF(m);
9464 if (struct_rusage == NULL)
9465 return NULL;
9466 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009467
Victor Stinner8c62be82010-05-06 00:08:46 +00009468 /* XXX(nnorwitz): Copied (w/mods) from resource.c, there should be only one. */
9469 result = PyStructSequence_New((PyTypeObject*) struct_rusage);
9470 if (!result)
9471 return NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009472
9473#ifndef doubletime
9474#define doubletime(TV) ((double)(TV).tv_sec + (TV).tv_usec * 0.000001)
9475#endif
9476
Victor Stinner8c62be82010-05-06 00:08:46 +00009477 PyStructSequence_SET_ITEM(result, 0,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009478 PyFloat_FromDouble(doubletime(ru->ru_utime)));
Victor Stinner8c62be82010-05-06 00:08:46 +00009479 PyStructSequence_SET_ITEM(result, 1,
Victor Stinner4195b5c2012-02-08 23:03:19 +01009480 PyFloat_FromDouble(doubletime(ru->ru_stime)));
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009481#define SET_INT(result, index, value)\
Victor Stinner8c62be82010-05-06 00:08:46 +00009482 PyStructSequence_SET_ITEM(result, index, PyLong_FromLong(value))
9483 SET_INT(result, 2, ru->ru_maxrss);
9484 SET_INT(result, 3, ru->ru_ixrss);
9485 SET_INT(result, 4, ru->ru_idrss);
9486 SET_INT(result, 5, ru->ru_isrss);
9487 SET_INT(result, 6, ru->ru_minflt);
9488 SET_INT(result, 7, ru->ru_majflt);
9489 SET_INT(result, 8, ru->ru_nswap);
9490 SET_INT(result, 9, ru->ru_inblock);
9491 SET_INT(result, 10, ru->ru_oublock);
9492 SET_INT(result, 11, ru->ru_msgsnd);
9493 SET_INT(result, 12, ru->ru_msgrcv);
9494 SET_INT(result, 13, ru->ru_nsignals);
9495 SET_INT(result, 14, ru->ru_nvcsw);
9496 SET_INT(result, 15, ru->ru_nivcsw);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009497#undef SET_INT
9498
Victor Stinner8c62be82010-05-06 00:08:46 +00009499 if (PyErr_Occurred()) {
9500 Py_DECREF(result);
9501 return NULL;
9502 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009503
Victor Stinner8c62be82010-05-06 00:08:46 +00009504 return Py_BuildValue("NiN", PyLong_FromPid(pid), status, result);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009505}
9506#endif /* HAVE_WAIT3 || HAVE_WAIT4 */
9507
Larry Hastings2f936352014-08-05 14:04:04 +10009508
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009509#ifdef HAVE_WAIT3
Larry Hastings2f936352014-08-05 14:04:04 +10009510/*[clinic input]
9511os.wait3
9512
9513 options: int
9514Wait for completion of a child process.
9515
9516Returns a tuple of information about the child process:
9517 (pid, status, rusage)
9518[clinic start generated code]*/
9519
9520PyDoc_STRVAR(os_wait3__doc__,
9521"wait3($module, /, options)\n"
9522"--\n"
9523"\n"
9524"Wait for completion of a child process.\n"
9525"\n"
9526"Returns a tuple of information about the child process:\n"
9527" (pid, status, rusage)");
9528
9529#define OS_WAIT3_METHODDEF \
9530 {"wait3", (PyCFunction)os_wait3, METH_VARARGS|METH_KEYWORDS, os_wait3__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009531
9532static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009533os_wait3_impl(PyModuleDef *module, int options);
9534
9535static PyObject *
9536os_wait3(PyModuleDef *module, PyObject *args, PyObject *kwargs)
9537{
9538 PyObject *return_value = NULL;
9539 static char *_keywords[] = {"options", NULL};
9540 int options;
9541
9542 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9543 "i:wait3", _keywords,
9544 &options))
9545 goto exit;
9546 return_value = os_wait3_impl(module, options);
9547
9548exit:
9549 return return_value;
9550}
9551
9552static PyObject *
9553os_wait3_impl(PyModuleDef *module, int options)
9554/*[clinic end generated code: output=1f2a63b6a93cbb57 input=8ac4c56956b61710]*/
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009555{
Victor Stinner8c62be82010-05-06 00:08:46 +00009556 pid_t pid;
Victor Stinner8c62be82010-05-06 00:08:46 +00009557 struct rusage ru;
9558 WAIT_TYPE status;
9559 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009560
Victor Stinner8c62be82010-05-06 00:08:46 +00009561 Py_BEGIN_ALLOW_THREADS
9562 pid = wait3(&status, options, &ru);
9563 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009564
Victor Stinner4195b5c2012-02-08 23:03:19 +01009565 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009566}
9567#endif /* HAVE_WAIT3 */
9568
Larry Hastings2f936352014-08-05 14:04:04 +10009569
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009570#ifdef HAVE_WAIT4
Larry Hastings2f936352014-08-05 14:04:04 +10009571/*[clinic input]
9572
9573os.wait4
9574
9575 pid: pid_t
9576 options: int
9577
9578Wait for completion of a specific child process.
9579
9580Returns a tuple of information about the child process:
9581 (pid, status, rusage)
9582[clinic start generated code]*/
9583
9584PyDoc_STRVAR(os_wait4__doc__,
9585"wait4($module, /, pid, options)\n"
9586"--\n"
9587"\n"
9588"Wait for completion of a specific child process.\n"
9589"\n"
9590"Returns a tuple of information about the child process:\n"
9591" (pid, status, rusage)");
9592
9593#define OS_WAIT4_METHODDEF \
9594 {"wait4", (PyCFunction)os_wait4, METH_VARARGS|METH_KEYWORDS, os_wait4__doc__},
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009595
9596static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009597os_wait4_impl(PyModuleDef *module, pid_t pid, int options);
9598
9599static PyObject *
9600os_wait4(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009601{
Larry Hastings2f936352014-08-05 14:04:04 +10009602 PyObject *return_value = NULL;
9603 static char *_keywords[] = {"pid", "options", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +00009604 pid_t pid;
9605 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009606
9607 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
9608 "" _Py_PARSE_PID "i:wait4", _keywords,
9609 &pid, &options))
9610 goto exit;
9611 return_value = os_wait4_impl(module, pid, options);
9612
9613exit:
9614 return return_value;
9615}
9616
9617static PyObject *
9618os_wait4_impl(PyModuleDef *module, pid_t pid, int options)
9619/*[clinic end generated code: output=20dfb05289d37dc6 input=d11deed0750600ba]*/
9620{
Victor Stinner8c62be82010-05-06 00:08:46 +00009621 struct rusage ru;
9622 WAIT_TYPE status;
9623 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009624
Victor Stinner8c62be82010-05-06 00:08:46 +00009625 Py_BEGIN_ALLOW_THREADS
9626 pid = wait4(pid, &status, options, &ru);
9627 Py_END_ALLOW_THREADS
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009628
Victor Stinner4195b5c2012-02-08 23:03:19 +01009629 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009630}
9631#endif /* HAVE_WAIT4 */
9632
Larry Hastings2f936352014-08-05 14:04:04 +10009633
Ross Lagerwall7807c352011-03-17 20:20:30 +02009634#if defined(HAVE_WAITID) && !defined(__APPLE__)
Larry Hastings2f936352014-08-05 14:04:04 +10009635/*[clinic input]
9636os.waitid
9637
9638 idtype: idtype_t
9639 Must be one of be P_PID, P_PGID or P_ALL.
9640 id: id_t
9641 The id to wait on.
9642 options: int
9643 Constructed from the ORing of one or more of WEXITED, WSTOPPED
9644 or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.
9645 /
9646
9647Returns the result of waiting for a process or processes.
9648
9649Returns either waitid_result or None if WNOHANG is specified and there are
9650no children in a waitable state.
9651[clinic start generated code]*/
9652
9653PyDoc_STRVAR(os_waitid__doc__,
9654"waitid($module, idtype, id, options, /)\n"
9655"--\n"
9656"\n"
9657"Returns the result of waiting for a process or processes.\n"
9658"\n"
9659" idtype\n"
9660" Must be one of be P_PID, P_PGID or P_ALL.\n"
9661" id\n"
9662" The id to wait on.\n"
9663" options\n"
9664" Constructed from the ORing of one or more of WEXITED, WSTOPPED\n"
9665" or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.\n"
9666"\n"
9667"Returns either waitid_result or None if WNOHANG is specified and there are\n"
9668"no children in a waitable state.");
9669
9670#define OS_WAITID_METHODDEF \
9671 {"waitid", (PyCFunction)os_waitid, METH_VARARGS, os_waitid__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +02009672
9673static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009674os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options);
9675
9676static PyObject *
9677os_waitid(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +02009678{
Larry Hastings2f936352014-08-05 14:04:04 +10009679 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009680 idtype_t idtype;
9681 id_t id;
Larry Hastings2f936352014-08-05 14:04:04 +10009682 int options;
9683
9684 if (!PyArg_ParseTuple(args,
9685 "i" _Py_PARSE_PID "i:waitid",
9686 &idtype, &id, &options))
9687 goto exit;
9688 return_value = os_waitid_impl(module, idtype, id, options);
9689
9690exit:
9691 return return_value;
9692}
9693
9694static PyObject *
9695os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options)
9696/*[clinic end generated code: output=fb44bf97f01021b2 input=d8e7f76e052b7920]*/
9697{
9698 PyObject *result;
9699 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +02009700 siginfo_t si;
9701 si.si_pid = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10009702
Ross Lagerwall7807c352011-03-17 20:20:30 +02009703 Py_BEGIN_ALLOW_THREADS
9704 res = waitid(idtype, id, &si, options);
9705 Py_END_ALLOW_THREADS
9706 if (res == -1)
9707 return posix_error();
9708
9709 if (si.si_pid == 0)
9710 Py_RETURN_NONE;
9711
9712 result = PyStructSequence_New(&WaitidResultType);
9713 if (!result)
9714 return NULL;
9715
9716 PyStructSequence_SET_ITEM(result, 0, PyLong_FromPid(si.si_pid));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02009717 PyStructSequence_SET_ITEM(result, 1, _PyLong_FromUid(si.si_uid));
Ross Lagerwall7807c352011-03-17 20:20:30 +02009718 PyStructSequence_SET_ITEM(result, 2, PyLong_FromLong((long)(si.si_signo)));
9719 PyStructSequence_SET_ITEM(result, 3, PyLong_FromLong((long)(si.si_status)));
9720 PyStructSequence_SET_ITEM(result, 4, PyLong_FromLong((long)(si.si_code)));
9721 if (PyErr_Occurred()) {
9722 Py_DECREF(result);
9723 return NULL;
9724 }
9725
9726 return result;
9727}
Larry Hastings2f936352014-08-05 14:04:04 +10009728#endif /* defined(HAVE_WAITID) && !defined(__APPLE__) */
Ross Lagerwall7807c352011-03-17 20:20:30 +02009729
Larry Hastings2f936352014-08-05 14:04:04 +10009730
9731#if defined(HAVE_WAITPID)
9732/*[clinic input]
9733os.waitpid
9734 pid: pid_t
9735 options: int
9736 /
9737
9738Wait for completion of a given child process.
9739
9740Returns a tuple of information regarding the child process:
9741 (pid, status)
9742
9743The options argument is ignored on Windows.
9744[clinic start generated code]*/
9745
9746PyDoc_STRVAR(os_waitpid__doc__,
9747"waitpid($module, pid, options, /)\n"
9748"--\n"
9749"\n"
9750"Wait for completion of a given child process.\n"
9751"\n"
9752"Returns a tuple of information regarding the child process:\n"
9753" (pid, status)\n"
9754"\n"
9755"The options argument is ignored on Windows.");
9756
9757#define OS_WAITPID_METHODDEF \
9758 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009759
Barry Warsaw53699e91996-12-10 23:23:01 +00009760static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009761os_waitpid_impl(PyModuleDef *module, pid_t pid, int options);
9762
9763static PyObject *
9764os_waitpid(PyModuleDef *module, PyObject *args)
Guido van Rossum85e3b011991-06-03 12:42:10 +00009765{
Larry Hastings2f936352014-08-05 14:04:04 +10009766 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00009767 pid_t pid;
9768 int options;
Larry Hastings2f936352014-08-05 14:04:04 +10009769
9770 if (!PyArg_ParseTuple(args,
9771 "" _Py_PARSE_PID "i:waitpid",
9772 &pid, &options))
9773 goto exit;
9774 return_value = os_waitpid_impl(module, pid, options);
9775
9776exit:
9777 return return_value;
9778}
9779
9780static PyObject *
9781os_waitpid_impl(PyModuleDef *module, pid_t pid, int options)
9782/*[clinic end generated code: output=095a6b00af70b7ac input=0bf1666b8758fda3]*/
9783{
Victor Stinner8c62be82010-05-06 00:08:46 +00009784 WAIT_TYPE status;
9785 WAIT_STATUS_INT(status) = 0;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00009786
Victor Stinner8c62be82010-05-06 00:08:46 +00009787 Py_BEGIN_ALLOW_THREADS
9788 pid = waitpid(pid, &status, options);
9789 Py_END_ALLOW_THREADS
9790 if (pid == -1)
9791 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009792
Victor Stinner8c62be82010-05-06 00:08:46 +00009793 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum21803b81992-08-09 12:55:27 +00009794}
Tim Petersab034fa2002-02-01 11:27:43 +00009795#elif defined(HAVE_CWAIT)
Tim Petersab034fa2002-02-01 11:27:43 +00009796/* MS C has a variant of waitpid() that's usable for most purposes. */
Larry Hastings2f936352014-08-05 14:04:04 +10009797/*[clinic input]
9798os.waitpid
9799 pid: Py_intptr_t
9800 options: int
9801 /
9802
9803Wait for completion of a given process.
9804
9805Returns a tuple of information regarding the process:
9806 (pid, status << 8)
9807
9808The options argument is ignored on Windows.
9809[clinic start generated code]*/
9810
9811PyDoc_STRVAR(os_waitpid__doc__,
9812"waitpid($module, pid, options, /)\n"
9813"--\n"
9814"\n"
9815"Wait for completion of a given process.\n"
9816"\n"
9817"Returns a tuple of information regarding the process:\n"
9818" (pid, status << 8)\n"
9819"\n"
9820"The options argument is ignored on Windows.");
9821
9822#define OS_WAITPID_METHODDEF \
9823 {"waitpid", (PyCFunction)os_waitpid, METH_VARARGS, os_waitpid__doc__},
Tim Petersab034fa2002-02-01 11:27:43 +00009824
9825static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009826os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options);
Tim Petersab034fa2002-02-01 11:27:43 +00009827
Larry Hastings2f936352014-08-05 14:04:04 +10009828static PyObject *
9829os_waitpid(PyModuleDef *module, PyObject *args)
9830{
9831 PyObject *return_value = NULL;
9832 Py_intptr_t pid;
9833 int options;
9834
9835 if (!PyArg_ParseTuple(args,
9836 "" _Py_PARSE_INTPTR "i:waitpid",
9837 &pid, &options))
9838 goto exit;
9839 return_value = os_waitpid_impl(module, pid, options);
9840
9841exit:
9842 return return_value;
9843}
9844
9845static PyObject *
9846os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options)
9847/*[clinic end generated code: output=c20b95b15ad44a3a input=444c8f51cca5b862]*/
9848{
9849 int status;
9850
Victor Stinner8c62be82010-05-06 00:08:46 +00009851 Py_BEGIN_ALLOW_THREADS
9852 pid = _cwait(&status, pid, options);
9853 Py_END_ALLOW_THREADS
9854 if (pid == -1)
9855 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009856
Victor Stinner8c62be82010-05-06 00:08:46 +00009857 /* shift the status left a byte so this is more like the POSIX waitpid */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01009858 return Py_BuildValue(_Py_PARSE_INTPTR "i", pid, status << 8);
Tim Petersab034fa2002-02-01 11:27:43 +00009859}
Larry Hastings2f936352014-08-05 14:04:04 +10009860#endif
9861
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009862
Guido van Rossumad0ee831995-03-01 10:34:45 +00009863#ifdef HAVE_WAIT
Larry Hastings2f936352014-08-05 14:04:04 +10009864/*[clinic input]
9865os.wait
9866
9867Wait for completion of a child process.
9868
9869Returns a tuple of information about the child process:
9870 (pid, status)
9871[clinic start generated code]*/
9872
9873PyDoc_STRVAR(os_wait__doc__,
9874"wait($module, /)\n"
9875"--\n"
9876"\n"
9877"Wait for completion of a child process.\n"
9878"\n"
9879"Returns a tuple of information about the child process:\n"
9880" (pid, status)");
9881
9882#define OS_WAIT_METHODDEF \
9883 {"wait", (PyCFunction)os_wait, METH_NOARGS, os_wait__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009884
Barry Warsaw53699e91996-12-10 23:23:01 +00009885static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10009886os_wait_impl(PyModuleDef *module);
9887
9888static PyObject *
9889os_wait(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
9890{
9891 return os_wait_impl(module);
9892}
9893
9894static PyObject *
9895os_wait_impl(PyModuleDef *module)
9896/*[clinic end generated code: output=2a83a9d164e7e6a8 input=03b0182d4a4700ce]*/
Guido van Rossum21803b81992-08-09 12:55:27 +00009897{
Victor Stinner8c62be82010-05-06 00:08:46 +00009898 pid_t pid;
9899 WAIT_TYPE status;
9900 WAIT_STATUS_INT(status) = 0;
Neal Norwitze241ce82003-02-17 18:17:05 +00009901
Victor Stinner8c62be82010-05-06 00:08:46 +00009902 Py_BEGIN_ALLOW_THREADS
9903 pid = wait(&status);
9904 Py_END_ALLOW_THREADS
9905 if (pid == -1)
9906 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00009907
Victor Stinner8c62be82010-05-06 00:08:46 +00009908 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum85e3b011991-06-03 12:42:10 +00009909}
Larry Hastings2f936352014-08-05 14:04:04 +10009910#endif /* HAVE_WAIT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00009911
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009912
Larry Hastings9cf065c2012-06-22 16:30:09 -07009913#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
9914PyDoc_STRVAR(readlink__doc__,
9915"readlink(path, *, dir_fd=None) -> path\n\n\
9916Return a string representing the path to which the symbolic link points.\n\
9917\n\
9918If dir_fd is not None, it should be a file descriptor open to a directory,\n\
9919 and path should be relative; path will then be relative to that directory.\n\
9920dir_fd may not be implemented on your platform.\n\
9921 If it is unavailable, using it will raise a NotImplementedError.");
Mark Hammondc2e85bd2002-10-03 05:10:39 +00009922#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009923
Guido van Rossumb6775db1994-08-01 11:34:53 +00009924#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00009925
Larry Hastings2f936352014-08-05 14:04:04 +10009926/* AC 3.5: merge win32 and not together */
Barry Warsaw53699e91996-12-10 23:23:01 +00009927static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07009928posix_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009929{
Larry Hastings9cf065c2012-06-22 16:30:09 -07009930 path_t path;
9931 int dir_fd = DEFAULT_DIR_FD;
9932 char buffer[MAXPATHLEN];
9933 ssize_t length;
9934 PyObject *return_value = NULL;
9935 static char *keywords[] = {"path", "dir_fd", NULL};
Thomas Wouters89f507f2006-12-13 04:49:30 +00009936
Larry Hastings9cf065c2012-06-22 16:30:09 -07009937 memset(&path, 0, sizeof(path));
Victor Stinner292c8352012-10-30 02:17:38 +01009938 path.function_name = "readlink";
Larry Hastings9cf065c2012-06-22 16:30:09 -07009939 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O&|$O&:readlink", keywords,
9940 path_converter, &path,
Larry Hastings2f936352014-08-05 14:04:04 +10009941 READLINKAT_DIR_FD_CONVERTER, &dir_fd))
Victor Stinner8c62be82010-05-06 00:08:46 +00009942 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00009943
Victor Stinner8c62be82010-05-06 00:08:46 +00009944 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07009945#ifdef HAVE_READLINKAT
9946 if (dir_fd != DEFAULT_DIR_FD)
9947 length = readlinkat(dir_fd, path.narrow, buffer, sizeof(buffer));
Victor Stinnera45598a2010-05-14 16:35:39 +00009948 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07009949#endif
9950 length = readlink(path.narrow, buffer, sizeof(buffer));
9951 Py_END_ALLOW_THREADS
9952
9953 if (length < 0) {
Victor Stinner292c8352012-10-30 02:17:38 +01009954 return_value = path_error(&path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009955 goto exit;
9956 }
9957
9958 if (PyUnicode_Check(path.object))
9959 return_value = PyUnicode_DecodeFSDefaultAndSize(buffer, length);
9960 else
9961 return_value = PyBytes_FromStringAndSize(buffer, length);
9962exit:
9963 path_cleanup(&path);
9964 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009965}
Larry Hastings9cf065c2012-06-22 16:30:09 -07009966
Guido van Rossumb6775db1994-08-01 11:34:53 +00009967#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00009968
Larry Hastings2f936352014-08-05 14:04:04 +10009969#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
9970
9971static PyObject *
9972win_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
9973{
9974 wchar_t *path;
9975 DWORD n_bytes_returned;
9976 DWORD io_result;
9977 PyObject *po, *result;
9978 int dir_fd;
9979 HANDLE reparse_point_handle;
9980
9981 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
9982 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
9983 wchar_t *print_name;
9984
9985 static char *keywords[] = {"path", "dir_fd", NULL};
9986
9987 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "U|$O&:readlink", keywords,
9988 &po,
9989 dir_fd_unavailable, &dir_fd
9990 ))
9991 return NULL;
9992
9993 path = PyUnicode_AsUnicode(po);
9994 if (path == NULL)
9995 return NULL;
9996
9997 /* First get a handle to the reparse point */
9998 Py_BEGIN_ALLOW_THREADS
9999 reparse_point_handle = CreateFileW(
10000 path,
10001 0,
10002 0,
10003 0,
10004 OPEN_EXISTING,
10005 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS,
10006 0);
10007 Py_END_ALLOW_THREADS
10008
10009 if (reparse_point_handle==INVALID_HANDLE_VALUE)
10010 return win32_error_object("readlink", po);
10011
10012 Py_BEGIN_ALLOW_THREADS
10013 /* New call DeviceIoControl to read the reparse point */
10014 io_result = DeviceIoControl(
10015 reparse_point_handle,
10016 FSCTL_GET_REPARSE_POINT,
10017 0, 0, /* in buffer */
10018 target_buffer, sizeof(target_buffer),
10019 &n_bytes_returned,
10020 0 /* we're not using OVERLAPPED_IO */
10021 );
10022 CloseHandle(reparse_point_handle);
10023 Py_END_ALLOW_THREADS
10024
10025 if (io_result==0)
10026 return win32_error_object("readlink", po);
10027
10028 if (rdb->ReparseTag != IO_REPARSE_TAG_SYMLINK)
10029 {
10030 PyErr_SetString(PyExc_ValueError,
10031 "not a symbolic link");
10032 return NULL;
10033 }
10034 print_name = rdb->SymbolicLinkReparseBuffer.PathBuffer +
10035 rdb->SymbolicLinkReparseBuffer.PrintNameOffset;
10036
10037 result = PyUnicode_FromWideChar(print_name,
10038 rdb->SymbolicLinkReparseBuffer.PrintNameLength/2);
10039 return result;
10040}
10041
10042#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
10043
10044
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010045
Larry Hastings9cf065c2012-06-22 16:30:09 -070010046#ifdef HAVE_SYMLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070010047
10048#if defined(MS_WINDOWS)
10049
10050/* Grab CreateSymbolicLinkW dynamically from kernel32 */
10051static DWORD (CALLBACK *Py_CreateSymbolicLinkW)(LPWSTR, LPWSTR, DWORD) = NULL;
10052static DWORD (CALLBACK *Py_CreateSymbolicLinkA)(LPSTR, LPSTR, DWORD) = NULL;
Victor Stinner31b3b922013-06-05 01:49:17 +020010053
Larry Hastings9cf065c2012-06-22 16:30:09 -070010054static int
Victor Stinner31b3b922013-06-05 01:49:17 +020010055check_CreateSymbolicLink(void)
Larry Hastings9cf065c2012-06-22 16:30:09 -070010056{
10057 HINSTANCE hKernel32;
10058 /* only recheck */
10059 if (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA)
10060 return 1;
10061 hKernel32 = GetModuleHandleW(L"KERNEL32");
10062 *(FARPROC*)&Py_CreateSymbolicLinkW = GetProcAddress(hKernel32,
10063 "CreateSymbolicLinkW");
10064 *(FARPROC*)&Py_CreateSymbolicLinkA = GetProcAddress(hKernel32,
10065 "CreateSymbolicLinkA");
10066 return (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA);
10067}
10068
Victor Stinner31b3b922013-06-05 01:49:17 +020010069/* Remove the last portion of the path */
10070static void
10071_dirnameW(WCHAR *path)
10072{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010073 WCHAR *ptr;
10074
10075 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010076 for(ptr = path + wcslen(path); ptr != path; ptr--) {
Victor Stinner072318b2013-06-05 02:07:46 +020010077 if (*ptr == L'\\' || *ptr == L'/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010078 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010079 }
10080 *ptr = 0;
10081}
10082
Victor Stinner31b3b922013-06-05 01:49:17 +020010083/* Remove the last portion of the path */
10084static void
10085_dirnameA(char *path)
10086{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010087 char *ptr;
10088
10089 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +020010090 for(ptr = path + strlen(path); ptr != path; ptr--) {
10091 if (*ptr == '\\' || *ptr == '/')
Jason R. Coombs3a092862013-05-27 23:21:28 -040010092 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010093 }
10094 *ptr = 0;
10095}
10096
Victor Stinner31b3b922013-06-05 01:49:17 +020010097/* Is this path absolute? */
10098static int
10099_is_absW(const WCHAR *path)
10100{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010101 return path[0] == L'\\' || path[0] == L'/' || path[1] == L':';
10102
10103}
10104
Victor Stinner31b3b922013-06-05 01:49:17 +020010105/* Is this path absolute? */
10106static int
10107_is_absA(const char *path)
10108{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010109 return path[0] == '\\' || path[0] == '/' || path[1] == ':';
10110
10111}
10112
Victor Stinner31b3b922013-06-05 01:49:17 +020010113/* join root and rest with a backslash */
10114static void
10115_joinW(WCHAR *dest_path, const WCHAR *root, const WCHAR *rest)
10116{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010117 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010118
Victor Stinner31b3b922013-06-05 01:49:17 +020010119 if (_is_absW(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010120 wcscpy(dest_path, rest);
10121 return;
10122 }
10123
10124 root_len = wcslen(root);
10125
10126 wcscpy(dest_path, root);
10127 if(root_len) {
Victor Stinner31b3b922013-06-05 01:49:17 +020010128 dest_path[root_len] = L'\\';
10129 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010130 }
10131 wcscpy(dest_path+root_len, rest);
10132}
10133
Victor Stinner31b3b922013-06-05 01:49:17 +020010134/* join root and rest with a backslash */
10135static void
10136_joinA(char *dest_path, const char *root, const char *rest)
10137{
Victor Stinnere7e7eba2013-06-05 00:35:54 +020010138 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010139
Victor Stinner31b3b922013-06-05 01:49:17 +020010140 if (_is_absA(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010141 strcpy(dest_path, rest);
10142 return;
10143 }
10144
10145 root_len = strlen(root);
10146
10147 strcpy(dest_path, root);
10148 if(root_len) {
10149 dest_path[root_len] = '\\';
Victor Stinner31b3b922013-06-05 01:49:17 +020010150 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -040010151 }
10152 strcpy(dest_path+root_len, rest);
10153}
10154
Victor Stinner31b3b922013-06-05 01:49:17 +020010155/* Return True if the path at src relative to dest is a directory */
10156static int
10157_check_dirW(WCHAR *src, WCHAR *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010158{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010159 WIN32_FILE_ATTRIBUTE_DATA src_info;
10160 WCHAR dest_parent[MAX_PATH];
10161 WCHAR src_resolved[MAX_PATH] = L"";
10162
10163 /* dest_parent = os.path.dirname(dest) */
10164 wcscpy(dest_parent, dest);
10165 _dirnameW(dest_parent);
10166 /* src_resolved = os.path.join(dest_parent, src) */
10167 _joinW(src_resolved, dest_parent, src);
10168 return (
10169 GetFileAttributesExW(src_resolved, GetFileExInfoStandard, &src_info)
10170 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10171 );
10172}
10173
Victor Stinner31b3b922013-06-05 01:49:17 +020010174/* Return True if the path at src relative to dest is a directory */
10175static int
10176_check_dirA(char *src, char *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -040010177{
Jason R. Coombs3a092862013-05-27 23:21:28 -040010178 WIN32_FILE_ATTRIBUTE_DATA src_info;
10179 char dest_parent[MAX_PATH];
10180 char src_resolved[MAX_PATH] = "";
10181
10182 /* dest_parent = os.path.dirname(dest) */
10183 strcpy(dest_parent, dest);
Victor Stinner5a436762013-06-05 00:37:12 +020010184 _dirnameA(dest_parent);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010185 /* src_resolved = os.path.join(dest_parent, src) */
Victor Stinner5a436762013-06-05 00:37:12 +020010186 _joinA(src_resolved, dest_parent, src);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010187 return (
10188 GetFileAttributesExA(src_resolved, GetFileExInfoStandard, &src_info)
10189 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
10190 );
10191}
Larry Hastings9cf065c2012-06-22 16:30:09 -070010192#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010193
Larry Hastings2f936352014-08-05 14:04:04 +100010194
10195/*[clinic input]
10196os.symlink
10197 src: path_t
10198 dst: path_t
10199 target_is_directory: bool = False
10200 *
10201 dir_fd: dir_fd(requires='symlinkat')=None
10202
10203# "symlink(src, dst, target_is_directory=False, *, dir_fd=None)\n\n\
10204
10205Create a symbolic link pointing to src named dst.
10206
10207target_is_directory is required on Windows if the target is to be
10208 interpreted as a directory. (On Windows, symlink requires
10209 Windows 6.0 or greater, and raises a NotImplementedError otherwise.)
10210 target_is_directory is ignored on non-Windows platforms.
10211
10212If dir_fd is not None, it should be a file descriptor open to a directory,
10213 and path should be relative; path will then be relative to that directory.
10214dir_fd may not be implemented on your platform.
10215 If it is unavailable, using it will raise a NotImplementedError.
10216
10217[clinic start generated code]*/
10218
10219PyDoc_STRVAR(os_symlink__doc__,
10220"symlink($module, /, src, dst, target_is_directory=False, *, dir_fd=None)\n"
10221"--\n"
10222"\n"
10223"Create a symbolic link pointing to src named dst.\n"
10224"\n"
10225"target_is_directory is required on Windows if the target is to be\n"
10226" interpreted as a directory. (On Windows, symlink requires\n"
10227" Windows 6.0 or greater, and raises a NotImplementedError otherwise.)\n"
10228" target_is_directory is ignored on non-Windows platforms.\n"
10229"\n"
10230"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10231" and path should be relative; path will then be relative to that directory.\n"
10232"dir_fd may not be implemented on your platform.\n"
10233" If it is unavailable, using it will raise a NotImplementedError.");
10234
10235#define OS_SYMLINK_METHODDEF \
10236 {"symlink", (PyCFunction)os_symlink, METH_VARARGS|METH_KEYWORDS, os_symlink__doc__},
10237
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010238static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010239os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd);
10240
10241static PyObject *
10242os_symlink(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010243{
Larry Hastings2f936352014-08-05 14:04:04 +100010244 PyObject *return_value = NULL;
10245 static char *_keywords[] = {"src", "dst", "target_is_directory", "dir_fd", NULL};
10246 path_t src = PATH_T_INITIALIZE("symlink", "src", 0, 0);
10247 path_t dst = PATH_T_INITIALIZE("symlink", "dst", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010248 int target_is_directory = 0;
Larry Hastings2f936352014-08-05 14:04:04 +100010249 int dir_fd = DEFAULT_DIR_FD;
10250
10251 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10252 "O&O&|p$O&:symlink", _keywords,
10253 path_converter, &src, path_converter, &dst, &target_is_directory, SYMLINKAT_DIR_FD_CONVERTER, &dir_fd))
10254 goto exit;
10255 return_value = os_symlink_impl(module, &src, &dst, target_is_directory, dir_fd);
10256
10257exit:
10258 /* Cleanup for src */
10259 path_cleanup(&src);
10260 /* Cleanup for dst */
10261 path_cleanup(&dst);
10262
10263 return return_value;
10264}
10265
10266static PyObject *
10267os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst, int target_is_directory, int dir_fd)
10268/*[clinic end generated code: output=1a31e6d88aafe9b6 input=e820ec4472547bc3]*/
10269{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010270#ifdef MS_WINDOWS
10271 DWORD result;
10272#else
10273 int result;
10274#endif
10275
Larry Hastings9cf065c2012-06-22 16:30:09 -070010276#ifdef MS_WINDOWS
10277 if (!check_CreateSymbolicLink()) {
10278 PyErr_SetString(PyExc_NotImplementedError,
10279 "CreateSymbolicLink functions not found");
Larry Hastings2f936352014-08-05 14:04:04 +100010280 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010281 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010282 if (!win32_can_symlink) {
10283 PyErr_SetString(PyExc_OSError, "symbolic link privilege not held");
Larry Hastings2f936352014-08-05 14:04:04 +100010284 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +030010285 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010286#endif
10287
Larry Hastings2f936352014-08-05 14:04:04 +100010288 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070010289 PyErr_SetString(PyExc_ValueError,
10290 "symlink: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +100010291 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010292 }
10293
10294#ifdef MS_WINDOWS
Jason R. Coombs3a092862013-05-27 23:21:28 -040010295
Larry Hastings9cf065c2012-06-22 16:30:09 -070010296 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010297 if (dst->wide) {
Jason R. Coombs3a092862013-05-27 23:21:28 -040010298 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010299 target_is_directory |= _check_dirW(src->wide, dst->wide);
10300 result = Py_CreateSymbolicLinkW(dst->wide, src->wide,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010301 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010302 }
10303 else {
10304 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +100010305 target_is_directory |= _check_dirA(src->narrow, dst->narrow);
10306 result = Py_CreateSymbolicLinkA(dst->narrow, src->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -070010307 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -040010308 }
Larry Hastings9cf065c2012-06-22 16:30:09 -070010309 Py_END_ALLOW_THREADS
10310
Larry Hastings2f936352014-08-05 14:04:04 +100010311 if (!result)
10312 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010313
10314#else
10315
10316 Py_BEGIN_ALLOW_THREADS
10317#if HAVE_SYMLINKAT
10318 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010319 result = symlinkat(src->narrow, dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010320 else
10321#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010322 result = symlink(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010323 Py_END_ALLOW_THREADS
10324
Larry Hastings2f936352014-08-05 14:04:04 +100010325 if (result)
10326 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010327#endif
10328
Larry Hastings2f936352014-08-05 14:04:04 +100010329 Py_RETURN_NONE;
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010330}
10331#endif /* HAVE_SYMLINK */
10332
Larry Hastings9cf065c2012-06-22 16:30:09 -070010333
Brian Curtind40e6f72010-07-08 21:39:08 +000010334
Guido van Rossumbfaf3d61997-12-29 20:02:27 +000010335
Larry Hastings605a62d2012-06-24 04:33:36 -070010336static PyStructSequence_Field times_result_fields[] = {
10337 {"user", "user time"},
10338 {"system", "system time"},
10339 {"children_user", "user time of children"},
10340 {"children_system", "system time of children"},
10341 {"elapsed", "elapsed time since an arbitrary point in the past"},
10342 {NULL}
10343};
10344
10345PyDoc_STRVAR(times_result__doc__,
10346"times_result: Result from os.times().\n\n\
10347This object may be accessed either as a tuple of\n\
10348 (user, system, children_user, children_system, elapsed),\n\
10349or via the attributes user, system, children_user, children_system,\n\
10350and elapsed.\n\
10351\n\
10352See os.times for more information.");
10353
10354static PyStructSequence_Desc times_result_desc = {
10355 "times_result", /* name */
10356 times_result__doc__, /* doc */
10357 times_result_fields,
10358 5
10359};
10360
10361static PyTypeObject TimesResultType;
10362
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010363#ifdef MS_WINDOWS
10364#define HAVE_TIMES /* mandatory, for the method table */
10365#endif
Larry Hastings605a62d2012-06-24 04:33:36 -070010366
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010367#ifdef HAVE_TIMES
Larry Hastings605a62d2012-06-24 04:33:36 -070010368
10369static PyObject *
10370build_times_result(double user, double system,
10371 double children_user, double children_system,
10372 double elapsed)
10373{
10374 PyObject *value = PyStructSequence_New(&TimesResultType);
10375 if (value == NULL)
10376 return NULL;
10377
10378#define SET(i, field) \
10379 { \
10380 PyObject *o = PyFloat_FromDouble(field); \
10381 if (!o) { \
10382 Py_DECREF(value); \
10383 return NULL; \
10384 } \
10385 PyStructSequence_SET_ITEM(value, i, o); \
10386 } \
10387
10388 SET(0, user);
10389 SET(1, system);
10390 SET(2, children_user);
10391 SET(3, children_system);
10392 SET(4, elapsed);
10393
10394#undef SET
10395
10396 return value;
10397}
10398
Larry Hastings605a62d2012-06-24 04:33:36 -070010399
Larry Hastings2f936352014-08-05 14:04:04 +100010400#ifndef MS_WINDOWS
10401#define NEED_TICKS_PER_SECOND
10402static long ticks_per_second = -1;
10403#endif /* MS_WINDOWS */
10404
10405/*[clinic input]
10406os.times
10407
10408Return a collection containing process timing information.
10409
10410The object returned behaves like a named tuple with these fields:
10411 (utime, stime, cutime, cstime, elapsed_time)
10412All fields are floating point numbers.
10413[clinic start generated code]*/
10414
10415PyDoc_STRVAR(os_times__doc__,
10416"times($module, /)\n"
10417"--\n"
10418"\n"
10419"Return a collection containing process timing information.\n"
10420"\n"
10421"The object returned behaves like a named tuple with these fields:\n"
10422" (utime, stime, cutime, cstime, elapsed_time)\n"
10423"All fields are floating point numbers.");
10424
10425#define OS_TIMES_METHODDEF \
10426 {"times", (PyCFunction)os_times, METH_NOARGS, os_times__doc__},
10427
Barry Warsaw53699e91996-12-10 23:23:01 +000010428static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010429os_times_impl(PyModuleDef *module);
10430
10431static PyObject *
10432os_times(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10433{
10434 return os_times_impl(module);
10435}
10436
10437static PyObject *
10438os_times_impl(PyModuleDef *module)
10439/*[clinic end generated code: output=b86896d031a9b768 input=2bf9df3d6ab2e48b]*/
10440#ifdef MS_WINDOWS
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010441{
Victor Stinner8c62be82010-05-06 00:08:46 +000010442 FILETIME create, exit, kernel, user;
10443 HANDLE hProc;
10444 hProc = GetCurrentProcess();
10445 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
10446 /* The fields of a FILETIME structure are the hi and lo part
10447 of a 64-bit value expressed in 100 nanosecond units.
10448 1e7 is one second in such units; 1e-7 the inverse.
10449 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
10450 */
Larry Hastings605a62d2012-06-24 04:33:36 -070010451 return build_times_result(
Victor Stinner8c62be82010-05-06 00:08:46 +000010452 (double)(user.dwHighDateTime*429.4967296 +
10453 user.dwLowDateTime*1e-7),
10454 (double)(kernel.dwHighDateTime*429.4967296 +
10455 kernel.dwLowDateTime*1e-7),
10456 (double)0,
10457 (double)0,
10458 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +000010459}
Larry Hastings2f936352014-08-05 14:04:04 +100010460#else /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010461{
Larry Hastings2f936352014-08-05 14:04:04 +100010462
10463
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010464 struct tms t;
10465 clock_t c;
10466 errno = 0;
10467 c = times(&t);
10468 if (c == (clock_t) -1)
10469 return posix_error();
10470 return build_times_result(
10471 (double)t.tms_utime / ticks_per_second,
10472 (double)t.tms_stime / ticks_per_second,
10473 (double)t.tms_cutime / ticks_per_second,
10474 (double)t.tms_cstime / ticks_per_second,
10475 (double)c / ticks_per_second);
10476}
Larry Hastings2f936352014-08-05 14:04:04 +100010477#endif /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +020010478#endif /* HAVE_TIMES */
10479
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010480
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010481#ifdef HAVE_GETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010482/*[clinic input]
10483os.getsid
10484
10485 pid: pid_t
10486 /
10487
10488Call the system call getsid(pid) and return the result.
10489[clinic start generated code]*/
10490
10491PyDoc_STRVAR(os_getsid__doc__,
10492"getsid($module, pid, /)\n"
10493"--\n"
10494"\n"
10495"Call the system call getsid(pid) and return the result.");
10496
10497#define OS_GETSID_METHODDEF \
10498 {"getsid", (PyCFunction)os_getsid, METH_VARARGS, os_getsid__doc__},
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010499
10500static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010501os_getsid_impl(PyModuleDef *module, pid_t pid);
10502
10503static PyObject *
10504os_getsid(PyModuleDef *module, PyObject *args)
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010505{
Larry Hastings2f936352014-08-05 14:04:04 +100010506 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010507 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010508
10509 if (!PyArg_ParseTuple(args,
10510 "" _Py_PARSE_PID ":getsid",
10511 &pid))
10512 goto exit;
10513 return_value = os_getsid_impl(module, pid);
10514
10515exit:
10516 return return_value;
10517}
10518
10519static PyObject *
10520os_getsid_impl(PyModuleDef *module, pid_t pid)
10521/*[clinic end generated code: output=ea8390f395f4e0e1 input=eeb2b923a30ce04e]*/
10522{
Victor Stinner8c62be82010-05-06 00:08:46 +000010523 int sid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010524 sid = getsid(pid);
10525 if (sid < 0)
10526 return posix_error();
10527 return PyLong_FromLong((long)sid);
Martin v. Löwis49ee14d2003-11-10 06:35:36 +000010528}
10529#endif /* HAVE_GETSID */
10530
10531
Guido van Rossumb6775db1994-08-01 11:34:53 +000010532#ifdef HAVE_SETSID
Larry Hastings2f936352014-08-05 14:04:04 +100010533/*[clinic input]
10534os.setsid
10535
10536Call the system call setsid().
10537[clinic start generated code]*/
10538
10539PyDoc_STRVAR(os_setsid__doc__,
10540"setsid($module, /)\n"
10541"--\n"
10542"\n"
10543"Call the system call setsid().");
10544
10545#define OS_SETSID_METHODDEF \
10546 {"setsid", (PyCFunction)os_setsid, METH_NOARGS, os_setsid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010547
Barry Warsaw53699e91996-12-10 23:23:01 +000010548static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010549os_setsid_impl(PyModuleDef *module);
10550
10551static PyObject *
10552os_setsid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
10553{
10554 return os_setsid_impl(module);
10555}
10556
10557static PyObject *
10558os_setsid_impl(PyModuleDef *module)
10559/*[clinic end generated code: output=2a9a1435d8d764d5 input=5fff45858e2f0776]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +000010560{
Victor Stinner8c62be82010-05-06 00:08:46 +000010561 if (setsid() < 0)
10562 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010563 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010564}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010565#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010566
Larry Hastings2f936352014-08-05 14:04:04 +100010567
Guido van Rossumb6775db1994-08-01 11:34:53 +000010568#ifdef HAVE_SETPGID
Larry Hastings2f936352014-08-05 14:04:04 +100010569/*[clinic input]
10570os.setpgid
10571
10572 pid: pid_t
10573 pgrp: pid_t
10574 /
10575
10576Call the system call setpgid(pid, pgrp).
10577[clinic start generated code]*/
10578
10579PyDoc_STRVAR(os_setpgid__doc__,
10580"setpgid($module, pid, pgrp, /)\n"
10581"--\n"
10582"\n"
10583"Call the system call setpgid(pid, pgrp).");
10584
10585#define OS_SETPGID_METHODDEF \
10586 {"setpgid", (PyCFunction)os_setpgid, METH_VARARGS, os_setpgid__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010587
Barry Warsaw53699e91996-12-10 23:23:01 +000010588static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010589os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp);
10590
10591static PyObject *
10592os_setpgid(PyModuleDef *module, PyObject *args)
Guido van Rossumc2670a01992-09-13 20:07:29 +000010593{
Larry Hastings2f936352014-08-05 14:04:04 +100010594 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010595 pid_t pid;
Larry Hastings2f936352014-08-05 14:04:04 +100010596 pid_t pgrp;
10597
10598 if (!PyArg_ParseTuple(args,
10599 "" _Py_PARSE_PID "" _Py_PARSE_PID ":setpgid",
10600 &pid, &pgrp))
10601 goto exit;
10602 return_value = os_setpgid_impl(module, pid, pgrp);
10603
10604exit:
10605 return return_value;
10606}
10607
10608static PyObject *
10609os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp)
10610/*[clinic end generated code: output=7ad79b725f890e1f input=fceb395eca572e1a]*/
10611{
Victor Stinner8c62be82010-05-06 00:08:46 +000010612 if (setpgid(pid, pgrp) < 0)
10613 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010614 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +000010615}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010616#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +000010617
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010618
Guido van Rossumb6775db1994-08-01 11:34:53 +000010619#ifdef HAVE_TCGETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010620/*[clinic input]
10621os.tcgetpgrp
10622
10623 fd: int
10624 /
10625
10626Return the process group associated with the terminal specified by fd.
10627[clinic start generated code]*/
10628
10629PyDoc_STRVAR(os_tcgetpgrp__doc__,
10630"tcgetpgrp($module, fd, /)\n"
10631"--\n"
10632"\n"
10633"Return the process group associated with the terminal specified by fd.");
10634
10635#define OS_TCGETPGRP_METHODDEF \
10636 {"tcgetpgrp", (PyCFunction)os_tcgetpgrp, METH_VARARGS, os_tcgetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010637
Barry Warsaw53699e91996-12-10 23:23:01 +000010638static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010639os_tcgetpgrp_impl(PyModuleDef *module, int fd);
10640
10641static PyObject *
10642os_tcgetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010643{
Larry Hastings2f936352014-08-05 14:04:04 +100010644 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010645 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100010646
10647 if (!PyArg_ParseTuple(args,
10648 "i:tcgetpgrp",
10649 &fd))
10650 goto exit;
10651 return_value = os_tcgetpgrp_impl(module, fd);
10652
10653exit:
10654 return return_value;
10655}
10656
10657static PyObject *
10658os_tcgetpgrp_impl(PyModuleDef *module, int fd)
10659/*[clinic end generated code: output=abcf52ed4c8d22cb input=7f6c18eac10ada86]*/
10660{
10661 pid_t pgid = tcgetpgrp(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +000010662 if (pgid < 0)
10663 return posix_error();
10664 return PyLong_FromPid(pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +000010665}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010666#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +000010667
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010668
Guido van Rossumb6775db1994-08-01 11:34:53 +000010669#ifdef HAVE_TCSETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +100010670/*[clinic input]
10671os.tcsetpgrp
10672
10673 fd: int
10674 pgid: pid_t
10675 /
10676
10677Set the process group associated with the terminal specified by fd.
10678[clinic start generated code]*/
10679
10680PyDoc_STRVAR(os_tcsetpgrp__doc__,
10681"tcsetpgrp($module, fd, pgid, /)\n"
10682"--\n"
10683"\n"
10684"Set the process group associated with the terminal specified by fd.");
10685
10686#define OS_TCSETPGRP_METHODDEF \
10687 {"tcsetpgrp", (PyCFunction)os_tcsetpgrp, METH_VARARGS, os_tcsetpgrp__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010688
Barry Warsaw53699e91996-12-10 23:23:01 +000010689static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010690os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid);
10691
10692static PyObject *
10693os_tcsetpgrp(PyModuleDef *module, PyObject *args)
Guido van Rossum7066dd71992-09-17 17:54:56 +000010694{
Larry Hastings2f936352014-08-05 14:04:04 +100010695 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010696 int fd;
10697 pid_t pgid;
Larry Hastings2f936352014-08-05 14:04:04 +100010698
10699 if (!PyArg_ParseTuple(args,
10700 "i" _Py_PARSE_PID ":tcsetpgrp",
10701 &fd, &pgid))
10702 goto exit;
10703 return_value = os_tcsetpgrp_impl(module, fd, pgid);
10704
10705exit:
10706 return return_value;
10707}
10708
10709static PyObject *
10710os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid)
10711/*[clinic end generated code: output=76f9bb8fd00f20f5 input=5bdc997c6a619020]*/
10712{
Victor Stinner8c62be82010-05-06 00:08:46 +000010713 if (tcsetpgrp(fd, pgid) < 0)
10714 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010715 Py_RETURN_NONE;
Guido van Rossum7066dd71992-09-17 17:54:56 +000010716}
Guido van Rossumb6775db1994-08-01 11:34:53 +000010717#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +000010718
Guido van Rossum687dd131993-05-17 08:34:16 +000010719/* Functions acting on file descriptors */
10720
Victor Stinnerdaf45552013-08-28 00:53:59 +020010721#ifdef O_CLOEXEC
10722extern int _Py_open_cloexec_works;
10723#endif
10724
Larry Hastings2f936352014-08-05 14:04:04 +100010725
10726/*[clinic input]
10727os.open -> int
10728 path: path_t
10729 flags: int
10730 mode: int = 0o777
10731 *
10732 dir_fd: dir_fd(requires='openat') = None
10733
10734# "open(path, flags, mode=0o777, *, dir_fd=None)\n\n\
10735
10736Open a file for low level IO. Returns a file descriptor (integer).
10737
10738If dir_fd is not None, it should be a file descriptor open to a directory,
10739 and path should be relative; path will then be relative to that directory.
10740dir_fd may not be implemented on your platform.
10741 If it is unavailable, using it will raise a NotImplementedError.
10742[clinic start generated code]*/
10743
10744PyDoc_STRVAR(os_open__doc__,
10745"open($module, /, path, flags, mode=511, *, dir_fd=None)\n"
10746"--\n"
10747"\n"
10748"Open a file for low level IO. Returns a file descriptor (integer).\n"
10749"\n"
10750"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
10751" and path should be relative; path will then be relative to that directory.\n"
10752"dir_fd may not be implemented on your platform.\n"
10753" If it is unavailable, using it will raise a NotImplementedError.");
10754
10755#define OS_OPEN_METHODDEF \
10756 {"open", (PyCFunction)os_open, METH_VARARGS|METH_KEYWORDS, os_open__doc__},
10757
10758static int
10759os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010760
Barry Warsaw53699e91996-12-10 23:23:01 +000010761static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010762os_open(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000010763{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010764 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100010765 static char *_keywords[] = {"path", "flags", "mode", "dir_fd", NULL};
10766 path_t path = PATH_T_INITIALIZE("open", "path", 0, 0);
10767 int flags;
10768 int mode = 511;
10769 int dir_fd = DEFAULT_DIR_FD;
10770 int _return_value;
10771
10772 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10773 "O&i|i$O&:open", _keywords,
10774 path_converter, &path, &flags, &mode, OPENAT_DIR_FD_CONVERTER, &dir_fd))
10775 goto exit;
10776 _return_value = os_open_impl(module, &path, flags, mode, dir_fd);
10777 if ((_return_value == -1) && PyErr_Occurred())
10778 goto exit;
10779 return_value = PyLong_FromLong((long)_return_value);
10780
10781exit:
10782 /* Cleanup for path */
10783 path_cleanup(&path);
10784
10785 return return_value;
10786}
10787
10788static int
10789os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode, int dir_fd)
10790/*[clinic end generated code: output=05b68fc4ed5e29c9 input=ad8623b29acd2934]*/
10791{
10792 int fd;
10793
Victor Stinnerdaf45552013-08-28 00:53:59 +020010794#ifdef O_CLOEXEC
10795 int *atomic_flag_works = &_Py_open_cloexec_works;
10796#elif !defined(MS_WINDOWS)
10797 int *atomic_flag_works = NULL;
10798#endif
Mark Hammondc2e85bd2002-10-03 05:10:39 +000010799
Victor Stinnerdaf45552013-08-28 00:53:59 +020010800#ifdef MS_WINDOWS
10801 flags |= O_NOINHERIT;
10802#elif defined(O_CLOEXEC)
10803 flags |= O_CLOEXEC;
10804#endif
10805
Victor Stinner8c62be82010-05-06 00:08:46 +000010806 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -070010807#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100010808 if (path->wide)
10809 fd = _wopen(path->wide, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010810 else
10811#endif
10812#ifdef HAVE_OPENAT
10813 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +100010814 fd = openat(dir_fd, path->narrow, flags, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010815 else
10816#endif
Larry Hastings2f936352014-08-05 14:04:04 +100010817 fd = open(path->narrow, flags, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +000010818 Py_END_ALLOW_THREADS
Guido van Rossum687dd131993-05-17 08:34:16 +000010819
Larry Hastings9cf065c2012-06-22 16:30:09 -070010820 if (fd == -1) {
Larry Hastings2f936352014-08-05 14:04:04 +100010821 PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
10822 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010823 }
10824
Victor Stinnerdaf45552013-08-28 00:53:59 +020010825#ifndef MS_WINDOWS
10826 if (_Py_set_inheritable(fd, 0, atomic_flag_works) < 0) {
10827 close(fd);
Larry Hastings2f936352014-08-05 14:04:04 +100010828 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020010829 }
10830#endif
10831
Larry Hastings2f936352014-08-05 14:04:04 +100010832 return fd;
10833}
10834
10835
10836/*[clinic input]
10837os.close
10838
10839 fd: int
10840
10841Close a file descriptor.
10842[clinic start generated code]*/
10843
10844PyDoc_STRVAR(os_close__doc__,
10845"close($module, /, fd)\n"
10846"--\n"
10847"\n"
10848"Close a file descriptor.");
10849
10850#define OS_CLOSE_METHODDEF \
10851 {"close", (PyCFunction)os_close, METH_VARARGS|METH_KEYWORDS, os_close__doc__},
10852
10853static PyObject *
10854os_close_impl(PyModuleDef *module, int fd);
10855
10856static PyObject *
10857os_close(PyModuleDef *module, PyObject *args, PyObject *kwargs)
10858{
10859 PyObject *return_value = NULL;
10860 static char *_keywords[] = {"fd", NULL};
10861 int fd;
10862
10863 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
10864 "i:close", _keywords,
10865 &fd))
10866 goto exit;
10867 return_value = os_close_impl(module, fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010868
10869exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070010870 return return_value;
10871}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010872
Barry Warsaw53699e91996-12-10 23:23:01 +000010873static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010874os_close_impl(PyModuleDef *module, int fd)
10875/*[clinic end generated code: output=927004e29ad55808 input=2bc42451ca5c3223]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000010876{
Larry Hastings2f936352014-08-05 14:04:04 +100010877 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +000010878 if (!_PyVerify_fd(fd))
10879 return posix_error();
10880 Py_BEGIN_ALLOW_THREADS
10881 res = close(fd);
10882 Py_END_ALLOW_THREADS
10883 if (res < 0)
10884 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +100010885 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000010886}
10887
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010888
Larry Hastings2f936352014-08-05 14:04:04 +100010889/*[clinic input]
10890os.closerange
10891
10892 fd_low: int
10893 fd_high: int
10894 /
10895
10896Closes all file descriptors in [fd_low, fd_high), ignoring errors.
10897[clinic start generated code]*/
10898
10899PyDoc_STRVAR(os_closerange__doc__,
10900"closerange($module, fd_low, fd_high, /)\n"
10901"--\n"
10902"\n"
10903"Closes all file descriptors in [fd_low, fd_high), ignoring errors.");
10904
10905#define OS_CLOSERANGE_METHODDEF \
10906 {"closerange", (PyCFunction)os_closerange, METH_VARARGS, os_closerange__doc__},
Christian Heimesfdab48e2008-01-20 09:06:41 +000010907
10908static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010909os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high);
10910
10911static PyObject *
10912os_closerange(PyModuleDef *module, PyObject *args)
Christian Heimesfdab48e2008-01-20 09:06:41 +000010913{
Larry Hastings2f936352014-08-05 14:04:04 +100010914 PyObject *return_value = NULL;
10915 int fd_low;
10916 int fd_high;
10917
10918 if (!PyArg_ParseTuple(args,
10919 "ii:closerange",
10920 &fd_low, &fd_high))
10921 goto exit;
10922 return_value = os_closerange_impl(module, fd_low, fd_high);
10923
10924exit:
10925 return return_value;
10926}
10927
10928static PyObject *
10929os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high)
10930/*[clinic end generated code: output=0a929ece386811c3 input=5855a3d053ebd4ec]*/
10931{
10932 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +000010933 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100010934 for (i = fd_low; i < fd_high; i++)
Victor Stinner8c62be82010-05-06 00:08:46 +000010935 if (_PyVerify_fd(i))
10936 close(i);
10937 Py_END_ALLOW_THREADS
10938 Py_RETURN_NONE;
Christian Heimesfdab48e2008-01-20 09:06:41 +000010939}
10940
10941
Larry Hastings2f936352014-08-05 14:04:04 +100010942/*[clinic input]
10943os.dup -> int
10944
10945 fd: int
10946 /
10947
10948Return a duplicate of a file descriptor.
10949[clinic start generated code]*/
10950
10951PyDoc_STRVAR(os_dup__doc__,
10952"dup($module, fd, /)\n"
10953"--\n"
10954"\n"
10955"Return a duplicate of a file descriptor.");
10956
10957#define OS_DUP_METHODDEF \
10958 {"dup", (PyCFunction)os_dup, METH_VARARGS, os_dup__doc__},
10959
10960static int
10961os_dup_impl(PyModuleDef *module, int fd);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010962
Barry Warsaw53699e91996-12-10 23:23:01 +000010963static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100010964os_dup(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000010965{
Larry Hastings2f936352014-08-05 14:04:04 +100010966 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010967 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100010968 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020010969
Larry Hastings2f936352014-08-05 14:04:04 +100010970 if (!PyArg_ParseTuple(args,
10971 "i:dup",
10972 &fd))
10973 goto exit;
10974 _return_value = os_dup_impl(module, fd);
10975 if ((_return_value == -1) && PyErr_Occurred())
10976 goto exit;
10977 return_value = PyLong_FromLong((long)_return_value);
Tim Golden23005082013-10-25 11:22:37 +010010978
Larry Hastings2f936352014-08-05 14:04:04 +100010979exit:
10980 return return_value;
10981}
Victor Stinnerdaf45552013-08-28 00:53:59 +020010982
Larry Hastings2f936352014-08-05 14:04:04 +100010983static int
10984os_dup_impl(PyModuleDef *module, int fd)
10985/*[clinic end generated code: output=75943e057b25e1bd input=6f10f7ea97f7852a]*/
10986{
10987 return _Py_dup(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +000010988}
10989
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000010990
Larry Hastings2f936352014-08-05 14:04:04 +100010991/*[clinic input]
10992os.dup2
10993 fd: int
10994 fd2: int
10995 inheritable: bool=True
10996
10997Duplicate file descriptor.
10998[clinic start generated code]*/
10999
11000PyDoc_STRVAR(os_dup2__doc__,
11001"dup2($module, /, fd, fd2, inheritable=True)\n"
11002"--\n"
11003"\n"
11004"Duplicate file descriptor.");
11005
11006#define OS_DUP2_METHODDEF \
11007 {"dup2", (PyCFunction)os_dup2, METH_VARARGS|METH_KEYWORDS, os_dup2__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011008
Barry Warsaw53699e91996-12-10 23:23:01 +000011009static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011010os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable);
11011
11012static PyObject *
11013os_dup2(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011014{
Larry Hastings2f936352014-08-05 14:04:04 +100011015 PyObject *return_value = NULL;
11016 static char *_keywords[] = {"fd", "fd2", "inheritable", NULL};
11017 int fd;
11018 int fd2;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011019 int inheritable = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100011020
11021 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11022 "ii|p:dup2", _keywords,
11023 &fd, &fd2, &inheritable))
11024 goto exit;
11025 return_value = os_dup2_impl(module, fd, fd2, inheritable);
11026
11027exit:
11028 return return_value;
11029}
11030
11031static PyObject *
11032os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable)
11033/*[clinic end generated code: output=531e482dd11a99a0 input=76e96f511be0352f]*/
11034{
Victor Stinnerdaf45552013-08-28 00:53:59 +020011035 int res;
11036#if defined(HAVE_DUP3) && \
11037 !(defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC))
11038 /* dup3() is available on Linux 2.6.27+ and glibc 2.9 */
11039 int dup3_works = -1;
11040#endif
11041
Victor Stinner8c62be82010-05-06 00:08:46 +000011042 if (!_PyVerify_fd_dup2(fd, fd2))
11043 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011044
11045#ifdef MS_WINDOWS
11046 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011047 res = dup2(fd, fd2);
Victor Stinnerdaf45552013-08-28 00:53:59 +020011048 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000011049 if (res < 0)
11050 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +020011051
11052 /* Character files like console cannot be make non-inheritable */
11053 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11054 close(fd2);
11055 return NULL;
11056 }
11057
11058#elif defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC)
11059 Py_BEGIN_ALLOW_THREADS
11060 if (!inheritable)
11061 res = fcntl(fd, F_DUP2FD_CLOEXEC, fd2);
11062 else
11063 res = dup2(fd, fd2);
11064 Py_END_ALLOW_THREADS
11065 if (res < 0)
11066 return posix_error();
11067
11068#else
11069
11070#ifdef HAVE_DUP3
11071 if (!inheritable && dup3_works != 0) {
11072 Py_BEGIN_ALLOW_THREADS
11073 res = dup3(fd, fd2, O_CLOEXEC);
11074 Py_END_ALLOW_THREADS
11075 if (res < 0) {
11076 if (dup3_works == -1)
11077 dup3_works = (errno != ENOSYS);
11078 if (dup3_works)
11079 return posix_error();
11080 }
11081 }
11082
11083 if (inheritable || dup3_works == 0)
11084 {
11085#endif
11086 Py_BEGIN_ALLOW_THREADS
11087 res = dup2(fd, fd2);
11088 Py_END_ALLOW_THREADS
11089 if (res < 0)
11090 return posix_error();
11091
11092 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
11093 close(fd2);
11094 return NULL;
11095 }
11096#ifdef HAVE_DUP3
11097 }
11098#endif
11099
11100#endif
11101
Larry Hastings2f936352014-08-05 14:04:04 +100011102 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +000011103}
11104
Larry Hastings2f936352014-08-05 14:04:04 +100011105
Ross Lagerwall7807c352011-03-17 20:20:30 +020011106#ifdef HAVE_LOCKF
Larry Hastings2f936352014-08-05 14:04:04 +100011107/*[clinic input]
11108os.lockf
11109
11110 fd: int
11111 An open file descriptor.
11112 command: int
11113 One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.
11114 length: Py_off_t
11115 The number of bytes to lock, starting at the current position.
11116 /
11117
11118Apply, test or remove a POSIX lock on an open file descriptor.
11119
11120[clinic start generated code]*/
11121
11122PyDoc_STRVAR(os_lockf__doc__,
11123"lockf($module, fd, command, length, /)\n"
11124"--\n"
11125"\n"
11126"Apply, test or remove a POSIX lock on an open file descriptor.\n"
11127"\n"
11128" fd\n"
11129" An open file descriptor.\n"
11130" command\n"
11131" One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.\n"
11132" length\n"
11133" The number of bytes to lock, starting at the current position.");
11134
11135#define OS_LOCKF_METHODDEF \
11136 {"lockf", (PyCFunction)os_lockf, METH_VARARGS, os_lockf__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011137
11138static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011139os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length);
11140
11141static PyObject *
11142os_lockf(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011143{
Larry Hastings2f936352014-08-05 14:04:04 +100011144 PyObject *return_value = NULL;
11145 int fd;
11146 int command;
11147 Py_off_t length;
11148
11149 if (!PyArg_ParseTuple(args,
11150 "iiO&:lockf",
11151 &fd, &command, Py_off_t_converter, &length))
11152 goto exit;
11153 return_value = os_lockf_impl(module, fd, command, length);
11154
11155exit:
11156 return return_value;
11157}
11158
11159static PyObject *
11160os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length)
11161/*[clinic end generated code: output=1b28346ac7335c0f input=65da41d2106e9b79]*/
11162{
11163 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011164
11165 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011166 res = lockf(fd, command, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011167 Py_END_ALLOW_THREADS
11168
11169 if (res < 0)
11170 return posix_error();
11171
11172 Py_RETURN_NONE;
11173}
Larry Hastings2f936352014-08-05 14:04:04 +100011174#endif /* HAVE_LOCKF */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011175
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011176
Larry Hastings2f936352014-08-05 14:04:04 +100011177/*[clinic input]
11178os.lseek -> Py_off_t
11179
11180 fd: int
11181 position: Py_off_t
11182 how: int
11183 /
11184
11185Set the position of a file descriptor. Return the new position.
11186
11187Return the new cursor position in number of bytes
11188relative to the beginning of the file.
11189[clinic start generated code]*/
11190
11191PyDoc_STRVAR(os_lseek__doc__,
11192"lseek($module, fd, position, how, /)\n"
11193"--\n"
11194"\n"
11195"Set the position of a file descriptor. Return the new position.\n"
11196"\n"
11197"Return the new cursor position in number of bytes\n"
11198"relative to the beginning of the file.");
11199
11200#define OS_LSEEK_METHODDEF \
11201 {"lseek", (PyCFunction)os_lseek, METH_VARARGS, os_lseek__doc__},
11202
11203static Py_off_t
11204os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how);
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011205
Barry Warsaw53699e91996-12-10 23:23:01 +000011206static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011207os_lseek(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011208{
Larry Hastings2f936352014-08-05 14:04:04 +100011209 PyObject *return_value = NULL;
11210 int fd;
11211 Py_off_t position;
11212 int how;
11213 Py_off_t _return_value;
11214
11215 if (!PyArg_ParseTuple(args,
11216 "iO&i:lseek",
11217 &fd, Py_off_t_converter, &position, &how))
11218 goto exit;
11219 _return_value = os_lseek_impl(module, fd, position, how);
11220 if ((_return_value == -1) && PyErr_Occurred())
11221 goto exit;
11222 return_value = PyLong_FromPy_off_t(_return_value);
11223
11224exit:
11225 return return_value;
11226}
11227
11228static Py_off_t
11229os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how)
11230/*[clinic end generated code: output=88cfc146f55667af input=902654ad3f96a6d3]*/
11231{
11232 Py_off_t result;
11233
11234 if (!_PyVerify_fd(fd)) {
11235 posix_error();
11236 return -1;
11237 }
Guido van Rossum687dd131993-05-17 08:34:16 +000011238#ifdef SEEK_SET
Victor Stinner8c62be82010-05-06 00:08:46 +000011239 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
11240 switch (how) {
Larry Hastings2f936352014-08-05 14:04:04 +100011241 case 0: how = SEEK_SET; break;
11242 case 1: how = SEEK_CUR; break;
11243 case 2: how = SEEK_END; break;
Victor Stinner8c62be82010-05-06 00:08:46 +000011244 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000011245#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +000011246
Victor Stinner8c62be82010-05-06 00:08:46 +000011247 if (PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100011248 return -1;
Guido van Rossum94f6f721999-01-06 18:42:14 +000011249
Larry Hastings2f936352014-08-05 14:04:04 +100011250 if (!_PyVerify_fd(fd)) {
11251 posix_error();
11252 return -1;
11253 }
Victor Stinner8c62be82010-05-06 00:08:46 +000011254 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011255#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100011256 result = _lseeki64(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011257#else
Larry Hastings2f936352014-08-05 14:04:04 +100011258 result = lseek(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +000011259#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011260 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011261 if (result < 0)
11262 posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +000011263
Larry Hastings2f936352014-08-05 14:04:04 +100011264 return result;
Guido van Rossum687dd131993-05-17 08:34:16 +000011265}
11266
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011267
Larry Hastings2f936352014-08-05 14:04:04 +100011268/*[clinic input]
11269os.read
11270 fd: int
11271 length: Py_ssize_t
11272 /
11273
11274Read from a file descriptor. Returns a bytes object.
11275[clinic start generated code]*/
11276
11277PyDoc_STRVAR(os_read__doc__,
11278"read($module, fd, length, /)\n"
11279"--\n"
11280"\n"
11281"Read from a file descriptor. Returns a bytes object.");
11282
11283#define OS_READ_METHODDEF \
11284 {"read", (PyCFunction)os_read, METH_VARARGS, os_read__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011285
Barry Warsaw53699e91996-12-10 23:23:01 +000011286static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011287os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length);
11288
11289static PyObject *
11290os_read(PyModuleDef *module, PyObject *args)
Guido van Rossum687dd131993-05-17 08:34:16 +000011291{
Larry Hastings2f936352014-08-05 14:04:04 +100011292 PyObject *return_value = NULL;
Victor Stinnerb28ed922014-07-11 17:04:41 +020011293 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011294 Py_ssize_t length;
11295
11296 if (!PyArg_ParseTuple(args,
11297 "in:read",
11298 &fd, &length))
11299 goto exit;
11300 return_value = os_read_impl(module, fd, length);
11301
11302exit:
11303 return return_value;
11304}
11305
11306static PyObject *
11307os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length)
11308/*[clinic end generated code: output=1f3bc27260a24968 input=1df2eaa27c0bf1d3]*/
11309{
Victor Stinner8c62be82010-05-06 00:08:46 +000011310 Py_ssize_t n;
11311 PyObject *buffer;
Larry Hastings2f936352014-08-05 14:04:04 +100011312
11313 if (length < 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +000011314 errno = EINVAL;
11315 return posix_error();
11316 }
Larry Hastings2f936352014-08-05 14:04:04 +100011317 if (!_PyVerify_fd(fd))
11318 return posix_error();
11319
11320#ifdef MS_WINDOWS
11321 #define READ_CAST (int)
11322 if (length > INT_MAX)
11323 length = INT_MAX;
11324#else
11325 #define READ_CAST
11326#endif
11327
11328 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011329 if (buffer == NULL)
11330 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011331 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011332 n = read(fd, PyBytes_AS_STRING(buffer), READ_CAST length);
Victor Stinner8c62be82010-05-06 00:08:46 +000011333 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011334
Victor Stinner8c62be82010-05-06 00:08:46 +000011335 if (n < 0) {
11336 Py_DECREF(buffer);
11337 return posix_error();
11338 }
Larry Hastings2f936352014-08-05 14:04:04 +100011339
11340 if (n != length)
Victor Stinner8c62be82010-05-06 00:08:46 +000011341 _PyBytes_Resize(&buffer, n);
Larry Hastings2f936352014-08-05 14:04:04 +100011342
Victor Stinner8c62be82010-05-06 00:08:46 +000011343 return buffer;
Guido van Rossum687dd131993-05-17 08:34:16 +000011344}
11345
Ross Lagerwall7807c352011-03-17 20:20:30 +020011346#if (defined(HAVE_SENDFILE) && (defined(__FreeBSD__) || defined(__DragonFly__) \
11347 || defined(__APPLE__))) || defined(HAVE_READV) || defined(HAVE_WRITEV)
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011348static Py_ssize_t
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011349iov_setup(struct iovec **iov, Py_buffer **buf, PyObject *seq, int cnt, int type)
11350{
11351 int i, j;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011352 Py_ssize_t blen, total = 0;
11353
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011354 *iov = PyMem_New(struct iovec, cnt);
11355 if (*iov == NULL) {
11356 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011357 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011358 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011359
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011360 *buf = PyMem_New(Py_buffer, cnt);
11361 if (*buf == NULL) {
11362 PyMem_Del(*iov);
11363 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +010011364 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011365 }
11366
11367 for (i = 0; i < cnt; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011368 PyObject *item = PySequence_GetItem(seq, i);
11369 if (item == NULL)
11370 goto fail;
11371 if (PyObject_GetBuffer(item, &(*buf)[i], type) == -1) {
11372 Py_DECREF(item);
11373 goto fail;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011374 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011375 Py_DECREF(item);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011376 (*iov)[i].iov_base = (*buf)[i].buf;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011377 blen = (*buf)[i].len;
11378 (*iov)[i].iov_len = blen;
11379 total += blen;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011380 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011381 return total;
Ross Lagerwall9ad63e02011-03-19 09:11:14 +020011382
11383fail:
11384 PyMem_Del(*iov);
11385 for (j = 0; j < i; j++) {
11386 PyBuffer_Release(&(*buf)[j]);
11387 }
11388 PyMem_Del(*buf);
Victor Stinner57ddf782014-01-08 15:21:28 +010011389 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011390}
11391
11392static void
11393iov_cleanup(struct iovec *iov, Py_buffer *buf, int cnt)
11394{
11395 int i;
11396 PyMem_Del(iov);
11397 for (i = 0; i < cnt; i++) {
11398 PyBuffer_Release(&buf[i]);
11399 }
11400 PyMem_Del(buf);
11401}
11402#endif
11403
Larry Hastings2f936352014-08-05 14:04:04 +100011404
Ross Lagerwall7807c352011-03-17 20:20:30 +020011405#ifdef HAVE_READV
Larry Hastings2f936352014-08-05 14:04:04 +100011406/*[clinic input]
11407os.readv -> Py_ssize_t
11408
11409 fd: int
11410 buffers: object
11411 /
11412
11413Read from a file descriptor fd into an iterable of buffers.
11414
11415The buffers should be mutable buffers accepting bytes.
11416readv will transfer data into each buffer until it is full
11417and then move on to the next buffer in the sequence to hold
11418the rest of the data.
11419
11420readv returns the total number of bytes read,
11421which may be less than the total capacity of all the buffers.
11422[clinic start generated code]*/
11423
11424PyDoc_STRVAR(os_readv__doc__,
11425"readv($module, fd, buffers, /)\n"
11426"--\n"
11427"\n"
11428"Read from a file descriptor fd into an iterable of buffers.\n"
11429"\n"
11430"The buffers should be mutable buffers accepting bytes.\n"
11431"readv will transfer data into each buffer until it is full\n"
11432"and then move on to the next buffer in the sequence to hold\n"
11433"the rest of the data.\n"
11434"\n"
11435"readv returns the total number of bytes read,\n"
11436"which may be less than the total capacity of all the buffers.");
11437
11438#define OS_READV_METHODDEF \
11439 {"readv", (PyCFunction)os_readv, METH_VARARGS, os_readv__doc__},
11440
11441static Py_ssize_t
11442os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011443
11444static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011445os_readv(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011446{
Larry Hastings2f936352014-08-05 14:04:04 +100011447 PyObject *return_value = NULL;
11448 int fd;
11449 PyObject *buffers;
11450 Py_ssize_t _return_value;
11451
11452 if (!PyArg_ParseTuple(args,
11453 "iO:readv",
11454 &fd, &buffers))
11455 goto exit;
11456 _return_value = os_readv_impl(module, fd, buffers);
11457 if ((_return_value == -1) && PyErr_Occurred())
11458 goto exit;
11459 return_value = PyLong_FromSsize_t(_return_value);
11460
11461exit:
11462 return return_value;
11463}
11464
11465static Py_ssize_t
11466os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers)
11467/*[clinic end generated code: output=72748b1c32a6e2a1 input=e679eb5dbfa0357d]*/
11468{
11469 int cnt;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011470 Py_ssize_t n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011471 struct iovec *iov;
11472 Py_buffer *buf;
11473
Larry Hastings2f936352014-08-05 14:04:04 +100011474 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011475 PyErr_SetString(PyExc_TypeError,
11476 "readv() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100011477 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011478 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020011479
Larry Hastings2f936352014-08-05 14:04:04 +100011480 cnt = PySequence_Size(buffers);
11481
11482 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_WRITABLE) < 0)
11483 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011484
11485 Py_BEGIN_ALLOW_THREADS
11486 n = readv(fd, iov, cnt);
11487 Py_END_ALLOW_THREADS
11488
11489 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100011490 if (n < 0) {
11491 posix_error();
11492 return -1;
11493 }
Victor Stinner57ddf782014-01-08 15:21:28 +010011494
Larry Hastings2f936352014-08-05 14:04:04 +100011495 return n;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011496}
Larry Hastings2f936352014-08-05 14:04:04 +100011497#endif /* HAVE_READV */
11498
Ross Lagerwall7807c352011-03-17 20:20:30 +020011499
11500#ifdef HAVE_PREAD
Larry Hastings2f936352014-08-05 14:04:04 +100011501/*[clinic input]
11502# TODO length should be size_t! but Python doesn't support parsing size_t yet.
11503os.pread
11504
11505 fd: int
11506 length: int
11507 offset: Py_off_t
11508 /
11509
11510Read a number of bytes from a file descriptor starting at a particular offset.
11511
11512Read length bytes from file descriptor fd, starting at offset bytes from
11513the beginning of the file. The file offset remains unchanged.
11514[clinic start generated code]*/
11515
11516PyDoc_STRVAR(os_pread__doc__,
11517"pread($module, fd, length, offset, /)\n"
11518"--\n"
11519"\n"
11520"Read a number of bytes from a file descriptor starting at a particular offset.\n"
11521"\n"
11522"Read length bytes from file descriptor fd, starting at offset bytes from\n"
11523"the beginning of the file. The file offset remains unchanged.");
11524
11525#define OS_PREAD_METHODDEF \
11526 {"pread", (PyCFunction)os_pread, METH_VARARGS, os_pread__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020011527
11528static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011529os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset);
11530
11531static PyObject *
11532os_pread(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011533{
Larry Hastings2f936352014-08-05 14:04:04 +100011534 PyObject *return_value = NULL;
11535 int fd;
11536 int length;
11537 Py_off_t offset;
11538
11539 if (!PyArg_ParseTuple(args,
11540 "iiO&:pread",
11541 &fd, &length, Py_off_t_converter, &offset))
11542 goto exit;
11543 return_value = os_pread_impl(module, fd, length, offset);
11544
11545exit:
11546 return return_value;
11547}
11548
11549static PyObject *
11550os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset)
11551/*[clinic end generated code: output=7b62bf6c06e20ae8 input=084948dcbaa35d4c]*/
11552{
Ross Lagerwall7807c352011-03-17 20:20:30 +020011553 Py_ssize_t n;
11554 PyObject *buffer;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011555
Larry Hastings2f936352014-08-05 14:04:04 +100011556 if (length < 0) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020011557 errno = EINVAL;
11558 return posix_error();
11559 }
Larry Hastings2f936352014-08-05 14:04:04 +100011560 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011561 if (buffer == NULL)
11562 return NULL;
11563 if (!_PyVerify_fd(fd)) {
11564 Py_DECREF(buffer);
11565 return posix_error();
11566 }
11567 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011568 n = pread(fd, PyBytes_AS_STRING(buffer), length, offset);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011569 Py_END_ALLOW_THREADS
11570 if (n < 0) {
11571 Py_DECREF(buffer);
11572 return posix_error();
11573 }
Larry Hastings2f936352014-08-05 14:04:04 +100011574 if (n != length)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011575 _PyBytes_Resize(&buffer, n);
11576 return buffer;
11577}
Larry Hastings2f936352014-08-05 14:04:04 +100011578#endif /* HAVE_PREAD */
Ross Lagerwall7807c352011-03-17 20:20:30 +020011579
Larry Hastings2f936352014-08-05 14:04:04 +100011580
11581/*[clinic input]
11582os.write -> Py_ssize_t
11583
11584 fd: int
11585 data: Py_buffer
11586 /
11587
11588Write a bytes object to a file descriptor.
11589[clinic start generated code]*/
11590
11591PyDoc_STRVAR(os_write__doc__,
11592"write($module, fd, data, /)\n"
11593"--\n"
11594"\n"
11595"Write a bytes object to a file descriptor.");
11596
11597#define OS_WRITE_METHODDEF \
11598 {"write", (PyCFunction)os_write, METH_VARARGS, os_write__doc__},
11599
11600static Py_ssize_t
11601os_write_impl(PyModuleDef *module, int fd, Py_buffer *data);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011602
11603static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011604os_write(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020011605{
Larry Hastings2f936352014-08-05 14:04:04 +100011606 PyObject *return_value = NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011607 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011608 Py_buffer data = {NULL, NULL};
11609 Py_ssize_t _return_value;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011610
Larry Hastings2f936352014-08-05 14:04:04 +100011611 if (!PyArg_ParseTuple(args,
11612 "iy*:write",
11613 &fd, &data))
11614 goto exit;
11615 _return_value = os_write_impl(module, fd, &data);
11616 if ((_return_value == -1) && PyErr_Occurred())
11617 goto exit;
11618 return_value = PyLong_FromSsize_t(_return_value);
11619
11620exit:
11621 /* Cleanup for data */
11622 if (data.obj)
11623 PyBuffer_Release(&data);
11624
11625 return return_value;
11626}
11627
11628static Py_ssize_t
11629os_write_impl(PyModuleDef *module, int fd, Py_buffer *data)
11630/*[clinic end generated code: output=aeb96acfdd4d5112 input=3207e28963234f3c]*/
11631{
11632 Py_ssize_t size;
11633 Py_ssize_t len = data->len;
11634
Ross Lagerwall7807c352011-03-17 20:20:30 +020011635 if (!_PyVerify_fd(fd)) {
Larry Hastings2f936352014-08-05 14:04:04 +100011636 posix_error();
11637 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011638 }
Larry Hastings2f936352014-08-05 14:04:04 +100011639
Ross Lagerwall7807c352011-03-17 20:20:30 +020011640 Py_BEGIN_ALLOW_THREADS
Victor Stinner14b9b112013-06-25 00:37:25 +020011641#ifdef MS_WINDOWS
Ross Lagerwall7807c352011-03-17 20:20:30 +020011642 if (len > INT_MAX)
11643 len = INT_MAX;
Larry Hastings2f936352014-08-05 14:04:04 +100011644 size = write(fd, data->buf, (int)len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011645#else
Larry Hastings2f936352014-08-05 14:04:04 +100011646 size = write(fd, data->buf, len);
Ross Lagerwall7807c352011-03-17 20:20:30 +020011647#endif
11648 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100011649 if (size < 0) {
11650 posix_error();
11651 return -1;
11652 }
11653 return size;
Ross Lagerwall7807c352011-03-17 20:20:30 +020011654}
11655
11656#ifdef HAVE_SENDFILE
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011657PyDoc_STRVAR(posix_sendfile__doc__,
11658"sendfile(out, in, offset, nbytes) -> byteswritten\n\
11659sendfile(out, in, offset, nbytes, headers=None, trailers=None, flags=0)\n\
11660 -> byteswritten\n\
11661Copy nbytes bytes from file descriptor in to file descriptor out.");
11662
Larry Hastings2f936352014-08-05 14:04:04 +100011663/* AC 3.5: don't bother converting, has optional group*/
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011664static PyObject *
11665posix_sendfile(PyObject *self, PyObject *args, PyObject *kwdict)
11666{
11667 int in, out;
11668 Py_ssize_t ret;
11669 off_t offset;
11670
11671#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
11672#ifndef __APPLE__
11673 Py_ssize_t len;
11674#endif
11675 PyObject *headers = NULL, *trailers = NULL;
11676 Py_buffer *hbuf, *tbuf;
11677 off_t sbytes;
11678 struct sf_hdtr sf;
11679 int flags = 0;
Benjamin Petersond8a43b42011-02-26 21:35:16 +000011680 static char *keywords[] = {"out", "in",
11681 "offset", "count",
11682 "headers", "trailers", "flags", NULL};
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011683
Victor Stinner6ce0dbf2013-07-07 16:32:36 +020011684 sf.headers = NULL;
11685 sf.trailers = NULL;
11686
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011687#ifdef __APPLE__
11688 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&O&|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011689 keywords, &out, &in, Py_off_t_converter, &offset, Py_off_t_converter, &sbytes,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011690#else
11691 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&n|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +100011692 keywords, &out, &in, Py_off_t_converter, &offset, &len,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011693#endif
11694 &headers, &trailers, &flags))
11695 return NULL;
11696 if (headers != NULL) {
11697 if (!PySequence_Check(headers)) {
11698 PyErr_SetString(PyExc_TypeError,
11699 "sendfile() headers must be a sequence or None");
11700 return NULL;
11701 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011702 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011703 sf.hdr_cnt = PySequence_Size(headers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011704 if (sf.hdr_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011705 (i = iov_setup(&(sf.headers), &hbuf,
11706 headers, sf.hdr_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011707 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011708#ifdef __APPLE__
11709 sbytes += i;
11710#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011711 }
11712 }
11713 if (trailers != NULL) {
11714 if (!PySequence_Check(trailers)) {
11715 PyErr_SetString(PyExc_TypeError,
11716 "sendfile() trailers must be a sequence or None");
11717 return NULL;
11718 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011719 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011720 sf.trl_cnt = PySequence_Size(trailers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011721 if (sf.trl_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +010011722 (i = iov_setup(&(sf.trailers), &tbuf,
11723 trailers, sf.trl_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011724 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +000011725#ifdef __APPLE__
11726 sbytes += i;
11727#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011728 }
11729 }
11730
11731 Py_BEGIN_ALLOW_THREADS
11732#ifdef __APPLE__
11733 ret = sendfile(in, out, offset, &sbytes, &sf, flags);
11734#else
11735 ret = sendfile(in, out, offset, len, &sf, &sbytes, flags);
11736#endif
11737 Py_END_ALLOW_THREADS
11738
11739 if (sf.headers != NULL)
11740 iov_cleanup(sf.headers, hbuf, sf.hdr_cnt);
11741 if (sf.trailers != NULL)
11742 iov_cleanup(sf.trailers, tbuf, sf.trl_cnt);
11743
11744 if (ret < 0) {
11745 if ((errno == EAGAIN) || (errno == EBUSY)) {
11746 if (sbytes != 0) {
11747 // some data has been sent
11748 goto done;
11749 }
11750 else {
11751 // no data has been sent; upper application is supposed
11752 // to retry on EAGAIN or EBUSY
11753 return posix_error();
11754 }
11755 }
11756 return posix_error();
11757 }
11758 goto done;
11759
11760done:
11761 #if !defined(HAVE_LARGEFILE_SUPPORT)
11762 return Py_BuildValue("l", sbytes);
11763 #else
11764 return Py_BuildValue("L", sbytes);
11765 #endif
11766
11767#else
11768 Py_ssize_t count;
11769 PyObject *offobj;
11770 static char *keywords[] = {"out", "in",
11771 "offset", "count", NULL};
11772 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiOn:sendfile",
11773 keywords, &out, &in, &offobj, &count))
11774 return NULL;
11775#ifdef linux
11776 if (offobj == Py_None) {
11777 Py_BEGIN_ALLOW_THREADS
11778 ret = sendfile(out, in, NULL, count);
11779 Py_END_ALLOW_THREADS
11780 if (ret < 0)
11781 return posix_error();
Giampaolo Rodola'ff1a7352011-04-19 09:47:16 +020011782 return Py_BuildValue("n", ret);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011783 }
11784#endif
Larry Hastings2f936352014-08-05 14:04:04 +100011785 if (!Py_off_t_converter(offobj, &offset))
Antoine Pitroudcc20b82011-02-26 13:38:35 +000011786 return NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000011787 Py_BEGIN_ALLOW_THREADS
11788 ret = sendfile(out, in, &offset, count);
11789 Py_END_ALLOW_THREADS
11790 if (ret < 0)
11791 return posix_error();
11792 return Py_BuildValue("n", ret);
11793#endif
11794}
Larry Hastings2f936352014-08-05 14:04:04 +100011795#endif /* HAVE_SENDFILE */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011796
Larry Hastings2f936352014-08-05 14:04:04 +100011797
11798/*[clinic input]
11799os.fstat
11800
11801 fd : int
11802
11803Perform a stat system call on the given file descriptor.
11804
11805Like stat(), but for an open file descriptor.
11806Equivalent to os.stat(fd).
11807[clinic start generated code]*/
11808
11809PyDoc_STRVAR(os_fstat__doc__,
11810"fstat($module, /, fd)\n"
11811"--\n"
11812"\n"
11813"Perform a stat system call on the given file descriptor.\n"
11814"\n"
11815"Like stat(), but for an open file descriptor.\n"
11816"Equivalent to os.stat(fd).");
11817
11818#define OS_FSTAT_METHODDEF \
11819 {"fstat", (PyCFunction)os_fstat, METH_VARARGS|METH_KEYWORDS, os_fstat__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011820
Barry Warsaw53699e91996-12-10 23:23:01 +000011821static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011822os_fstat_impl(PyModuleDef *module, int fd);
11823
11824static PyObject *
11825os_fstat(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossum687dd131993-05-17 08:34:16 +000011826{
Larry Hastings2f936352014-08-05 14:04:04 +100011827 PyObject *return_value = NULL;
11828 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000011829 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011830
11831 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
11832 "i:fstat", _keywords,
11833 &fd))
11834 goto exit;
11835 return_value = os_fstat_impl(module, fd);
11836
11837exit:
11838 return return_value;
11839}
11840
11841static PyObject *
11842os_fstat_impl(PyModuleDef *module, int fd)
11843/*[clinic end generated code: output=dae4a9678c7bd881 input=27e0e0ebbe5600c9]*/
11844{
Victor Stinner8c62be82010-05-06 00:08:46 +000011845 STRUCT_STAT st;
11846 int res;
Larry Hastings2f936352014-08-05 14:04:04 +100011847
Victor Stinner8c62be82010-05-06 00:08:46 +000011848 Py_BEGIN_ALLOW_THREADS
11849 res = FSTAT(fd, &st);
11850 Py_END_ALLOW_THREADS
11851 if (res != 0) {
Martin v. Löwis14694662006-02-03 12:54:16 +000011852#ifdef MS_WINDOWS
Victor Stinnerb024e842012-10-31 22:24:06 +010011853 return PyErr_SetFromWindowsErr(0);
Martin v. Löwis14694662006-02-03 12:54:16 +000011854#else
Victor Stinner8c62be82010-05-06 00:08:46 +000011855 return posix_error();
Martin v. Löwis14694662006-02-03 12:54:16 +000011856#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000011857 }
Tim Peters5aa91602002-01-30 05:46:57 +000011858
Victor Stinner4195b5c2012-02-08 23:03:19 +010011859 return _pystat_fromstructstat(&st);
Guido van Rossum687dd131993-05-17 08:34:16 +000011860}
11861
Larry Hastings2f936352014-08-05 14:04:04 +100011862
11863/*[clinic input]
11864os.isatty -> bool
11865 fd: int
11866 /
11867
11868Return True if the fd is connected to a terminal.
11869
11870Return True if the file descriptor is an open file descriptor
11871connected to the slave end of a terminal.
11872[clinic start generated code]*/
11873
11874PyDoc_STRVAR(os_isatty__doc__,
11875"isatty($module, fd, /)\n"
11876"--\n"
11877"\n"
11878"Return True if the fd is connected to a terminal.\n"
11879"\n"
11880"Return True if the file descriptor is an open file descriptor\n"
11881"connected to the slave end of a terminal.");
11882
11883#define OS_ISATTY_METHODDEF \
11884 {"isatty", (PyCFunction)os_isatty, METH_VARARGS, os_isatty__doc__},
11885
11886static int
11887os_isatty_impl(PyModuleDef *module, int fd);
Skip Montanaro1517d842000-07-19 14:34:14 +000011888
11889static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011890os_isatty(PyModuleDef *module, PyObject *args)
Skip Montanaro1517d842000-07-19 14:34:14 +000011891{
Larry Hastings2f936352014-08-05 14:04:04 +100011892 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000011893 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +100011894 int _return_value;
11895
11896 if (!PyArg_ParseTuple(args,
11897 "i:isatty",
11898 &fd))
11899 goto exit;
11900 _return_value = os_isatty_impl(module, fd);
11901 if ((_return_value == -1) && PyErr_Occurred())
11902 goto exit;
11903 return_value = PyBool_FromLong((long)_return_value);
11904
11905exit:
11906 return return_value;
Skip Montanaro1517d842000-07-19 14:34:14 +000011907}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011908
Larry Hastings2f936352014-08-05 14:04:04 +100011909static int
11910os_isatty_impl(PyModuleDef *module, int fd)
11911/*[clinic end generated code: output=4bfadbfe22715097 input=08ce94aa1eaf7b5e]*/
11912{
11913 if (!_PyVerify_fd(fd))
11914 return 0;
11915 return isatty(fd);
11916}
11917
11918
Guido van Rossuma4916fa1996-05-23 22:58:55 +000011919#ifdef HAVE_PIPE
Larry Hastings2f936352014-08-05 14:04:04 +100011920/*[clinic input]
11921os.pipe
11922
11923Create a pipe.
11924
11925Returns a tuple of two file descriptors:
11926 (read_fd, write_fd)
11927[clinic start generated code]*/
11928
11929PyDoc_STRVAR(os_pipe__doc__,
11930"pipe($module, /)\n"
11931"--\n"
11932"\n"
11933"Create a pipe.\n"
11934"\n"
11935"Returns a tuple of two file descriptors:\n"
11936" (read_fd, write_fd)");
11937
11938#define OS_PIPE_METHODDEF \
11939 {"pipe", (PyCFunction)os_pipe, METH_NOARGS, os_pipe__doc__},
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000011940
Barry Warsaw53699e91996-12-10 23:23:01 +000011941static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100011942os_pipe_impl(PyModuleDef *module);
11943
11944static PyObject *
11945os_pipe(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
11946{
11947 return os_pipe_impl(module);
11948}
11949
11950static PyObject *
11951os_pipe_impl(PyModuleDef *module)
11952/*[clinic end generated code: output=0da2479f2266e774 input=02535e8c8fa6c4d4]*/
Guido van Rossum687dd131993-05-17 08:34:16 +000011953{
Victor Stinner8c62be82010-05-06 00:08:46 +000011954 int fds[2];
Victor Stinnerdaf45552013-08-28 00:53:59 +020011955#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000011956 HANDLE read, write;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011957 SECURITY_ATTRIBUTES attr;
Victor Stinner8c62be82010-05-06 00:08:46 +000011958 BOOL ok;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011959#else
11960 int res;
11961#endif
11962
11963#ifdef MS_WINDOWS
11964 attr.nLength = sizeof(attr);
11965 attr.lpSecurityDescriptor = NULL;
11966 attr.bInheritHandle = FALSE;
11967
11968 Py_BEGIN_ALLOW_THREADS
11969 ok = CreatePipe(&read, &write, &attr, 0);
11970 if (ok) {
11971 fds[0] = _open_osfhandle((Py_intptr_t)read, _O_RDONLY);
11972 fds[1] = _open_osfhandle((Py_intptr_t)write, _O_WRONLY);
11973 if (fds[0] == -1 || fds[1] == -1) {
11974 CloseHandle(read);
11975 CloseHandle(write);
11976 ok = 0;
11977 }
11978 }
11979 Py_END_ALLOW_THREADS
11980
Victor Stinner8c62be82010-05-06 00:08:46 +000011981 if (!ok)
Victor Stinnerb024e842012-10-31 22:24:06 +010011982 return PyErr_SetFromWindowsErr(0);
Victor Stinnerdaf45552013-08-28 00:53:59 +020011983#else
11984
11985#ifdef HAVE_PIPE2
11986 Py_BEGIN_ALLOW_THREADS
11987 res = pipe2(fds, O_CLOEXEC);
11988 Py_END_ALLOW_THREADS
11989
11990 if (res != 0 && errno == ENOSYS)
11991 {
11992#endif
11993 Py_BEGIN_ALLOW_THREADS
11994 res = pipe(fds);
11995 Py_END_ALLOW_THREADS
11996
11997 if (res == 0) {
11998 if (_Py_set_inheritable(fds[0], 0, NULL) < 0) {
11999 close(fds[0]);
12000 close(fds[1]);
12001 return NULL;
12002 }
12003 if (_Py_set_inheritable(fds[1], 0, NULL) < 0) {
12004 close(fds[0]);
12005 close(fds[1]);
12006 return NULL;
12007 }
12008 }
12009#ifdef HAVE_PIPE2
12010 }
12011#endif
12012
12013 if (res != 0)
12014 return PyErr_SetFromErrno(PyExc_OSError);
12015#endif /* !MS_WINDOWS */
12016 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum687dd131993-05-17 08:34:16 +000012017}
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012018#endif /* HAVE_PIPE */
12019
Larry Hastings2f936352014-08-05 14:04:04 +100012020
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012021#ifdef HAVE_PIPE2
Larry Hastings2f936352014-08-05 14:04:04 +100012022/*[clinic input]
12023os.pipe2
12024
12025 flags: int
12026 /
12027
12028Create a pipe with flags set atomically.
12029
12030Returns a tuple of two file descriptors:
12031 (read_fd, write_fd)
12032
12033flags can be constructed by ORing together one or more of these values:
12034O_NONBLOCK, O_CLOEXEC.
12035[clinic start generated code]*/
12036
12037PyDoc_STRVAR(os_pipe2__doc__,
12038"pipe2($module, flags, /)\n"
12039"--\n"
12040"\n"
12041"Create a pipe with flags set atomically.\n"
12042"\n"
12043"Returns a tuple of two file descriptors:\n"
12044" (read_fd, write_fd)\n"
12045"\n"
12046"flags can be constructed by ORing together one or more of these values:\n"
12047"O_NONBLOCK, O_CLOEXEC.");
12048
12049#define OS_PIPE2_METHODDEF \
12050 {"pipe2", (PyCFunction)os_pipe2, METH_VARARGS, os_pipe2__doc__},
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012051
12052static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012053os_pipe2_impl(PyModuleDef *module, int flags);
12054
12055static PyObject *
12056os_pipe2(PyModuleDef *module, PyObject *args)
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012057{
Larry Hastings2f936352014-08-05 14:04:04 +100012058 PyObject *return_value = NULL;
Charles-François Natali368f34b2011-06-06 19:49:47 +020012059 int flags;
Larry Hastings2f936352014-08-05 14:04:04 +100012060
12061 if (!PyArg_ParseTuple(args,
12062 "i:pipe2",
12063 &flags))
12064 goto exit;
12065 return_value = os_pipe2_impl(module, flags);
12066
12067exit:
12068 return return_value;
12069}
12070
12071static PyObject *
12072os_pipe2_impl(PyModuleDef *module, int flags)
12073/*[clinic end generated code: output=9e27c799ce19220b input=f261b6e7e63c6817]*/
12074{
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012075 int fds[2];
12076 int res;
12077
Charles-François Natalidaafdd52011-05-29 20:07:40 +020012078 res = pipe2(fds, flags);
12079 if (res != 0)
12080 return posix_error();
12081 return Py_BuildValue("(ii)", fds[0], fds[1]);
12082}
12083#endif /* HAVE_PIPE2 */
12084
Larry Hastings2f936352014-08-05 14:04:04 +100012085
Ross Lagerwall7807c352011-03-17 20:20:30 +020012086#ifdef HAVE_WRITEV
Larry Hastings2f936352014-08-05 14:04:04 +100012087/*[clinic input]
12088os.writev -> Py_ssize_t
12089 fd: int
12090 buffers: object
12091 /
12092
12093Iterate over buffers, and write the contents of each to a file descriptor.
12094
12095Returns the total number of bytes written.
12096buffers must be a sequence of bytes-like objects.
12097[clinic start generated code]*/
12098
12099PyDoc_STRVAR(os_writev__doc__,
12100"writev($module, fd, buffers, /)\n"
12101"--\n"
12102"\n"
12103"Iterate over buffers, and write the contents of each to a file descriptor.\n"
12104"\n"
12105"Returns the total number of bytes written.\n"
12106"buffers must be a sequence of bytes-like objects.");
12107
12108#define OS_WRITEV_METHODDEF \
12109 {"writev", (PyCFunction)os_writev, METH_VARARGS, os_writev__doc__},
12110
12111static Py_ssize_t
12112os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012113
12114static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012115os_writev(PyModuleDef *module, PyObject *args)
Ross Lagerwall7807c352011-03-17 20:20:30 +020012116{
Larry Hastings2f936352014-08-05 14:04:04 +100012117 PyObject *return_value = NULL;
12118 int fd;
12119 PyObject *buffers;
12120 Py_ssize_t _return_value;
12121
12122 if (!PyArg_ParseTuple(args,
12123 "iO:writev",
12124 &fd, &buffers))
12125 goto exit;
12126 _return_value = os_writev_impl(module, fd, buffers);
12127 if ((_return_value == -1) && PyErr_Occurred())
12128 goto exit;
12129 return_value = PyLong_FromSsize_t(_return_value);
12130
12131exit:
12132 return return_value;
12133}
12134
12135static Py_ssize_t
12136os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers)
12137/*[clinic end generated code: output=591c662dccbe4951 input=5b8d17fe4189d2fe]*/
12138{
12139 int cnt;
12140 Py_ssize_t result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012141 struct iovec *iov;
12142 Py_buffer *buf;
Larry Hastings2f936352014-08-05 14:04:04 +100012143
12144 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020012145 PyErr_SetString(PyExc_TypeError,
12146 "writev() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +100012147 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012148 }
Larry Hastings2f936352014-08-05 14:04:04 +100012149 cnt = PySequence_Size(buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012150
Larry Hastings2f936352014-08-05 14:04:04 +100012151 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_SIMPLE) < 0) {
12152 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012153 }
12154
12155 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012156 result = writev(fd, iov, cnt);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012157 Py_END_ALLOW_THREADS
12158
12159 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +100012160 if (result < 0)
12161 posix_error();
Victor Stinner57ddf782014-01-08 15:21:28 +010012162
Georg Brandl306336b2012-06-24 12:55:33 +020012163 return result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012164}
Larry Hastings2f936352014-08-05 14:04:04 +100012165#endif /* HAVE_WRITEV */
12166
12167
12168#ifdef HAVE_PWRITE
12169/*[clinic input]
12170os.pwrite -> Py_ssize_t
12171
12172 fd: int
12173 buffer: Py_buffer
12174 offset: Py_off_t
12175 /
12176
12177Write bytes to a file descriptor starting at a particular offset.
12178
12179Write buffer to fd, starting at offset bytes from the beginning of
12180the file. Returns the number of bytes writte. Does not change the
12181current file offset.
12182[clinic start generated code]*/
12183
12184PyDoc_STRVAR(os_pwrite__doc__,
12185"pwrite($module, fd, buffer, offset, /)\n"
12186"--\n"
12187"\n"
12188"Write bytes to a file descriptor starting at a particular offset.\n"
12189"\n"
12190"Write buffer to fd, starting at offset bytes from the beginning of\n"
12191"the file. Returns the number of bytes writte. Does not change the\n"
12192"current file offset.");
12193
12194#define OS_PWRITE_METHODDEF \
12195 {"pwrite", (PyCFunction)os_pwrite, METH_VARARGS, os_pwrite__doc__},
12196
12197static Py_ssize_t
12198os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset);
12199
12200static PyObject *
12201os_pwrite(PyModuleDef *module, PyObject *args)
12202{
12203 PyObject *return_value = NULL;
12204 int fd;
12205 Py_buffer buffer = {NULL, NULL};
12206 Py_off_t offset;
12207 Py_ssize_t _return_value;
12208
12209 if (!PyArg_ParseTuple(args,
12210 "iy*O&:pwrite",
12211 &fd, &buffer, Py_off_t_converter, &offset))
12212 goto exit;
12213 _return_value = os_pwrite_impl(module, fd, &buffer, offset);
12214 if ((_return_value == -1) && PyErr_Occurred())
12215 goto exit;
12216 return_value = PyLong_FromSsize_t(_return_value);
12217
12218exit:
12219 /* Cleanup for buffer */
12220 if (buffer.obj)
12221 PyBuffer_Release(&buffer);
12222
12223 return return_value;
12224}
12225
12226static Py_ssize_t
12227os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer, Py_off_t offset)
12228/*[clinic end generated code: output=ec9cc5b2238e96a7 input=19903f1b3dd26377]*/
12229{
12230 Py_ssize_t size;
12231
12232 if (!_PyVerify_fd(fd)) {
12233 posix_error();
12234 return -1;
12235 }
12236
12237 Py_BEGIN_ALLOW_THREADS
12238 size = pwrite(fd, buffer->buf, (size_t)buffer->len, offset);
12239 Py_END_ALLOW_THREADS
12240
12241 if (size < 0)
12242 posix_error();
12243 return size;
12244}
12245#endif /* HAVE_PWRITE */
12246
12247
12248#ifdef HAVE_MKFIFO
12249/*[clinic input]
12250os.mkfifo
12251
12252 path: path_t
12253 mode: int=0o666
12254 *
12255 dir_fd: dir_fd(requires='mkfifoat')=None
12256
12257Create a "fifo" (a POSIX named pipe).
12258
12259If dir_fd is not None, it should be a file descriptor open to a directory,
12260 and path should be relative; path will then be relative to that directory.
12261dir_fd may not be implemented on your platform.
12262 If it is unavailable, using it will raise a NotImplementedError.
12263[clinic start generated code]*/
12264
12265PyDoc_STRVAR(os_mkfifo__doc__,
12266"mkfifo($module, /, path, mode=438, *, dir_fd=None)\n"
12267"--\n"
12268"\n"
12269"Create a \"fifo\" (a POSIX named pipe).\n"
12270"\n"
12271"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12272" and path should be relative; path will then be relative to that directory.\n"
12273"dir_fd may not be implemented on your platform.\n"
12274" If it is unavailable, using it will raise a NotImplementedError.");
12275
12276#define OS_MKFIFO_METHODDEF \
12277 {"mkfifo", (PyCFunction)os_mkfifo, METH_VARARGS|METH_KEYWORDS, os_mkfifo__doc__},
12278
12279static PyObject *
12280os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd);
12281
12282static PyObject *
12283os_mkfifo(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12284{
12285 PyObject *return_value = NULL;
12286 static char *_keywords[] = {"path", "mode", "dir_fd", NULL};
12287 path_t path = PATH_T_INITIALIZE("mkfifo", "path", 0, 0);
12288 int mode = 438;
12289 int dir_fd = DEFAULT_DIR_FD;
12290
12291 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12292 "O&|i$O&:mkfifo", _keywords,
12293 path_converter, &path, &mode, MKFIFOAT_DIR_FD_CONVERTER, &dir_fd))
12294 goto exit;
12295 return_value = os_mkfifo_impl(module, &path, mode, dir_fd);
12296
12297exit:
12298 /* Cleanup for path */
12299 path_cleanup(&path);
12300
12301 return return_value;
12302}
12303
12304static PyObject *
12305os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
12306/*[clinic end generated code: output=b3321927546893d0 input=73032e98a36e0e19]*/
12307{
12308 int result;
12309
12310 Py_BEGIN_ALLOW_THREADS
12311#ifdef HAVE_MKFIFOAT
12312 if (dir_fd != DEFAULT_DIR_FD)
12313 result = mkfifoat(dir_fd, path->narrow, mode);
12314 else
Ross Lagerwall7807c352011-03-17 20:20:30 +020012315#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012316 result = mkfifo(path->narrow, mode);
12317 Py_END_ALLOW_THREADS
12318
12319 if (result < 0)
12320 return posix_error();
12321
12322 Py_RETURN_NONE;
12323}
12324#endif /* HAVE_MKFIFO */
12325
12326
12327#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
12328/*[clinic input]
12329os.mknod
12330
12331 path: path_t
12332 mode: int=0o600
12333 device: int=0
12334 *
12335 dir_fd: dir_fd(requires='mknodat')=None
12336
12337Create a node in the file system.
12338
12339Create a node in the file system (file, device special file or named pipe)
12340at path. mode specifies both the permissions to use and the
12341type of node to be created, being combined (bitwise OR) with one of
12342S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,
12343device defines the newly created device special file (probably using
12344os.makedev()). Otherwise device is ignored.
12345
12346If dir_fd is not None, it should be a file descriptor open to a directory,
12347 and path should be relative; path will then be relative to that directory.
12348dir_fd may not be implemented on your platform.
12349 If it is unavailable, using it will raise a NotImplementedError.
12350[clinic start generated code]*/
12351
12352PyDoc_STRVAR(os_mknod__doc__,
12353"mknod($module, /, path, mode=384, device=0, *, dir_fd=None)\n"
12354"--\n"
12355"\n"
12356"Create a node in the file system.\n"
12357"\n"
12358"Create a node in the file system (file, device special file or named pipe)\n"
12359"at path. mode specifies both the permissions to use and the\n"
12360"type of node to be created, being combined (bitwise OR) with one of\n"
12361"S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,\n"
12362"device defines the newly created device special file (probably using\n"
12363"os.makedev()). Otherwise device is ignored.\n"
12364"\n"
12365"If dir_fd is not None, it should be a file descriptor open to a directory,\n"
12366" and path should be relative; path will then be relative to that directory.\n"
12367"dir_fd may not be implemented on your platform.\n"
12368" If it is unavailable, using it will raise a NotImplementedError.");
12369
12370#define OS_MKNOD_METHODDEF \
12371 {"mknod", (PyCFunction)os_mknod, METH_VARARGS|METH_KEYWORDS, os_mknod__doc__},
12372
12373static PyObject *
12374os_mknod_impl(PyModuleDef *module, path_t *path, int mode, int device, int dir_fd);
12375
12376static PyObject *
12377os_mknod(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12378{
12379 PyObject *return_value = NULL;
12380 static char *_keywords[] = {"path", "mode", "device", "dir_fd", NULL};
12381 path_t path = PATH_T_INITIALIZE("mknod", "path", 0, 0);
12382 int mode = 384;
12383 int device = 0;
12384 int dir_fd = DEFAULT_DIR_FD;
12385
12386 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12387 "O&|ii$O&:mknod", _keywords,
12388 path_converter, &path, &mode, &device, MKNODAT_DIR_FD_CONVERTER, &dir_fd))
12389 goto exit;
12390 return_value = os_mknod_impl(module, &path, mode, device, dir_fd);
12391
12392exit:
12393 /* Cleanup for path */
12394 path_cleanup(&path);
12395
12396 return return_value;
12397}
12398
12399static PyObject *
12400os_mknod_impl(PyModuleDef *module, path_t *path, int mode, int device, int dir_fd)
12401/*[clinic end generated code: output=c688739c15ca7bbb input=30e02126aba9732e]*/
12402{
12403 int result;
12404
12405 Py_BEGIN_ALLOW_THREADS
12406#ifdef HAVE_MKNODAT
12407 if (dir_fd != DEFAULT_DIR_FD)
12408 result = mknodat(dir_fd, path->narrow, mode, device);
12409 else
12410#endif
12411 result = mknod(path->narrow, mode, device);
12412 Py_END_ALLOW_THREADS
12413
12414 if (result < 0)
12415 return posix_error();
12416
12417 Py_RETURN_NONE;
12418}
12419#endif /* defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV) */
12420
12421
12422#ifdef HAVE_DEVICE_MACROS
12423/*[clinic input]
12424os.major -> unsigned_int
12425
12426 device: int
12427 /
12428
12429Extracts a device major number from a raw device number.
12430[clinic start generated code]*/
12431
12432PyDoc_STRVAR(os_major__doc__,
12433"major($module, device, /)\n"
12434"--\n"
12435"\n"
12436"Extracts a device major number from a raw device number.");
12437
12438#define OS_MAJOR_METHODDEF \
12439 {"major", (PyCFunction)os_major, METH_VARARGS, os_major__doc__},
12440
12441static unsigned int
12442os_major_impl(PyModuleDef *module, int device);
12443
12444static PyObject *
12445os_major(PyModuleDef *module, PyObject *args)
12446{
12447 PyObject *return_value = NULL;
12448 int device;
12449 unsigned int _return_value;
12450
12451 if (!PyArg_ParseTuple(args,
12452 "i:major",
12453 &device))
12454 goto exit;
12455 _return_value = os_major_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012456 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012457 goto exit;
12458 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12459
12460exit:
12461 return return_value;
12462}
12463
12464static unsigned int
12465os_major_impl(PyModuleDef *module, int device)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012466/*[clinic end generated code: output=52e6743300dcf4ad input=ea48820b7e10d310]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012467{
12468 return major(device);
12469}
12470
12471
12472/*[clinic input]
12473os.minor -> unsigned_int
12474
12475 device: int
12476 /
12477
12478Extracts a device minor number from a raw device number.
12479[clinic start generated code]*/
12480
12481PyDoc_STRVAR(os_minor__doc__,
12482"minor($module, device, /)\n"
12483"--\n"
12484"\n"
12485"Extracts a device minor number from a raw device number.");
12486
12487#define OS_MINOR_METHODDEF \
12488 {"minor", (PyCFunction)os_minor, METH_VARARGS, os_minor__doc__},
12489
12490static unsigned int
12491os_minor_impl(PyModuleDef *module, int device);
12492
12493static PyObject *
12494os_minor(PyModuleDef *module, PyObject *args)
12495{
12496 PyObject *return_value = NULL;
12497 int device;
12498 unsigned int _return_value;
12499
12500 if (!PyArg_ParseTuple(args,
12501 "i:minor",
12502 &device))
12503 goto exit;
12504 _return_value = os_minor_impl(module, device);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012505 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012506 goto exit;
12507 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12508
12509exit:
12510 return return_value;
12511}
12512
12513static unsigned int
12514os_minor_impl(PyModuleDef *module, int device)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012515/*[clinic end generated code: output=aebe4bd7f455b755 input=089733ebbf9754e8]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012516{
12517 return minor(device);
12518}
12519
12520
12521/*[clinic input]
12522os.makedev -> unsigned_int
12523
12524 major: int
12525 minor: int
12526 /
12527
12528Composes a raw device number from the major and minor device numbers.
12529[clinic start generated code]*/
12530
12531PyDoc_STRVAR(os_makedev__doc__,
12532"makedev($module, major, minor, /)\n"
12533"--\n"
12534"\n"
12535"Composes a raw device number from the major and minor device numbers.");
12536
12537#define OS_MAKEDEV_METHODDEF \
12538 {"makedev", (PyCFunction)os_makedev, METH_VARARGS, os_makedev__doc__},
12539
12540static unsigned int
12541os_makedev_impl(PyModuleDef *module, int major, int minor);
12542
12543static PyObject *
12544os_makedev(PyModuleDef *module, PyObject *args)
12545{
12546 PyObject *return_value = NULL;
12547 int major;
12548 int minor;
12549 unsigned int _return_value;
12550
12551 if (!PyArg_ParseTuple(args,
12552 "ii:makedev",
12553 &major, &minor))
12554 goto exit;
12555 _return_value = os_makedev_impl(module, major, minor);
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012556 if ((_return_value == (unsigned int)-1) && PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +100012557 goto exit;
12558 return_value = PyLong_FromUnsignedLong((unsigned long)_return_value);
12559
12560exit:
12561 return return_value;
12562}
12563
12564static unsigned int
12565os_makedev_impl(PyModuleDef *module, int major, int minor)
Larry Hastingsa73cb8a2014-08-05 19:55:21 +100012566/*[clinic end generated code: output=5cb79d9c9eac58b0 input=f55bf7cffb028a08]*/
Larry Hastings2f936352014-08-05 14:04:04 +100012567{
12568 return makedev(major, minor);
12569}
12570#endif /* HAVE_DEVICE_MACROS */
12571
12572
12573#ifdef HAVE_FTRUNCATE
12574/*[clinic input]
12575os.ftruncate
12576
12577 fd: int
12578 length: Py_off_t
12579 /
12580
12581Truncate a file, specified by file descriptor, to a specific length.
12582[clinic start generated code]*/
12583
12584PyDoc_STRVAR(os_ftruncate__doc__,
12585"ftruncate($module, fd, length, /)\n"
12586"--\n"
12587"\n"
12588"Truncate a file, specified by file descriptor, to a specific length.");
12589
12590#define OS_FTRUNCATE_METHODDEF \
12591 {"ftruncate", (PyCFunction)os_ftruncate, METH_VARARGS, os_ftruncate__doc__},
12592
12593static PyObject *
12594os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length);
12595
12596static PyObject *
12597os_ftruncate(PyModuleDef *module, PyObject *args)
12598{
12599 PyObject *return_value = NULL;
12600 int fd;
12601 Py_off_t length;
12602
12603 if (!PyArg_ParseTuple(args,
12604 "iO&:ftruncate",
12605 &fd, Py_off_t_converter, &length))
12606 goto exit;
12607 return_value = os_ftruncate_impl(module, fd, length);
12608
12609exit:
12610 return return_value;
12611}
12612
12613static PyObject *
12614os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length)
12615/*[clinic end generated code: output=62326766cb9b76bf input=63b43641e52818f2]*/
12616{
12617 int result;
12618
12619 Py_BEGIN_ALLOW_THREADS
12620 result = ftruncate(fd, length);
12621 Py_END_ALLOW_THREADS
12622 if (result < 0)
12623 return posix_error();
12624 Py_RETURN_NONE;
12625}
12626#endif /* HAVE_FTRUNCATE */
12627
12628
12629#ifdef HAVE_TRUNCATE
12630/*[clinic input]
12631os.truncate
12632 path: path_t(allow_fd='PATH_HAVE_FTRUNCATE')
12633 length: Py_off_t
12634
12635Truncate a file, specified by path, to a specific length.
12636
12637On some platforms, path may also be specified as an open file descriptor.
12638 If this functionality is unavailable, using it raises an exception.
12639[clinic start generated code]*/
12640
12641PyDoc_STRVAR(os_truncate__doc__,
12642"truncate($module, /, path, length)\n"
12643"--\n"
12644"\n"
12645"Truncate a file, specified by path, to a specific length.\n"
12646"\n"
12647"On some platforms, path may also be specified as an open file descriptor.\n"
12648" If this functionality is unavailable, using it raises an exception.");
12649
12650#define OS_TRUNCATE_METHODDEF \
12651 {"truncate", (PyCFunction)os_truncate, METH_VARARGS|METH_KEYWORDS, os_truncate__doc__},
12652
12653static PyObject *
12654os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length);
12655
12656static PyObject *
12657os_truncate(PyModuleDef *module, PyObject *args, PyObject *kwargs)
12658{
12659 PyObject *return_value = NULL;
12660 static char *_keywords[] = {"path", "length", NULL};
12661 path_t path = PATH_T_INITIALIZE("truncate", "path", 0, PATH_HAVE_FTRUNCATE);
12662 Py_off_t length;
12663
12664 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
12665 "O&O&:truncate", _keywords,
12666 path_converter, &path, Py_off_t_converter, &length))
12667 goto exit;
12668 return_value = os_truncate_impl(module, &path, length);
12669
12670exit:
12671 /* Cleanup for path */
12672 path_cleanup(&path);
12673
12674 return return_value;
12675}
12676
12677static PyObject *
12678os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length)
12679/*[clinic end generated code: output=6bd76262d2e027c6 input=77229cf0b50a9b77]*/
12680{
12681 int result;
12682
12683 Py_BEGIN_ALLOW_THREADS
12684#ifdef HAVE_FTRUNCATE
12685 if (path->fd != -1)
12686 result = ftruncate(path->fd, length);
12687 else
12688#endif
12689 result = truncate(path->narrow, length);
12690 Py_END_ALLOW_THREADS
12691 if (result < 0)
12692 return path_error(path);
12693
12694 Py_RETURN_NONE;
12695}
12696#endif /* HAVE_TRUNCATE */
12697
Ross Lagerwall7807c352011-03-17 20:20:30 +020012698
Victor Stinnerd6b17692014-09-30 12:20:05 +020012699/* Issue #22396: On 32-bit AIX platform, the prototypes of os.posix_fadvise()
12700 and os.posix_fallocate() in system headers are wrong if _LARGE_FILES is
12701 defined, which is the case in Python on AIX. AIX bug report:
12702 http://www-01.ibm.com/support/docview.wss?uid=isg1IV56170 */
12703#if defined(_AIX) && defined(_LARGE_FILES) && !defined(__64BIT__)
12704# define POSIX_FADVISE_AIX_BUG
12705#endif
12706
Victor Stinnerec39e262014-09-30 12:35:58 +020012707
Victor Stinnerd6b17692014-09-30 12:20:05 +020012708#if defined(HAVE_POSIX_FALLOCATE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +100012709/*[clinic input]
12710os.posix_fallocate
12711
12712 fd: int
12713 offset: Py_off_t
12714 length: Py_off_t
12715 /
12716
12717Ensure a file has allocated at least a particular number of bytes on disk.
12718
12719Ensure that the file specified by fd encompasses a range of bytes
12720starting at offset bytes from the beginning and continuing for length bytes.
12721[clinic start generated code]*/
12722
12723PyDoc_STRVAR(os_posix_fallocate__doc__,
12724"posix_fallocate($module, fd, offset, length, /)\n"
12725"--\n"
12726"\n"
12727"Ensure a file has allocated at least a particular number of bytes on disk.\n"
12728"\n"
12729"Ensure that the file specified by fd encompasses a range of bytes\n"
12730"starting at offset bytes from the beginning and continuing for length bytes.");
12731
12732#define OS_POSIX_FALLOCATE_METHODDEF \
12733 {"posix_fallocate", (PyCFunction)os_posix_fallocate, METH_VARARGS, os_posix_fallocate__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012734
12735static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012736os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012737
Larry Hastings2f936352014-08-05 14:04:04 +100012738static PyObject *
12739os_posix_fallocate(PyModuleDef *module, PyObject *args)
12740{
12741 PyObject *return_value = NULL;
12742 int fd;
12743 Py_off_t offset;
12744 Py_off_t length;
12745
12746 if (!PyArg_ParseTuple(args,
12747 "iO&O&:posix_fallocate",
12748 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length))
12749 goto exit;
12750 return_value = os_posix_fallocate_impl(module, fd, offset, length);
12751
12752exit:
12753 return return_value;
12754}
12755
12756static PyObject *
12757os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length)
12758/*[clinic end generated code: output=0cd702d2065c79db input=d7a2ef0ab2ca52fb]*/
12759{
12760 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012761
12762 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012763 result = posix_fallocate(fd, offset, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012764 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012765 if (result != 0) {
12766 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012767 return posix_error();
12768 }
12769 Py_RETURN_NONE;
12770}
Victor Stinnerec39e262014-09-30 12:35:58 +020012771#endif /* HAVE_POSIX_FALLOCATE) && !POSIX_FADVISE_AIX_BUG */
Larry Hastings2f936352014-08-05 14:04:04 +100012772
Ross Lagerwall7807c352011-03-17 20:20:30 +020012773
Victor Stinnerd6b17692014-09-30 12:20:05 +020012774#if defined(HAVE_POSIX_FADVISE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +100012775/*[clinic input]
12776os.posix_fadvise
12777
12778 fd: int
12779 offset: Py_off_t
12780 length: Py_off_t
12781 advice: int
12782 /
12783
12784Announce an intention to access data in a specific pattern.
12785
12786Announce an intention to access data in a specific pattern, thus allowing
12787the kernel to make optimizations.
12788The advice applies to the region of the file specified by fd starting at
12789offset and continuing for length bytes.
12790advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,
12791POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or
12792POSIX_FADV_DONTNEED.
12793[clinic start generated code]*/
12794
12795PyDoc_STRVAR(os_posix_fadvise__doc__,
12796"posix_fadvise($module, fd, offset, length, advice, /)\n"
12797"--\n"
12798"\n"
12799"Announce an intention to access data in a specific pattern.\n"
12800"\n"
12801"Announce an intention to access data in a specific pattern, thus allowing\n"
12802"the kernel to make optimizations.\n"
12803"The advice applies to the region of the file specified by fd starting at\n"
12804"offset and continuing for length bytes.\n"
12805"advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,\n"
12806"POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or\n"
12807"POSIX_FADV_DONTNEED.");
12808
12809#define OS_POSIX_FADVISE_METHODDEF \
12810 {"posix_fadvise", (PyCFunction)os_posix_fadvise, METH_VARARGS, os_posix_fadvise__doc__},
Ross Lagerwall7807c352011-03-17 20:20:30 +020012811
12812static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012813os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012814
Larry Hastings2f936352014-08-05 14:04:04 +100012815static PyObject *
12816os_posix_fadvise(PyModuleDef *module, PyObject *args)
12817{
12818 PyObject *return_value = NULL;
12819 int fd;
12820 Py_off_t offset;
12821 Py_off_t length;
12822 int advice;
12823
12824 if (!PyArg_ParseTuple(args,
12825 "iO&O&i:posix_fadvise",
12826 &fd, Py_off_t_converter, &offset, Py_off_t_converter, &length, &advice))
12827 goto exit;
12828 return_value = os_posix_fadvise_impl(module, fd, offset, length, advice);
12829
12830exit:
12831 return return_value;
12832}
12833
12834static PyObject *
12835os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset, Py_off_t length, int advice)
12836/*[clinic end generated code: output=dad93f32c04dd4f7 input=0fbe554edc2f04b5]*/
12837{
12838 int result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012839
12840 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012841 result = posix_fadvise(fd, offset, length, advice);
Ross Lagerwall7807c352011-03-17 20:20:30 +020012842 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100012843 if (result != 0) {
12844 errno = result;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012845 return posix_error();
12846 }
12847 Py_RETURN_NONE;
12848}
Victor Stinnerec39e262014-09-30 12:35:58 +020012849#endif /* HAVE_POSIX_FADVISE && !POSIX_FADVISE_AIX_BUG */
Ross Lagerwall7807c352011-03-17 20:20:30 +020012850
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012851#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000012852
Fred Drake762e2061999-08-26 17:23:54 +000012853/* Save putenv() parameters as values here, so we can collect them when they
12854 * get re-set with another call for the same key. */
12855static PyObject *posix_putenv_garbage;
12856
Larry Hastings2f936352014-08-05 14:04:04 +100012857static void
12858posix_putenv_garbage_setitem(PyObject *name, PyObject *value)
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012859{
Larry Hastings2f936352014-08-05 14:04:04 +100012860 /* Install the first arg and newstr in posix_putenv_garbage;
12861 * this will cause previous value to be collected. This has to
12862 * happen after the real putenv() call because the old value
12863 * was still accessible until then. */
12864 if (PyDict_SetItem(posix_putenv_garbage, name, value))
12865 /* really not much we can do; just leak */
12866 PyErr_Clear();
12867 else
12868 Py_DECREF(value);
12869}
12870
12871
Thomas Hellerf78f12a2007-11-08 19:33:05 +000012872#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100012873/*[clinic input]
12874os.putenv
12875
12876 name: unicode
12877 value: unicode
12878 /
12879
12880Change or add an environment variable.
12881[clinic start generated code]*/
12882
12883PyDoc_STRVAR(os_putenv__doc__,
12884"putenv($module, name, value, /)\n"
12885"--\n"
12886"\n"
12887"Change or add an environment variable.");
12888
12889#define OS_PUTENV_METHODDEF \
12890 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
12891
12892static PyObject *
12893os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
12894
12895static PyObject *
12896os_putenv(PyModuleDef *module, PyObject *args)
12897{
12898 PyObject *return_value = NULL;
12899 PyObject *name;
12900 PyObject *value;
Victor Stinner65170952011-11-22 22:16:17 +010012901
Victor Stinner8c62be82010-05-06 00:08:46 +000012902 if (!PyArg_ParseTuple(args,
Larry Hastings2f936352014-08-05 14:04:04 +100012903 "UU:putenv",
12904 &name, &value))
12905 goto exit;
12906 return_value = os_putenv_impl(module, name, value);
Guido van Rossumd48f2521997-12-05 22:19:34 +000012907
Larry Hastings2f936352014-08-05 14:04:04 +100012908exit:
12909 return return_value;
12910}
12911
12912static PyObject *
12913os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
12914/*[clinic end generated code: output=5ce9ef9b15606e7e input=ba586581c2e6105f]*/
12915{
12916 wchar_t *env;
12917
12918 PyObject *unicode = PyUnicode_FromFormat("%U=%U", name, value);
12919 if (unicode == NULL) {
Victor Stinner84ae1182010-05-06 22:05:07 +000012920 PyErr_NoMemory();
Larry Hastings2f936352014-08-05 14:04:04 +100012921 return NULL;
Victor Stinner84ae1182010-05-06 22:05:07 +000012922 }
Larry Hastings2f936352014-08-05 14:04:04 +100012923 if (_MAX_ENV < PyUnicode_GET_LENGTH(unicode)) {
Victor Stinner65170952011-11-22 22:16:17 +010012924 PyErr_Format(PyExc_ValueError,
12925 "the environment variable is longer than %u characters",
12926 _MAX_ENV);
12927 goto error;
12928 }
12929
Larry Hastings2f936352014-08-05 14:04:04 +100012930 env = PyUnicode_AsUnicode(unicode);
12931 if (env == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +020012932 goto error;
Larry Hastings2f936352014-08-05 14:04:04 +100012933 if (_wputenv(env)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000012934 posix_error();
Victor Stinner84ae1182010-05-06 22:05:07 +000012935 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +000012936 }
Guido van Rossuma4916fa1996-05-23 22:58:55 +000012937
Larry Hastings2f936352014-08-05 14:04:04 +100012938 posix_putenv_garbage_setitem(name, unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012939 Py_RETURN_NONE;
12940
12941error:
Larry Hastings2f936352014-08-05 14:04:04 +100012942 Py_DECREF(unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +000012943 return NULL;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000012944}
Larry Hastings2f936352014-08-05 14:04:04 +100012945#else /* MS_WINDOWS */
12946/*[clinic input]
12947os.putenv
Guido van Rossumb6a47161997-09-15 22:54:34 +000012948
Larry Hastings2f936352014-08-05 14:04:04 +100012949 name: FSConverter
12950 value: FSConverter
12951 /
12952
12953Change or add an environment variable.
12954[clinic start generated code]*/
12955
12956PyDoc_STRVAR(os_putenv__doc__,
12957"putenv($module, name, value, /)\n"
12958"--\n"
12959"\n"
12960"Change or add an environment variable.");
12961
12962#define OS_PUTENV_METHODDEF \
12963 {"putenv", (PyCFunction)os_putenv, METH_VARARGS, os_putenv__doc__},
Guido van Rossumc524d952001-10-19 01:31:59 +000012964
12965static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100012966os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value);
12967
12968static PyObject *
12969os_putenv(PyModuleDef *module, PyObject *args)
Guido van Rossumc524d952001-10-19 01:31:59 +000012970{
Larry Hastings2f936352014-08-05 14:04:04 +100012971 PyObject *return_value = NULL;
12972 PyObject *name = NULL;
12973 PyObject *value = NULL;
12974
12975 if (!PyArg_ParseTuple(args,
12976 "O&O&:putenv",
12977 PyUnicode_FSConverter, &name, PyUnicode_FSConverter, &value))
12978 goto exit;
12979 return_value = os_putenv_impl(module, name, value);
12980
12981exit:
12982 /* Cleanup for name */
12983 Py_XDECREF(name);
12984 /* Cleanup for value */
12985 Py_XDECREF(value);
12986
12987 return return_value;
12988}
12989
12990static PyObject *
12991os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
12992/*[clinic end generated code: output=85ab223393dc7afd input=a97bc6152f688d31]*/
12993{
12994 PyObject *bytes = NULL;
12995 char *env;
12996 char *name_string = PyBytes_AsString(name);
12997 char *value_string = PyBytes_AsString(value);
12998
12999 bytes = PyBytes_FromFormat("%s=%s", name_string, value_string);
13000 if (bytes == NULL) {
13001 PyErr_NoMemory();
13002 return NULL;
13003 }
13004
13005 env = PyBytes_AS_STRING(bytes);
13006 if (putenv(env)) {
13007 Py_DECREF(bytes);
13008 return posix_error();
13009 }
13010
13011 posix_putenv_garbage_setitem(name, bytes);
13012 Py_RETURN_NONE;
13013}
13014#endif /* MS_WINDOWS */
13015#endif /* HAVE_PUTENV */
13016
13017
13018#ifdef HAVE_UNSETENV
13019/*[clinic input]
13020os.unsetenv
13021 name: FSConverter
13022 /
13023
13024Delete an environment variable.
13025[clinic start generated code]*/
13026
13027PyDoc_STRVAR(os_unsetenv__doc__,
13028"unsetenv($module, name, /)\n"
13029"--\n"
13030"\n"
13031"Delete an environment variable.");
13032
13033#define OS_UNSETENV_METHODDEF \
13034 {"unsetenv", (PyCFunction)os_unsetenv, METH_VARARGS, os_unsetenv__doc__},
13035
13036static PyObject *
13037os_unsetenv_impl(PyModuleDef *module, PyObject *name);
13038
13039static PyObject *
13040os_unsetenv(PyModuleDef *module, PyObject *args)
13041{
13042 PyObject *return_value = NULL;
13043 PyObject *name = NULL;
13044
13045 if (!PyArg_ParseTuple(args,
13046 "O&:unsetenv",
13047 PyUnicode_FSConverter, &name))
13048 goto exit;
13049 return_value = os_unsetenv_impl(module, name);
13050
13051exit:
13052 /* Cleanup for name */
13053 Py_XDECREF(name);
13054
13055 return return_value;
13056}
13057
13058static PyObject *
13059os_unsetenv_impl(PyModuleDef *module, PyObject *name)
13060/*[clinic end generated code: output=91318c995f9a0767 input=2bb5288a599c7107]*/
13061{
Victor Stinner984890f2011-11-24 13:53:38 +010013062#ifndef HAVE_BROKEN_UNSETENV
Victor Stinner60b385e2011-11-22 22:01:28 +010013063 int err;
Victor Stinner984890f2011-11-24 13:53:38 +010013064#endif
Victor Stinner84ae1182010-05-06 22:05:07 +000013065
Victor Stinner984890f2011-11-24 13:53:38 +010013066#ifdef HAVE_BROKEN_UNSETENV
13067 unsetenv(PyBytes_AS_STRING(name));
13068#else
Victor Stinner65170952011-11-22 22:16:17 +010013069 err = unsetenv(PyBytes_AS_STRING(name));
Larry Hastings2f936352014-08-05 14:04:04 +100013070 if (err)
Victor Stinner60b385e2011-11-22 22:01:28 +010013071 return posix_error();
Victor Stinner984890f2011-11-24 13:53:38 +010013072#endif
Guido van Rossumc524d952001-10-19 01:31:59 +000013073
Victor Stinner8c62be82010-05-06 00:08:46 +000013074 /* Remove the key from posix_putenv_garbage;
13075 * this will cause it to be collected. This has to
13076 * happen after the real unsetenv() call because the
13077 * old value was still accessible until then.
13078 */
Victor Stinner65170952011-11-22 22:16:17 +010013079 if (PyDict_DelItem(posix_putenv_garbage, name)) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013080 /* really not much we can do; just leak */
13081 PyErr_Clear();
13082 }
Victor Stinner84ae1182010-05-06 22:05:07 +000013083 Py_RETURN_NONE;
Guido van Rossumc524d952001-10-19 01:31:59 +000013084}
Larry Hastings2f936352014-08-05 14:04:04 +100013085#endif /* HAVE_UNSETENV */
Guido van Rossumc524d952001-10-19 01:31:59 +000013086
Larry Hastings2f936352014-08-05 14:04:04 +100013087
13088/*[clinic input]
13089os.strerror
13090
13091 code: int
13092 /
13093
13094Translate an error code to a message string.
13095[clinic start generated code]*/
13096
13097PyDoc_STRVAR(os_strerror__doc__,
13098"strerror($module, code, /)\n"
13099"--\n"
13100"\n"
13101"Translate an error code to a message string.");
13102
13103#define OS_STRERROR_METHODDEF \
13104 {"strerror", (PyCFunction)os_strerror, METH_VARARGS, os_strerror__doc__},
Guido van Rossumb6a47161997-09-15 22:54:34 +000013105
Guido van Rossumf68d8e52001-04-14 17:55:09 +000013106static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013107os_strerror_impl(PyModuleDef *module, int code);
13108
13109static PyObject *
13110os_strerror(PyModuleDef *module, PyObject *args)
Guido van Rossumb6a47161997-09-15 22:54:34 +000013111{
Larry Hastings2f936352014-08-05 14:04:04 +100013112 PyObject *return_value = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013113 int code;
Larry Hastings2f936352014-08-05 14:04:04 +100013114
13115 if (!PyArg_ParseTuple(args,
13116 "i:strerror",
13117 &code))
13118 goto exit;
13119 return_value = os_strerror_impl(module, code);
13120
13121exit:
13122 return return_value;
13123}
13124
13125static PyObject *
13126os_strerror_impl(PyModuleDef *module, int code)
13127/*[clinic end generated code: output=8665c70bb2ca4720 input=75a8673d97915a91]*/
13128{
13129 char *message = strerror(code);
Victor Stinner8c62be82010-05-06 00:08:46 +000013130 if (message == NULL) {
13131 PyErr_SetString(PyExc_ValueError,
13132 "strerror() argument out of range");
13133 return NULL;
13134 }
Victor Stinner1b579672011-12-17 05:47:23 +010013135 return PyUnicode_DecodeLocale(message, "surrogateescape");
Guido van Rossumb6a47161997-09-15 22:54:34 +000013136}
Guido van Rossumb6a47161997-09-15 22:54:34 +000013137
Guido van Rossumf1af3fe1996-07-23 19:18:10 +000013138
Guido van Rossumc9641791998-08-04 15:26:23 +000013139#ifdef HAVE_SYS_WAIT_H
Fred Drake106c1a02002-04-23 15:58:02 +000013140#ifdef WCOREDUMP
Larry Hastings2f936352014-08-05 14:04:04 +100013141/*[clinic input]
13142os.WCOREDUMP -> bool
13143
13144 status: int
13145 /
13146
13147Return True if the process returning status was dumped to a core file.
13148[clinic start generated code]*/
13149
13150PyDoc_STRVAR(os_WCOREDUMP__doc__,
13151"WCOREDUMP($module, status, /)\n"
13152"--\n"
13153"\n"
13154"Return True if the process returning status was dumped to a core file.");
13155
13156#define OS_WCOREDUMP_METHODDEF \
13157 {"WCOREDUMP", (PyCFunction)os_WCOREDUMP, METH_VARARGS, os_WCOREDUMP__doc__},
13158
13159static int
13160os_WCOREDUMP_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013161
13162static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013163os_WCOREDUMP(PyModuleDef *module, PyObject *args)
Fred Drake106c1a02002-04-23 15:58:02 +000013164{
Larry Hastings2f936352014-08-05 14:04:04 +100013165 PyObject *return_value = NULL;
13166 int status;
13167 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013168
Larry Hastings2f936352014-08-05 14:04:04 +100013169 if (!PyArg_ParseTuple(args,
13170 "i:WCOREDUMP",
13171 &status))
13172 goto exit;
13173 _return_value = os_WCOREDUMP_impl(module, status);
13174 if ((_return_value == -1) && PyErr_Occurred())
13175 goto exit;
13176 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013177
Larry Hastings2f936352014-08-05 14:04:04 +100013178exit:
13179 return return_value;
13180}
13181
13182static int
13183os_WCOREDUMP_impl(PyModuleDef *module, int status)
13184/*[clinic end generated code: output=e04d55c09c299828 input=8b05e7ab38528d04]*/
13185{
13186 WAIT_TYPE wait_status;
13187 WAIT_STATUS_INT(wait_status) = status;
13188 return WCOREDUMP(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013189}
13190#endif /* WCOREDUMP */
13191
Larry Hastings2f936352014-08-05 14:04:04 +100013192
Fred Drake106c1a02002-04-23 15:58:02 +000013193#ifdef WIFCONTINUED
Larry Hastings2f936352014-08-05 14:04:04 +100013194/*[clinic input]
13195os.WIFCONTINUED -> bool
13196
13197 status: int
13198
13199Return True if a particular process was continued from a job control stop.
13200
13201Return True if the process returning status was continued from a
13202job control stop.
13203[clinic start generated code]*/
13204
13205PyDoc_STRVAR(os_WIFCONTINUED__doc__,
13206"WIFCONTINUED($module, /, status)\n"
13207"--\n"
13208"\n"
13209"Return True if a particular process was continued from a job control stop.\n"
13210"\n"
13211"Return True if the process returning status was continued from a\n"
13212"job control stop.");
13213
13214#define OS_WIFCONTINUED_METHODDEF \
13215 {"WIFCONTINUED", (PyCFunction)os_WIFCONTINUED, METH_VARARGS|METH_KEYWORDS, os_WIFCONTINUED__doc__},
13216
13217static int
13218os_WIFCONTINUED_impl(PyModuleDef *module, int status);
Fred Drake106c1a02002-04-23 15:58:02 +000013219
13220static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013221os_WIFCONTINUED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drake106c1a02002-04-23 15:58:02 +000013222{
Larry Hastings2f936352014-08-05 14:04:04 +100013223 PyObject *return_value = NULL;
13224 static char *_keywords[] = {"status", NULL};
13225 int status;
13226 int _return_value;
Fred Drake106c1a02002-04-23 15:58:02 +000013227
Larry Hastings2f936352014-08-05 14:04:04 +100013228 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13229 "i:WIFCONTINUED", _keywords,
13230 &status))
13231 goto exit;
13232 _return_value = os_WIFCONTINUED_impl(module, status);
13233 if ((_return_value == -1) && PyErr_Occurred())
13234 goto exit;
13235 return_value = PyBool_FromLong((long)_return_value);
Fred Drake106c1a02002-04-23 15:58:02 +000013236
Larry Hastings2f936352014-08-05 14:04:04 +100013237exit:
13238 return return_value;
13239}
13240
13241static int
13242os_WIFCONTINUED_impl(PyModuleDef *module, int status)
13243/*[clinic end generated code: output=9c4e6105a4520ab5 input=e777e7d38eb25bd9]*/
13244{
13245 WAIT_TYPE wait_status;
13246 WAIT_STATUS_INT(wait_status) = status;
13247 return WIFCONTINUED(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +000013248}
13249#endif /* WIFCONTINUED */
13250
Larry Hastings2f936352014-08-05 14:04:04 +100013251
Guido van Rossumc9641791998-08-04 15:26:23 +000013252#ifdef WIFSTOPPED
Larry Hastings2f936352014-08-05 14:04:04 +100013253/*[clinic input]
13254os.WIFSTOPPED -> bool
13255
13256 status: int
13257
13258Return True if the process returning status was stopped.
13259[clinic start generated code]*/
13260
13261PyDoc_STRVAR(os_WIFSTOPPED__doc__,
13262"WIFSTOPPED($module, /, status)\n"
13263"--\n"
13264"\n"
13265"Return True if the process returning status was stopped.");
13266
13267#define OS_WIFSTOPPED_METHODDEF \
13268 {"WIFSTOPPED", (PyCFunction)os_WIFSTOPPED, METH_VARARGS|METH_KEYWORDS, os_WIFSTOPPED__doc__},
13269
13270static int
13271os_WIFSTOPPED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013272
13273static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013274os_WIFSTOPPED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013275{
Larry Hastings2f936352014-08-05 14:04:04 +100013276 PyObject *return_value = NULL;
13277 static char *_keywords[] = {"status", NULL};
13278 int status;
13279 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013280
Larry Hastings2f936352014-08-05 14:04:04 +100013281 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13282 "i:WIFSTOPPED", _keywords,
13283 &status))
13284 goto exit;
13285 _return_value = os_WIFSTOPPED_impl(module, status);
13286 if ((_return_value == -1) && PyErr_Occurred())
13287 goto exit;
13288 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013289
Larry Hastings2f936352014-08-05 14:04:04 +100013290exit:
13291 return return_value;
13292}
13293
13294static int
13295os_WIFSTOPPED_impl(PyModuleDef *module, int status)
13296/*[clinic end generated code: output=e0de2da8ec9593ff input=043cb7f1289ef904]*/
13297{
13298 WAIT_TYPE wait_status;
13299 WAIT_STATUS_INT(wait_status) = status;
13300 return WIFSTOPPED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013301}
13302#endif /* WIFSTOPPED */
13303
Larry Hastings2f936352014-08-05 14:04:04 +100013304
Guido van Rossumc9641791998-08-04 15:26:23 +000013305#ifdef WIFSIGNALED
Larry Hastings2f936352014-08-05 14:04:04 +100013306/*[clinic input]
13307os.WIFSIGNALED -> bool
13308
13309 status: int
13310
13311Return True if the process returning status was terminated by a signal.
13312[clinic start generated code]*/
13313
13314PyDoc_STRVAR(os_WIFSIGNALED__doc__,
13315"WIFSIGNALED($module, /, status)\n"
13316"--\n"
13317"\n"
13318"Return True if the process returning status was terminated by a signal.");
13319
13320#define OS_WIFSIGNALED_METHODDEF \
13321 {"WIFSIGNALED", (PyCFunction)os_WIFSIGNALED, METH_VARARGS|METH_KEYWORDS, os_WIFSIGNALED__doc__},
13322
13323static int
13324os_WIFSIGNALED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013325
13326static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013327os_WIFSIGNALED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013328{
Larry Hastings2f936352014-08-05 14:04:04 +100013329 PyObject *return_value = NULL;
13330 static char *_keywords[] = {"status", NULL};
13331 int status;
13332 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013333
Larry Hastings2f936352014-08-05 14:04:04 +100013334 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13335 "i:WIFSIGNALED", _keywords,
13336 &status))
13337 goto exit;
13338 _return_value = os_WIFSIGNALED_impl(module, status);
13339 if ((_return_value == -1) && PyErr_Occurred())
13340 goto exit;
13341 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013342
Larry Hastings2f936352014-08-05 14:04:04 +100013343exit:
13344 return return_value;
13345}
13346
13347static int
13348os_WIFSIGNALED_impl(PyModuleDef *module, int status)
13349/*[clinic end generated code: output=f14d106558f406be input=d55ba7cc9ce5dc43]*/
13350{
13351 WAIT_TYPE wait_status;
13352 WAIT_STATUS_INT(wait_status) = status;
13353 return WIFSIGNALED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013354}
13355#endif /* WIFSIGNALED */
13356
Larry Hastings2f936352014-08-05 14:04:04 +100013357
Guido van Rossumc9641791998-08-04 15:26:23 +000013358#ifdef WIFEXITED
Larry Hastings2f936352014-08-05 14:04:04 +100013359/*[clinic input]
13360os.WIFEXITED -> bool
13361
13362 status: int
13363
13364Return True if the process returning status exited via the exit() system call.
13365[clinic start generated code]*/
13366
13367PyDoc_STRVAR(os_WIFEXITED__doc__,
13368"WIFEXITED($module, /, status)\n"
13369"--\n"
13370"\n"
13371"Return True if the process returning status exited via the exit() system call.");
13372
13373#define OS_WIFEXITED_METHODDEF \
13374 {"WIFEXITED", (PyCFunction)os_WIFEXITED, METH_VARARGS|METH_KEYWORDS, os_WIFEXITED__doc__},
13375
13376static int
13377os_WIFEXITED_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013378
13379static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013380os_WIFEXITED(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013381{
Larry Hastings2f936352014-08-05 14:04:04 +100013382 PyObject *return_value = NULL;
13383 static char *_keywords[] = {"status", NULL};
13384 int status;
13385 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013386
Larry Hastings2f936352014-08-05 14:04:04 +100013387 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13388 "i:WIFEXITED", _keywords,
13389 &status))
13390 goto exit;
13391 _return_value = os_WIFEXITED_impl(module, status);
13392 if ((_return_value == -1) && PyErr_Occurred())
13393 goto exit;
13394 return_value = PyBool_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013395
Larry Hastings2f936352014-08-05 14:04:04 +100013396exit:
13397 return return_value;
13398}
13399
13400static int
13401os_WIFEXITED_impl(PyModuleDef *module, int status)
13402/*[clinic end generated code: output=2f76087d53721255 input=d63775a6791586c0]*/
13403{
13404 WAIT_TYPE wait_status;
13405 WAIT_STATUS_INT(wait_status) = status;
13406 return WIFEXITED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013407}
13408#endif /* WIFEXITED */
13409
Larry Hastings2f936352014-08-05 14:04:04 +100013410
Guido van Rossum54ecc3d1999-01-27 17:53:11 +000013411#ifdef WEXITSTATUS
Larry Hastings2f936352014-08-05 14:04:04 +100013412/*[clinic input]
13413os.WEXITSTATUS -> int
13414
13415 status: int
13416
13417Return the process return code from status.
13418[clinic start generated code]*/
13419
13420PyDoc_STRVAR(os_WEXITSTATUS__doc__,
13421"WEXITSTATUS($module, /, status)\n"
13422"--\n"
13423"\n"
13424"Return the process return code from status.");
13425
13426#define OS_WEXITSTATUS_METHODDEF \
13427 {"WEXITSTATUS", (PyCFunction)os_WEXITSTATUS, METH_VARARGS|METH_KEYWORDS, os_WEXITSTATUS__doc__},
13428
13429static int
13430os_WEXITSTATUS_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013431
13432static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013433os_WEXITSTATUS(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013434{
Larry Hastings2f936352014-08-05 14:04:04 +100013435 PyObject *return_value = NULL;
13436 static char *_keywords[] = {"status", NULL};
13437 int status;
13438 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013439
Larry Hastings2f936352014-08-05 14:04:04 +100013440 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13441 "i:WEXITSTATUS", _keywords,
13442 &status))
13443 goto exit;
13444 _return_value = os_WEXITSTATUS_impl(module, status);
13445 if ((_return_value == -1) && PyErr_Occurred())
13446 goto exit;
13447 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013448
Larry Hastings2f936352014-08-05 14:04:04 +100013449exit:
13450 return return_value;
13451}
13452
13453static int
13454os_WEXITSTATUS_impl(PyModuleDef *module, int status)
13455/*[clinic end generated code: output=13b6c270e2a326b1 input=e1fb4944e377585b]*/
13456{
13457 WAIT_TYPE wait_status;
13458 WAIT_STATUS_INT(wait_status) = status;
13459 return WEXITSTATUS(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013460}
13461#endif /* WEXITSTATUS */
13462
Larry Hastings2f936352014-08-05 14:04:04 +100013463
Guido van Rossumc9641791998-08-04 15:26:23 +000013464#ifdef WTERMSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013465/*[clinic input]
13466os.WTERMSIG -> int
13467
13468 status: int
13469
13470Return the signal that terminated the process that provided the status value.
13471[clinic start generated code]*/
13472
13473PyDoc_STRVAR(os_WTERMSIG__doc__,
13474"WTERMSIG($module, /, status)\n"
13475"--\n"
13476"\n"
13477"Return the signal that terminated the process that provided the status value.");
13478
13479#define OS_WTERMSIG_METHODDEF \
13480 {"WTERMSIG", (PyCFunction)os_WTERMSIG, METH_VARARGS|METH_KEYWORDS, os_WTERMSIG__doc__},
13481
13482static int
13483os_WTERMSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013484
13485static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013486os_WTERMSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013487{
Larry Hastings2f936352014-08-05 14:04:04 +100013488 PyObject *return_value = NULL;
13489 static char *_keywords[] = {"status", NULL};
13490 int status;
13491 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013492
Larry Hastings2f936352014-08-05 14:04:04 +100013493 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13494 "i:WTERMSIG", _keywords,
13495 &status))
13496 goto exit;
13497 _return_value = os_WTERMSIG_impl(module, status);
13498 if ((_return_value == -1) && PyErr_Occurred())
13499 goto exit;
13500 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013501
Larry Hastings2f936352014-08-05 14:04:04 +100013502exit:
13503 return return_value;
13504}
13505
13506static int
13507os_WTERMSIG_impl(PyModuleDef *module, int status)
13508/*[clinic end generated code: output=bf1fd4b002d0a9ed input=727fd7f84ec3f243]*/
13509{
13510 WAIT_TYPE wait_status;
13511 WAIT_STATUS_INT(wait_status) = status;
13512 return WTERMSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013513}
13514#endif /* WTERMSIG */
13515
Larry Hastings2f936352014-08-05 14:04:04 +100013516
Guido van Rossumc9641791998-08-04 15:26:23 +000013517#ifdef WSTOPSIG
Larry Hastings2f936352014-08-05 14:04:04 +100013518/*[clinic input]
13519os.WSTOPSIG -> int
13520
13521 status: int
13522
13523Return the signal that stopped the process that provided the status value.
13524[clinic start generated code]*/
13525
13526PyDoc_STRVAR(os_WSTOPSIG__doc__,
13527"WSTOPSIG($module, /, status)\n"
13528"--\n"
13529"\n"
13530"Return the signal that stopped the process that provided the status value.");
13531
13532#define OS_WSTOPSIG_METHODDEF \
13533 {"WSTOPSIG", (PyCFunction)os_WSTOPSIG, METH_VARARGS|METH_KEYWORDS, os_WSTOPSIG__doc__},
13534
13535static int
13536os_WSTOPSIG_impl(PyModuleDef *module, int status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013537
13538static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013539os_WSTOPSIG(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Guido van Rossumc9641791998-08-04 15:26:23 +000013540{
Larry Hastings2f936352014-08-05 14:04:04 +100013541 PyObject *return_value = NULL;
13542 static char *_keywords[] = {"status", NULL};
13543 int status;
13544 int _return_value;
Tim Peters5aa91602002-01-30 05:46:57 +000013545
Larry Hastings2f936352014-08-05 14:04:04 +100013546 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13547 "i:WSTOPSIG", _keywords,
13548 &status))
13549 goto exit;
13550 _return_value = os_WSTOPSIG_impl(module, status);
13551 if ((_return_value == -1) && PyErr_Occurred())
13552 goto exit;
13553 return_value = PyLong_FromLong((long)_return_value);
Tim Peters5aa91602002-01-30 05:46:57 +000013554
Larry Hastings2f936352014-08-05 14:04:04 +100013555exit:
13556 return return_value;
13557}
13558
13559static int
13560os_WSTOPSIG_impl(PyModuleDef *module, int status)
13561/*[clinic end generated code: output=92e1647d29ee0549 input=46ebf1d1b293c5c1]*/
13562{
13563 WAIT_TYPE wait_status;
13564 WAIT_STATUS_INT(wait_status) = status;
13565 return WSTOPSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +000013566}
13567#endif /* WSTOPSIG */
Guido van Rossumc9641791998-08-04 15:26:23 +000013568#endif /* HAVE_SYS_WAIT_H */
13569
13570
Larry Hastings2f936352014-08-05 14:04:04 +100013571#ifndef OS_WCOREDUMP_METHODDEF
13572#define OS_WCOREDUMP_METHODDEF
13573#endif /* OS_WCOREDUMP_METHODDEF */
13574
13575#ifndef OS_WIFCONTINUED_METHODDEF
13576#define OS_WIFCONTINUED_METHODDEF
13577#endif /* OS_WIFCONTINUED_METHODDEF */
13578
13579#ifndef OS_WIFSTOPPED_METHODDEF
13580#define OS_WIFSTOPPED_METHODDEF
13581#endif /* OS_WIFSTOPPED_METHODDEF */
13582
13583#ifndef OS_WIFSIGNALED_METHODDEF
13584#define OS_WIFSIGNALED_METHODDEF
13585#endif /* OS_WIFSIGNALED_METHODDEF */
13586
13587#ifndef OS_WIFEXITED_METHODDEF
13588#define OS_WIFEXITED_METHODDEF
13589#endif /* OS_WIFEXITED_METHODDEF */
13590
13591#ifndef OS_WEXITSTATUS_METHODDEF
13592#define OS_WEXITSTATUS_METHODDEF
13593#endif /* OS_WEXITSTATUS_METHODDEF */
13594
13595#ifndef OS_WTERMSIG_METHODDEF
13596#define OS_WTERMSIG_METHODDEF
13597#endif /* OS_WTERMSIG_METHODDEF */
13598
13599#ifndef OS_WSTOPSIG_METHODDEF
13600#define OS_WSTOPSIG_METHODDEF
13601#endif /* OS_WSTOPSIG_METHODDEF */
13602
13603
Thomas Wouters477c8d52006-05-27 19:21:47 +000013604#if defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossumd5753e11999-10-19 13:29:23 +000013605#ifdef _SCO_DS
13606/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
13607 needed definitions in sys/statvfs.h */
13608#define _SVID3
13609#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000013610#include <sys/statvfs.h>
13611
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013612static PyObject*
13613_pystatvfs_fromstructstatvfs(struct statvfs st) {
Victor Stinner8c62be82010-05-06 00:08:46 +000013614 PyObject *v = PyStructSequence_New(&StatVFSResultType);
13615 if (v == NULL)
13616 return NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013617
13618#if !defined(HAVE_LARGEFILE_SUPPORT)
Victor Stinner8c62be82010-05-06 00:08:46 +000013619 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13620 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13621 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long) st.f_blocks));
13622 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long) st.f_bfree));
13623 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong((long) st.f_bavail));
13624 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong((long) st.f_files));
13625 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong((long) st.f_ffree));
13626 PyStructSequence_SET_ITEM(v, 7, PyLong_FromLong((long) st.f_favail));
13627 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13628 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013629#else
Victor Stinner8c62be82010-05-06 00:08:46 +000013630 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
13631 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
13632 PyStructSequence_SET_ITEM(v, 2,
13633 PyLong_FromLongLong((PY_LONG_LONG) st.f_blocks));
13634 PyStructSequence_SET_ITEM(v, 3,
13635 PyLong_FromLongLong((PY_LONG_LONG) st.f_bfree));
13636 PyStructSequence_SET_ITEM(v, 4,
13637 PyLong_FromLongLong((PY_LONG_LONG) st.f_bavail));
13638 PyStructSequence_SET_ITEM(v, 5,
13639 PyLong_FromLongLong((PY_LONG_LONG) st.f_files));
13640 PyStructSequence_SET_ITEM(v, 6,
13641 PyLong_FromLongLong((PY_LONG_LONG) st.f_ffree));
13642 PyStructSequence_SET_ITEM(v, 7,
13643 PyLong_FromLongLong((PY_LONG_LONG) st.f_favail));
13644 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
13645 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013646#endif
Victor Stinnerf0a7bac2013-10-30 18:55:24 +010013647 if (PyErr_Occurred()) {
13648 Py_DECREF(v);
13649 return NULL;
13650 }
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013651
Victor Stinner8c62be82010-05-06 00:08:46 +000013652 return v;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013653}
13654
Larry Hastings2f936352014-08-05 14:04:04 +100013655
13656/*[clinic input]
13657os.fstatvfs
13658 fd: int
13659 /
13660
13661Perform an fstatvfs system call on the given fd.
13662
13663Equivalent to statvfs(fd).
13664[clinic start generated code]*/
13665
13666PyDoc_STRVAR(os_fstatvfs__doc__,
13667"fstatvfs($module, fd, /)\n"
13668"--\n"
13669"\n"
13670"Perform an fstatvfs system call on the given fd.\n"
13671"\n"
13672"Equivalent to statvfs(fd).");
13673
13674#define OS_FSTATVFS_METHODDEF \
13675 {"fstatvfs", (PyCFunction)os_fstatvfs, METH_VARARGS, os_fstatvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013676
13677static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013678os_fstatvfs_impl(PyModuleDef *module, int fd);
13679
13680static PyObject *
13681os_fstatvfs(PyModuleDef *module, PyObject *args)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013682{
Larry Hastings2f936352014-08-05 14:04:04 +100013683 PyObject *return_value = NULL;
13684 int fd;
13685
13686 if (!PyArg_ParseTuple(args,
13687 "i:fstatvfs",
13688 &fd))
13689 goto exit;
13690 return_value = os_fstatvfs_impl(module, fd);
13691
13692exit:
13693 return return_value;
13694}
13695
13696static PyObject *
13697os_fstatvfs_impl(PyModuleDef *module, int fd)
13698/*[clinic end generated code: output=0e32bf07f946ec0d input=d8122243ac50975e]*/
13699{
13700 int result;
Victor Stinner8c62be82010-05-06 00:08:46 +000013701 struct statvfs st;
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013702
Victor Stinner8c62be82010-05-06 00:08:46 +000013703 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013704 result = fstatvfs(fd, &st);
Victor Stinner8c62be82010-05-06 00:08:46 +000013705 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +100013706 if (result != 0)
Victor Stinner8c62be82010-05-06 00:08:46 +000013707 return posix_error();
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013708
Victor Stinner8c62be82010-05-06 00:08:46 +000013709 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013710}
Larry Hastings2f936352014-08-05 14:04:04 +100013711#endif /* defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H) */
Guido van Rossum94f6f721999-01-06 18:42:14 +000013712
13713
Thomas Wouters477c8d52006-05-27 19:21:47 +000013714#if defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossum94f6f721999-01-06 18:42:14 +000013715#include <sys/statvfs.h>
Larry Hastings2f936352014-08-05 14:04:04 +100013716/*[clinic input]
13717os.statvfs
Guido van Rossum94f6f721999-01-06 18:42:14 +000013718
Larry Hastings2f936352014-08-05 14:04:04 +100013719 path: path_t(allow_fd='PATH_HAVE_FSTATVFS')
13720
13721Perform a statvfs system call on the given path.
13722
13723path may always be specified as a string.
13724On some platforms, path may also be specified as an open file descriptor.
13725 If this functionality is unavailable, using it raises an exception.
13726[clinic start generated code]*/
13727
13728PyDoc_STRVAR(os_statvfs__doc__,
13729"statvfs($module, /, path)\n"
13730"--\n"
13731"\n"
13732"Perform a statvfs system call on the given path.\n"
13733"\n"
13734"path may always be specified as a string.\n"
13735"On some platforms, path may also be specified as an open file descriptor.\n"
13736" If this functionality is unavailable, using it raises an exception.");
13737
13738#define OS_STATVFS_METHODDEF \
13739 {"statvfs", (PyCFunction)os_statvfs, METH_VARARGS|METH_KEYWORDS, os_statvfs__doc__},
Guido van Rossum94f6f721999-01-06 18:42:14 +000013740
13741static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013742os_statvfs_impl(PyModuleDef *module, path_t *path);
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013743
Larry Hastings2f936352014-08-05 14:04:04 +100013744static PyObject *
13745os_statvfs(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13746{
13747 PyObject *return_value = NULL;
13748 static char *_keywords[] = {"path", NULL};
13749 path_t path = PATH_T_INITIALIZE("statvfs", "path", 0, PATH_HAVE_FSTATVFS);
13750
13751 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13752 "O&:statvfs", _keywords,
13753 path_converter, &path))
13754 goto exit;
13755 return_value = os_statvfs_impl(module, &path);
13756
13757exit:
13758 /* Cleanup for path */
13759 path_cleanup(&path);
13760
13761 return return_value;
13762}
13763
13764static PyObject *
13765os_statvfs_impl(PyModuleDef *module, path_t *path)
13766/*[clinic end generated code: output=00ff54983360b446 input=3f5c35791c669bd9]*/
13767{
13768 int result;
13769 struct statvfs st;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013770
13771 Py_BEGIN_ALLOW_THREADS
13772#ifdef HAVE_FSTATVFS
Larry Hastings2f936352014-08-05 14:04:04 +100013773 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -070013774#ifdef __APPLE__
13775 /* handle weak-linking on Mac OS X 10.3 */
13776 if (fstatvfs == NULL) {
Larry Hastings2f936352014-08-05 14:04:04 +100013777 fd_specified("statvfs", path->fd);
13778 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013779 }
13780#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013781 result = fstatvfs(path->fd, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013782 }
13783 else
13784#endif
Larry Hastings2f936352014-08-05 14:04:04 +100013785 result = statvfs(path->narrow, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013786 Py_END_ALLOW_THREADS
13787
13788 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100013789 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070013790 }
13791
Larry Hastings2f936352014-08-05 14:04:04 +100013792 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +000013793}
Larry Hastings2f936352014-08-05 14:04:04 +100013794#endif /* defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H) */
13795
Guido van Rossum94f6f721999-01-06 18:42:14 +000013796
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013797#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100013798/*[clinic input]
13799os._getdiskusage
13800
13801 path: Py_UNICODE
13802
13803Return disk usage statistics about the given path as a (total, free) tuple.
13804[clinic start generated code]*/
13805
13806PyDoc_STRVAR(os__getdiskusage__doc__,
13807"_getdiskusage($module, /, path)\n"
13808"--\n"
13809"\n"
13810"Return disk usage statistics about the given path as a (total, free) tuple.");
13811
13812#define OS__GETDISKUSAGE_METHODDEF \
13813 {"_getdiskusage", (PyCFunction)os__getdiskusage, METH_VARARGS|METH_KEYWORDS, os__getdiskusage__doc__},
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013814
13815static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100013816os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path);
13817
13818static PyObject *
13819os__getdiskusage(PyModuleDef *module, PyObject *args, PyObject *kwargs)
13820{
13821 PyObject *return_value = NULL;
13822 static char *_keywords[] = {"path", NULL};
13823 Py_UNICODE *path;
13824
13825 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
13826 "u:_getdiskusage", _keywords,
13827 &path))
13828 goto exit;
13829 return_value = os__getdiskusage_impl(module, path);
13830
13831exit:
13832 return return_value;
13833}
13834
13835static PyObject *
13836os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path)
13837/*[clinic end generated code: output=054c972179b13708 input=6458133aed893c78]*/
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013838{
13839 BOOL retval;
13840 ULARGE_INTEGER _, total, free;
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013841
13842 Py_BEGIN_ALLOW_THREADS
Victor Stinner6139c1b2011-11-09 22:14:14 +010013843 retval = GetDiskFreeSpaceExW(path, &_, &total, &free);
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013844 Py_END_ALLOW_THREADS
13845 if (retval == 0)
13846 return PyErr_SetFromWindowsErr(0);
13847
13848 return Py_BuildValue("(LL)", total.QuadPart, free.QuadPart);
13849}
Larry Hastings2f936352014-08-05 14:04:04 +100013850#endif /* MS_WINDOWS */
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +020013851
13852
Fred Drakec9680921999-12-13 16:37:25 +000013853/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
13854 * It maps strings representing configuration variable names to
13855 * integer values, allowing those functions to be called with the
Thomas Wouters7e474022000-07-16 12:04:32 +000013856 * magic names instead of polluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +000013857 * rarely-used constants. There are three separate tables that use
13858 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +000013859 *
13860 * This code is always included, even if none of the interfaces that
13861 * need it are included. The #if hackery needed to avoid it would be
13862 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +000013863 */
13864struct constdef {
13865 char *name;
13866 long value;
13867};
13868
Fred Drake12c6e2d1999-12-14 21:25:03 +000013869static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000013870conv_confname(PyObject *arg, int *valuep, struct constdef *table,
Guido van Rossum7d5baac2007-08-27 23:24:46 +000013871 size_t tablesize)
Fred Drake12c6e2d1999-12-14 21:25:03 +000013872{
Christian Heimes217cfd12007-12-02 14:31:20 +000013873 if (PyLong_Check(arg)) {
Stefan Krah0e803b32010-11-26 16:16:47 +000013874 *valuep = PyLong_AS_LONG(arg);
13875 return 1;
Fred Drake12c6e2d1999-12-14 21:25:03 +000013876 }
Guido van Rossumbce56a62007-05-10 18:04:33 +000013877 else {
Stefan Krah0e803b32010-11-26 16:16:47 +000013878 /* look up the value in the table using a binary search */
13879 size_t lo = 0;
13880 size_t mid;
13881 size_t hi = tablesize;
13882 int cmp;
13883 const char *confname;
13884 if (!PyUnicode_Check(arg)) {
13885 PyErr_SetString(PyExc_TypeError,
13886 "configuration names must be strings or integers");
13887 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013888 }
Stefan Krah0e803b32010-11-26 16:16:47 +000013889 confname = _PyUnicode_AsString(arg);
13890 if (confname == NULL)
13891 return 0;
13892 while (lo < hi) {
13893 mid = (lo + hi) / 2;
13894 cmp = strcmp(confname, table[mid].name);
13895 if (cmp < 0)
13896 hi = mid;
13897 else if (cmp > 0)
13898 lo = mid + 1;
13899 else {
13900 *valuep = table[mid].value;
13901 return 1;
13902 }
13903 }
13904 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
13905 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +000013906 }
Fred Drake12c6e2d1999-12-14 21:25:03 +000013907}
13908
13909
13910#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
13911static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +000013912#ifdef _PC_ABI_AIO_XFER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013913 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000013914#endif
13915#ifdef _PC_ABI_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013916 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
Fred Draked86ed291999-12-15 15:34:33 +000013917#endif
Fred Drakec9680921999-12-13 16:37:25 +000013918#ifdef _PC_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013919 {"PC_ASYNC_IO", _PC_ASYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013920#endif
13921#ifdef _PC_CHOWN_RESTRICTED
Victor Stinner8c62be82010-05-06 00:08:46 +000013922 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
Fred Drakec9680921999-12-13 16:37:25 +000013923#endif
13924#ifdef _PC_FILESIZEBITS
Victor Stinner8c62be82010-05-06 00:08:46 +000013925 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
Fred Drakec9680921999-12-13 16:37:25 +000013926#endif
13927#ifdef _PC_LAST
Victor Stinner8c62be82010-05-06 00:08:46 +000013928 {"PC_LAST", _PC_LAST},
Fred Drakec9680921999-12-13 16:37:25 +000013929#endif
13930#ifdef _PC_LINK_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013931 {"PC_LINK_MAX", _PC_LINK_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013932#endif
13933#ifdef _PC_MAX_CANON
Victor Stinner8c62be82010-05-06 00:08:46 +000013934 {"PC_MAX_CANON", _PC_MAX_CANON},
Fred Drakec9680921999-12-13 16:37:25 +000013935#endif
13936#ifdef _PC_MAX_INPUT
Victor Stinner8c62be82010-05-06 00:08:46 +000013937 {"PC_MAX_INPUT", _PC_MAX_INPUT},
Fred Drakec9680921999-12-13 16:37:25 +000013938#endif
13939#ifdef _PC_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013940 {"PC_NAME_MAX", _PC_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013941#endif
13942#ifdef _PC_NO_TRUNC
Victor Stinner8c62be82010-05-06 00:08:46 +000013943 {"PC_NO_TRUNC", _PC_NO_TRUNC},
Fred Drakec9680921999-12-13 16:37:25 +000013944#endif
13945#ifdef _PC_PATH_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000013946 {"PC_PATH_MAX", _PC_PATH_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000013947#endif
13948#ifdef _PC_PIPE_BUF
Victor Stinner8c62be82010-05-06 00:08:46 +000013949 {"PC_PIPE_BUF", _PC_PIPE_BUF},
Fred Drakec9680921999-12-13 16:37:25 +000013950#endif
13951#ifdef _PC_PRIO_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013952 {"PC_PRIO_IO", _PC_PRIO_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013953#endif
13954#ifdef _PC_SOCK_MAXBUF
Victor Stinner8c62be82010-05-06 00:08:46 +000013955 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
Fred Drakec9680921999-12-13 16:37:25 +000013956#endif
13957#ifdef _PC_SYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000013958 {"PC_SYNC_IO", _PC_SYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +000013959#endif
13960#ifdef _PC_VDISABLE
Victor Stinner8c62be82010-05-06 00:08:46 +000013961 {"PC_VDISABLE", _PC_VDISABLE},
Fred Drakec9680921999-12-13 16:37:25 +000013962#endif
Jesus Cea7e9065c2010-10-25 13:02:04 +000013963#ifdef _PC_ACL_ENABLED
13964 {"PC_ACL_ENABLED", _PC_ACL_ENABLED},
13965#endif
13966#ifdef _PC_MIN_HOLE_SIZE
13967 {"PC_MIN_HOLE_SIZE", _PC_MIN_HOLE_SIZE},
13968#endif
13969#ifdef _PC_ALLOC_SIZE_MIN
13970 {"PC_ALLOC_SIZE_MIN", _PC_ALLOC_SIZE_MIN},
13971#endif
13972#ifdef _PC_REC_INCR_XFER_SIZE
13973 {"PC_REC_INCR_XFER_SIZE", _PC_REC_INCR_XFER_SIZE},
13974#endif
13975#ifdef _PC_REC_MAX_XFER_SIZE
13976 {"PC_REC_MAX_XFER_SIZE", _PC_REC_MAX_XFER_SIZE},
13977#endif
13978#ifdef _PC_REC_MIN_XFER_SIZE
13979 {"PC_REC_MIN_XFER_SIZE", _PC_REC_MIN_XFER_SIZE},
13980#endif
13981#ifdef _PC_REC_XFER_ALIGN
13982 {"PC_REC_XFER_ALIGN", _PC_REC_XFER_ALIGN},
13983#endif
13984#ifdef _PC_SYMLINK_MAX
13985 {"PC_SYMLINK_MAX", _PC_SYMLINK_MAX},
13986#endif
13987#ifdef _PC_XATTR_ENABLED
13988 {"PC_XATTR_ENABLED", _PC_XATTR_ENABLED},
13989#endif
13990#ifdef _PC_XATTR_EXISTS
13991 {"PC_XATTR_EXISTS", _PC_XATTR_EXISTS},
13992#endif
13993#ifdef _PC_TIMESTAMP_RESOLUTION
13994 {"PC_TIMESTAMP_RESOLUTION", _PC_TIMESTAMP_RESOLUTION},
13995#endif
Fred Drakec9680921999-12-13 16:37:25 +000013996};
13997
Fred Drakec9680921999-12-13 16:37:25 +000013998static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000013999conv_path_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014000{
14001 return conv_confname(arg, valuep, posix_constants_pathconf,
14002 sizeof(posix_constants_pathconf)
14003 / sizeof(struct constdef));
14004}
14005#endif
14006
Larry Hastings2f936352014-08-05 14:04:04 +100014007
Fred Drakec9680921999-12-13 16:37:25 +000014008#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014009/*[clinic input]
14010os.fpathconf -> long
14011
14012 fd: int
14013 name: path_confname
14014 /
14015
14016Return the configuration limit name for the file descriptor fd.
14017
14018If there is no limit, return -1.
14019[clinic start generated code]*/
14020
14021PyDoc_STRVAR(os_fpathconf__doc__,
14022"fpathconf($module, fd, name, /)\n"
14023"--\n"
14024"\n"
14025"Return the configuration limit name for the file descriptor fd.\n"
14026"\n"
14027"If there is no limit, return -1.");
14028
14029#define OS_FPATHCONF_METHODDEF \
14030 {"fpathconf", (PyCFunction)os_fpathconf, METH_VARARGS, os_fpathconf__doc__},
14031
14032static long
14033os_fpathconf_impl(PyModuleDef *module, int fd, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014034
14035static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014036os_fpathconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014037{
Larry Hastings2f936352014-08-05 14:04:04 +100014038 PyObject *return_value = NULL;
14039 int fd;
14040 int name;
14041 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014042
Larry Hastings2f936352014-08-05 14:04:04 +100014043 if (!PyArg_ParseTuple(args,
14044 "iO&:fpathconf",
14045 &fd, conv_path_confname, &name))
14046 goto exit;
14047 _return_value = os_fpathconf_impl(module, fd, name);
14048 if ((_return_value == -1) && PyErr_Occurred())
14049 goto exit;
14050 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014051
Larry Hastings2f936352014-08-05 14:04:04 +100014052exit:
14053 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014054}
Larry Hastings2f936352014-08-05 14:04:04 +100014055
14056static long
14057os_fpathconf_impl(PyModuleDef *module, int fd, int name)
14058/*[clinic end generated code: output=3bf04b40e0523a8c input=5942a024d3777810]*/
14059{
14060 long limit;
14061
14062 errno = 0;
14063 limit = fpathconf(fd, name);
14064 if (limit == -1 && errno != 0)
14065 posix_error();
14066
14067 return limit;
14068}
14069#endif /* HAVE_FPATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014070
14071
14072#ifdef HAVE_PATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014073/*[clinic input]
14074os.pathconf -> long
14075 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
14076 name: path_confname
14077
14078Return the configuration limit name for the file or directory path.
14079
14080If there is no limit, return -1.
14081On some platforms, path may also be specified as an open file descriptor.
14082 If this functionality is unavailable, using it raises an exception.
14083[clinic start generated code]*/
14084
14085PyDoc_STRVAR(os_pathconf__doc__,
14086"pathconf($module, /, path, name)\n"
14087"--\n"
14088"\n"
14089"Return the configuration limit name for the file or directory path.\n"
14090"\n"
14091"If there is no limit, return -1.\n"
14092"On some platforms, path may also be specified as an open file descriptor.\n"
14093" If this functionality is unavailable, using it raises an exception.");
14094
14095#define OS_PATHCONF_METHODDEF \
14096 {"pathconf", (PyCFunction)os_pathconf, METH_VARARGS|METH_KEYWORDS, os_pathconf__doc__},
14097
14098static long
14099os_pathconf_impl(PyModuleDef *module, path_t *path, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014100
14101static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014102os_pathconf(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Fred Drakec9680921999-12-13 16:37:25 +000014103{
Larry Hastings2f936352014-08-05 14:04:04 +100014104 PyObject *return_value = NULL;
14105 static char *_keywords[] = {"path", "name", NULL};
14106 path_t path = PATH_T_INITIALIZE("pathconf", "path", 0, PATH_HAVE_FPATHCONF);
Fred Drakec9680921999-12-13 16:37:25 +000014107 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014108 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014109
Larry Hastings2f936352014-08-05 14:04:04 +100014110 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
14111 "O&O&:pathconf", _keywords,
14112 path_converter, &path, conv_path_confname, &name))
14113 goto exit;
14114 _return_value = os_pathconf_impl(module, &path, name);
14115 if ((_return_value == -1) && PyErr_Occurred())
14116 goto exit;
14117 return_value = PyLong_FromLong(_return_value);
14118
14119exit:
14120 /* Cleanup for path */
14121 path_cleanup(&path);
14122
14123 return return_value;
14124}
14125
14126static long
14127os_pathconf_impl(PyModuleDef *module, path_t *path, int name)
14128/*[clinic end generated code: output=1a53e125b6cf63e4 input=bc3e2a985af27e5e]*/
14129{
Victor Stinner8c62be82010-05-06 00:08:46 +000014130 long limit;
Fred Drakec9680921999-12-13 16:37:25 +000014131
Victor Stinner8c62be82010-05-06 00:08:46 +000014132 errno = 0;
Georg Brandl306336b2012-06-24 12:55:33 +020014133#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +100014134 if (path->fd != -1)
14135 limit = fpathconf(path->fd, name);
Georg Brandl306336b2012-06-24 12:55:33 +020014136 else
14137#endif
Larry Hastings2f936352014-08-05 14:04:04 +100014138 limit = pathconf(path->narrow, name);
Victor Stinner8c62be82010-05-06 00:08:46 +000014139 if (limit == -1 && errno != 0) {
14140 if (errno == EINVAL)
Stefan Krah99439262010-11-26 12:58:05 +000014141 /* could be a path or name problem */
14142 posix_error();
Fred Drakec9680921999-12-13 16:37:25 +000014143 else
Larry Hastings2f936352014-08-05 14:04:04 +100014144 path_error(path);
Victor Stinner8c62be82010-05-06 00:08:46 +000014145 }
Larry Hastings2f936352014-08-05 14:04:04 +100014146
14147 return limit;
Fred Drakec9680921999-12-13 16:37:25 +000014148}
Larry Hastings2f936352014-08-05 14:04:04 +100014149#endif /* HAVE_PATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014150
14151#ifdef HAVE_CONFSTR
14152static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +000014153#ifdef _CS_ARCHITECTURE
Victor Stinner8c62be82010-05-06 00:08:46 +000014154 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
Fred Draked86ed291999-12-15 15:34:33 +000014155#endif
Mark Dickinson876d7c82010-04-16 12:47:52 +000014156#ifdef _CS_GNU_LIBC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014157 {"CS_GNU_LIBC_VERSION", _CS_GNU_LIBC_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014158#endif
14159#ifdef _CS_GNU_LIBPTHREAD_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014160 {"CS_GNU_LIBPTHREAD_VERSION", _CS_GNU_LIBPTHREAD_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +000014161#endif
Fred Draked86ed291999-12-15 15:34:33 +000014162#ifdef _CS_HOSTNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014163 {"CS_HOSTNAME", _CS_HOSTNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014164#endif
14165#ifdef _CS_HW_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014166 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014167#endif
14168#ifdef _CS_HW_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014169 {"CS_HW_SERIAL", _CS_HW_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014170#endif
14171#ifdef _CS_INITTAB_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014172 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014173#endif
Fred Drakec9680921999-12-13 16:37:25 +000014174#ifdef _CS_LFS64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014175 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014176#endif
14177#ifdef _CS_LFS64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014178 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014179#endif
14180#ifdef _CS_LFS64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014181 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014182#endif
14183#ifdef _CS_LFS64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014184 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014185#endif
14186#ifdef _CS_LFS_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014187 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014188#endif
14189#ifdef _CS_LFS_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014190 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014191#endif
14192#ifdef _CS_LFS_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014193 {"CS_LFS_LIBS", _CS_LFS_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014194#endif
14195#ifdef _CS_LFS_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014196 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014197#endif
Fred Draked86ed291999-12-15 15:34:33 +000014198#ifdef _CS_MACHINE
Victor Stinner8c62be82010-05-06 00:08:46 +000014199 {"CS_MACHINE", _CS_MACHINE},
Fred Draked86ed291999-12-15 15:34:33 +000014200#endif
Fred Drakec9680921999-12-13 16:37:25 +000014201#ifdef _CS_PATH
Victor Stinner8c62be82010-05-06 00:08:46 +000014202 {"CS_PATH", _CS_PATH},
Fred Drakec9680921999-12-13 16:37:25 +000014203#endif
Fred Draked86ed291999-12-15 15:34:33 +000014204#ifdef _CS_RELEASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014205 {"CS_RELEASE", _CS_RELEASE},
Fred Draked86ed291999-12-15 15:34:33 +000014206#endif
14207#ifdef _CS_SRPC_DOMAIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014208 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
Fred Draked86ed291999-12-15 15:34:33 +000014209#endif
14210#ifdef _CS_SYSNAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014211 {"CS_SYSNAME", _CS_SYSNAME},
Fred Draked86ed291999-12-15 15:34:33 +000014212#endif
14213#ifdef _CS_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014214 {"CS_VERSION", _CS_VERSION},
Fred Draked86ed291999-12-15 15:34:33 +000014215#endif
Fred Drakec9680921999-12-13 16:37:25 +000014216#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014217 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014218#endif
14219#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014220 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014221#endif
14222#ifdef _CS_XBS5_ILP32_OFF32_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014223 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014224#endif
14225#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014226 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014227#endif
14228#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014229 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014230#endif
14231#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014232 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014233#endif
14234#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014235 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014236#endif
14237#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014238 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014239#endif
14240#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014241 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014242#endif
14243#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014244 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014245#endif
14246#ifdef _CS_XBS5_LP64_OFF64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014247 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014248#endif
14249#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014250 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014251#endif
14252#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014253 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014254#endif
14255#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014256 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014257#endif
14258#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +000014259 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +000014260#endif
14261#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +000014262 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +000014263#endif
Fred Draked86ed291999-12-15 15:34:33 +000014264#ifdef _MIPS_CS_AVAIL_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014265 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014266#endif
14267#ifdef _MIPS_CS_BASE
Victor Stinner8c62be82010-05-06 00:08:46 +000014268 {"MIPS_CS_BASE", _MIPS_CS_BASE},
Fred Draked86ed291999-12-15 15:34:33 +000014269#endif
14270#ifdef _MIPS_CS_HOSTID
Victor Stinner8c62be82010-05-06 00:08:46 +000014271 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
Fred Draked86ed291999-12-15 15:34:33 +000014272#endif
14273#ifdef _MIPS_CS_HW_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014274 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014275#endif
14276#ifdef _MIPS_CS_NUM_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014277 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014278#endif
14279#ifdef _MIPS_CS_OSREL_MAJ
Victor Stinner8c62be82010-05-06 00:08:46 +000014280 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
Fred Draked86ed291999-12-15 15:34:33 +000014281#endif
14282#ifdef _MIPS_CS_OSREL_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014283 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
Fred Draked86ed291999-12-15 15:34:33 +000014284#endif
14285#ifdef _MIPS_CS_OSREL_PATCH
Victor Stinner8c62be82010-05-06 00:08:46 +000014286 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
Fred Draked86ed291999-12-15 15:34:33 +000014287#endif
14288#ifdef _MIPS_CS_OS_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +000014289 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
Fred Draked86ed291999-12-15 15:34:33 +000014290#endif
14291#ifdef _MIPS_CS_OS_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +000014292 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +000014293#endif
14294#ifdef _MIPS_CS_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +000014295 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +000014296#endif
14297#ifdef _MIPS_CS_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000014298 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +000014299#endif
14300#ifdef _MIPS_CS_VENDOR
Victor Stinner8c62be82010-05-06 00:08:46 +000014301 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
Fred Draked86ed291999-12-15 15:34:33 +000014302#endif
Fred Drakec9680921999-12-13 16:37:25 +000014303};
14304
14305static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014306conv_confstr_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014307{
14308 return conv_confname(arg, valuep, posix_constants_confstr,
14309 sizeof(posix_constants_confstr)
14310 / sizeof(struct constdef));
14311}
14312
Larry Hastings2f936352014-08-05 14:04:04 +100014313
14314/*[clinic input]
14315os.confstr
14316
14317 name: confstr_confname
14318 /
14319
14320Return a string-valued system configuration variable.
14321[clinic start generated code]*/
14322
14323PyDoc_STRVAR(os_confstr__doc__,
14324"confstr($module, name, /)\n"
14325"--\n"
14326"\n"
14327"Return a string-valued system configuration variable.");
14328
14329#define OS_CONFSTR_METHODDEF \
14330 {"confstr", (PyCFunction)os_confstr, METH_VARARGS, os_confstr__doc__},
Fred Drakec9680921999-12-13 16:37:25 +000014331
14332static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014333os_confstr_impl(PyModuleDef *module, int name);
14334
14335static PyObject *
14336os_confstr(PyModuleDef *module, PyObject *args)
14337{
14338 PyObject *return_value = NULL;
14339 int name;
14340
14341 if (!PyArg_ParseTuple(args,
14342 "O&:confstr",
14343 conv_confstr_confname, &name))
14344 goto exit;
14345 return_value = os_confstr_impl(module, name);
14346
14347exit:
14348 return return_value;
14349}
14350
14351static PyObject *
14352os_confstr_impl(PyModuleDef *module, int name)
14353/*[clinic end generated code: output=3f5e8aba9f8e3174 input=18fb4d0567242e65]*/
Fred Drakec9680921999-12-13 16:37:25 +000014354{
14355 PyObject *result = NULL;
Victor Stinnercb043522010-09-10 23:49:04 +000014356 char buffer[255];
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014357 size_t len;
Fred Drakec9680921999-12-13 16:37:25 +000014358
Victor Stinnercb043522010-09-10 23:49:04 +000014359 errno = 0;
14360 len = confstr(name, buffer, sizeof(buffer));
14361 if (len == 0) {
14362 if (errno) {
14363 posix_error();
14364 return NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014365 }
14366 else {
Victor Stinnercb043522010-09-10 23:49:04 +000014367 Py_RETURN_NONE;
Fred Drakec9680921999-12-13 16:37:25 +000014368 }
14369 }
Victor Stinnercb043522010-09-10 23:49:04 +000014370
Victor Stinnerdd3a6a52013-06-25 23:13:47 +020014371 if (len >= sizeof(buffer)) {
Victor Stinnercb043522010-09-10 23:49:04 +000014372 char *buf = PyMem_Malloc(len);
14373 if (buf == NULL)
14374 return PyErr_NoMemory();
14375 confstr(name, buf, len);
14376 result = PyUnicode_DecodeFSDefaultAndSize(buf, len-1);
14377 PyMem_Free(buf);
14378 }
14379 else
14380 result = PyUnicode_DecodeFSDefaultAndSize(buffer, len-1);
Fred Drakec9680921999-12-13 16:37:25 +000014381 return result;
14382}
Larry Hastings2f936352014-08-05 14:04:04 +100014383#endif /* HAVE_CONFSTR */
Fred Drakec9680921999-12-13 16:37:25 +000014384
14385
14386#ifdef HAVE_SYSCONF
14387static struct constdef posix_constants_sysconf[] = {
14388#ifdef _SC_2_CHAR_TERM
Victor Stinner8c62be82010-05-06 00:08:46 +000014389 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
Fred Drakec9680921999-12-13 16:37:25 +000014390#endif
14391#ifdef _SC_2_C_BIND
Victor Stinner8c62be82010-05-06 00:08:46 +000014392 {"SC_2_C_BIND", _SC_2_C_BIND},
Fred Drakec9680921999-12-13 16:37:25 +000014393#endif
14394#ifdef _SC_2_C_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014395 {"SC_2_C_DEV", _SC_2_C_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014396#endif
14397#ifdef _SC_2_C_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014398 {"SC_2_C_VERSION", _SC_2_C_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014399#endif
14400#ifdef _SC_2_FORT_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014401 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014402#endif
14403#ifdef _SC_2_FORT_RUN
Victor Stinner8c62be82010-05-06 00:08:46 +000014404 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
Fred Drakec9680921999-12-13 16:37:25 +000014405#endif
14406#ifdef _SC_2_LOCALEDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000014407 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
Fred Drakec9680921999-12-13 16:37:25 +000014408#endif
14409#ifdef _SC_2_SW_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +000014410 {"SC_2_SW_DEV", _SC_2_SW_DEV},
Fred Drakec9680921999-12-13 16:37:25 +000014411#endif
14412#ifdef _SC_2_UPE
Victor Stinner8c62be82010-05-06 00:08:46 +000014413 {"SC_2_UPE", _SC_2_UPE},
Fred Drakec9680921999-12-13 16:37:25 +000014414#endif
14415#ifdef _SC_2_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014416 {"SC_2_VERSION", _SC_2_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014417#endif
Fred Draked86ed291999-12-15 15:34:33 +000014418#ifdef _SC_ABI_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014419 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
Fred Draked86ed291999-12-15 15:34:33 +000014420#endif
14421#ifdef _SC_ACL
Victor Stinner8c62be82010-05-06 00:08:46 +000014422 {"SC_ACL", _SC_ACL},
Fred Draked86ed291999-12-15 15:34:33 +000014423#endif
Fred Drakec9680921999-12-13 16:37:25 +000014424#ifdef _SC_AIO_LISTIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014425 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014426#endif
Fred Drakec9680921999-12-13 16:37:25 +000014427#ifdef _SC_AIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014428 {"SC_AIO_MAX", _SC_AIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014429#endif
14430#ifdef _SC_AIO_PRIO_DELTA_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014431 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014432#endif
14433#ifdef _SC_ARG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014434 {"SC_ARG_MAX", _SC_ARG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014435#endif
14436#ifdef _SC_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014437 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014438#endif
14439#ifdef _SC_ATEXIT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014440 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014441#endif
Fred Draked86ed291999-12-15 15:34:33 +000014442#ifdef _SC_AUDIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014443 {"SC_AUDIT", _SC_AUDIT},
Fred Draked86ed291999-12-15 15:34:33 +000014444#endif
Fred Drakec9680921999-12-13 16:37:25 +000014445#ifdef _SC_AVPHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014446 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014447#endif
14448#ifdef _SC_BC_BASE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014449 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014450#endif
14451#ifdef _SC_BC_DIM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014452 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014453#endif
14454#ifdef _SC_BC_SCALE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014455 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014456#endif
14457#ifdef _SC_BC_STRING_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014458 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014459#endif
Fred Draked86ed291999-12-15 15:34:33 +000014460#ifdef _SC_CAP
Victor Stinner8c62be82010-05-06 00:08:46 +000014461 {"SC_CAP", _SC_CAP},
Fred Draked86ed291999-12-15 15:34:33 +000014462#endif
Fred Drakec9680921999-12-13 16:37:25 +000014463#ifdef _SC_CHARCLASS_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014464 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014465#endif
14466#ifdef _SC_CHAR_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014467 {"SC_CHAR_BIT", _SC_CHAR_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014468#endif
14469#ifdef _SC_CHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014470 {"SC_CHAR_MAX", _SC_CHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014471#endif
14472#ifdef _SC_CHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014473 {"SC_CHAR_MIN", _SC_CHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014474#endif
14475#ifdef _SC_CHILD_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014476 {"SC_CHILD_MAX", _SC_CHILD_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014477#endif
14478#ifdef _SC_CLK_TCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014479 {"SC_CLK_TCK", _SC_CLK_TCK},
Fred Drakec9680921999-12-13 16:37:25 +000014480#endif
14481#ifdef _SC_COHER_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014482 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014483#endif
14484#ifdef _SC_COLL_WEIGHTS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014485 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014486#endif
14487#ifdef _SC_DCACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014488 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014489#endif
14490#ifdef _SC_DCACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014491 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014492#endif
14493#ifdef _SC_DCACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014494 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014495#endif
14496#ifdef _SC_DCACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014497 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014498#endif
14499#ifdef _SC_DCACHE_TBLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014500 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014501#endif
14502#ifdef _SC_DELAYTIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014503 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014504#endif
14505#ifdef _SC_EQUIV_CLASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014506 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014507#endif
14508#ifdef _SC_EXPR_NEST_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014509 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014510#endif
14511#ifdef _SC_FSYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000014512 {"SC_FSYNC", _SC_FSYNC},
Fred Drakec9680921999-12-13 16:37:25 +000014513#endif
14514#ifdef _SC_GETGR_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014515 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014516#endif
14517#ifdef _SC_GETPW_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014518 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014519#endif
14520#ifdef _SC_ICACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000014521 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000014522#endif
14523#ifdef _SC_ICACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014524 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000014525#endif
14526#ifdef _SC_ICACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014527 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000014528#endif
14529#ifdef _SC_ICACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000014530 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000014531#endif
Fred Draked86ed291999-12-15 15:34:33 +000014532#ifdef _SC_INF
Victor Stinner8c62be82010-05-06 00:08:46 +000014533 {"SC_INF", _SC_INF},
Fred Draked86ed291999-12-15 15:34:33 +000014534#endif
Fred Drakec9680921999-12-13 16:37:25 +000014535#ifdef _SC_INT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014536 {"SC_INT_MAX", _SC_INT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014537#endif
14538#ifdef _SC_INT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014539 {"SC_INT_MIN", _SC_INT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014540#endif
14541#ifdef _SC_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014542 {"SC_IOV_MAX", _SC_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014543#endif
Fred Draked86ed291999-12-15 15:34:33 +000014544#ifdef _SC_IP_SECOPTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014545 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
Fred Draked86ed291999-12-15 15:34:33 +000014546#endif
Fred Drakec9680921999-12-13 16:37:25 +000014547#ifdef _SC_JOB_CONTROL
Victor Stinner8c62be82010-05-06 00:08:46 +000014548 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
Fred Drakec9680921999-12-13 16:37:25 +000014549#endif
Fred Draked86ed291999-12-15 15:34:33 +000014550#ifdef _SC_KERN_POINTERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014551 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
Fred Draked86ed291999-12-15 15:34:33 +000014552#endif
14553#ifdef _SC_KERN_SIM
Victor Stinner8c62be82010-05-06 00:08:46 +000014554 {"SC_KERN_SIM", _SC_KERN_SIM},
Fred Draked86ed291999-12-15 15:34:33 +000014555#endif
Fred Drakec9680921999-12-13 16:37:25 +000014556#ifdef _SC_LINE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014557 {"SC_LINE_MAX", _SC_LINE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014558#endif
14559#ifdef _SC_LOGIN_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014560 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014561#endif
14562#ifdef _SC_LOGNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014563 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014564#endif
14565#ifdef _SC_LONG_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014566 {"SC_LONG_BIT", _SC_LONG_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014567#endif
Fred Draked86ed291999-12-15 15:34:33 +000014568#ifdef _SC_MAC
Victor Stinner8c62be82010-05-06 00:08:46 +000014569 {"SC_MAC", _SC_MAC},
Fred Draked86ed291999-12-15 15:34:33 +000014570#endif
Fred Drakec9680921999-12-13 16:37:25 +000014571#ifdef _SC_MAPPED_FILES
Victor Stinner8c62be82010-05-06 00:08:46 +000014572 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
Fred Drakec9680921999-12-13 16:37:25 +000014573#endif
14574#ifdef _SC_MAXPID
Victor Stinner8c62be82010-05-06 00:08:46 +000014575 {"SC_MAXPID", _SC_MAXPID},
Fred Drakec9680921999-12-13 16:37:25 +000014576#endif
14577#ifdef _SC_MB_LEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014578 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014579#endif
14580#ifdef _SC_MEMLOCK
Victor Stinner8c62be82010-05-06 00:08:46 +000014581 {"SC_MEMLOCK", _SC_MEMLOCK},
Fred Drakec9680921999-12-13 16:37:25 +000014582#endif
14583#ifdef _SC_MEMLOCK_RANGE
Victor Stinner8c62be82010-05-06 00:08:46 +000014584 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
Fred Drakec9680921999-12-13 16:37:25 +000014585#endif
14586#ifdef _SC_MEMORY_PROTECTION
Victor Stinner8c62be82010-05-06 00:08:46 +000014587 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
Fred Drakec9680921999-12-13 16:37:25 +000014588#endif
14589#ifdef _SC_MESSAGE_PASSING
Victor Stinner8c62be82010-05-06 00:08:46 +000014590 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
Fred Drakec9680921999-12-13 16:37:25 +000014591#endif
Fred Draked86ed291999-12-15 15:34:33 +000014592#ifdef _SC_MMAP_FIXED_ALIGNMENT
Victor Stinner8c62be82010-05-06 00:08:46 +000014593 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
Fred Draked86ed291999-12-15 15:34:33 +000014594#endif
Fred Drakec9680921999-12-13 16:37:25 +000014595#ifdef _SC_MQ_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014596 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014597#endif
14598#ifdef _SC_MQ_PRIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014599 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014600#endif
Fred Draked86ed291999-12-15 15:34:33 +000014601#ifdef _SC_NACLS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014602 {"SC_NACLS_MAX", _SC_NACLS_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000014603#endif
Fred Drakec9680921999-12-13 16:37:25 +000014604#ifdef _SC_NGROUPS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014605 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014606#endif
14607#ifdef _SC_NL_ARGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014608 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014609#endif
14610#ifdef _SC_NL_LANGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014611 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014612#endif
14613#ifdef _SC_NL_MSGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014614 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014615#endif
14616#ifdef _SC_NL_NMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014617 {"SC_NL_NMAX", _SC_NL_NMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014618#endif
14619#ifdef _SC_NL_SETMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014620 {"SC_NL_SETMAX", _SC_NL_SETMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014621#endif
14622#ifdef _SC_NL_TEXTMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014623 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
Fred Drakec9680921999-12-13 16:37:25 +000014624#endif
14625#ifdef _SC_NPROCESSORS_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014626 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
Fred Drakec9680921999-12-13 16:37:25 +000014627#endif
14628#ifdef _SC_NPROCESSORS_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014629 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
Fred Drakec9680921999-12-13 16:37:25 +000014630#endif
Fred Draked86ed291999-12-15 15:34:33 +000014631#ifdef _SC_NPROC_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000014632 {"SC_NPROC_CONF", _SC_NPROC_CONF},
Fred Draked86ed291999-12-15 15:34:33 +000014633#endif
14634#ifdef _SC_NPROC_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000014635 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
Fred Draked86ed291999-12-15 15:34:33 +000014636#endif
Fred Drakec9680921999-12-13 16:37:25 +000014637#ifdef _SC_NZERO
Victor Stinner8c62be82010-05-06 00:08:46 +000014638 {"SC_NZERO", _SC_NZERO},
Fred Drakec9680921999-12-13 16:37:25 +000014639#endif
14640#ifdef _SC_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014641 {"SC_OPEN_MAX", _SC_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014642#endif
14643#ifdef _SC_PAGESIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014644 {"SC_PAGESIZE", _SC_PAGESIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014645#endif
14646#ifdef _SC_PAGE_SIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014647 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014648#endif
14649#ifdef _SC_PASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014650 {"SC_PASS_MAX", _SC_PASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014651#endif
14652#ifdef _SC_PHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000014653 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000014654#endif
14655#ifdef _SC_PII
Victor Stinner8c62be82010-05-06 00:08:46 +000014656 {"SC_PII", _SC_PII},
Fred Drakec9680921999-12-13 16:37:25 +000014657#endif
14658#ifdef _SC_PII_INTERNET
Victor Stinner8c62be82010-05-06 00:08:46 +000014659 {"SC_PII_INTERNET", _SC_PII_INTERNET},
Fred Drakec9680921999-12-13 16:37:25 +000014660#endif
14661#ifdef _SC_PII_INTERNET_DGRAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014662 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
Fred Drakec9680921999-12-13 16:37:25 +000014663#endif
14664#ifdef _SC_PII_INTERNET_STREAM
Victor Stinner8c62be82010-05-06 00:08:46 +000014665 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
Fred Drakec9680921999-12-13 16:37:25 +000014666#endif
14667#ifdef _SC_PII_OSI
Victor Stinner8c62be82010-05-06 00:08:46 +000014668 {"SC_PII_OSI", _SC_PII_OSI},
Fred Drakec9680921999-12-13 16:37:25 +000014669#endif
14670#ifdef _SC_PII_OSI_CLTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014671 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
Fred Drakec9680921999-12-13 16:37:25 +000014672#endif
14673#ifdef _SC_PII_OSI_COTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014674 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
Fred Drakec9680921999-12-13 16:37:25 +000014675#endif
14676#ifdef _SC_PII_OSI_M
Victor Stinner8c62be82010-05-06 00:08:46 +000014677 {"SC_PII_OSI_M", _SC_PII_OSI_M},
Fred Drakec9680921999-12-13 16:37:25 +000014678#endif
14679#ifdef _SC_PII_SOCKET
Victor Stinner8c62be82010-05-06 00:08:46 +000014680 {"SC_PII_SOCKET", _SC_PII_SOCKET},
Fred Drakec9680921999-12-13 16:37:25 +000014681#endif
14682#ifdef _SC_PII_XTI
Victor Stinner8c62be82010-05-06 00:08:46 +000014683 {"SC_PII_XTI", _SC_PII_XTI},
Fred Drakec9680921999-12-13 16:37:25 +000014684#endif
14685#ifdef _SC_POLL
Victor Stinner8c62be82010-05-06 00:08:46 +000014686 {"SC_POLL", _SC_POLL},
Fred Drakec9680921999-12-13 16:37:25 +000014687#endif
14688#ifdef _SC_PRIORITIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014689 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014690#endif
14691#ifdef _SC_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014692 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014693#endif
14694#ifdef _SC_REALTIME_SIGNALS
Victor Stinner8c62be82010-05-06 00:08:46 +000014695 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
Fred Drakec9680921999-12-13 16:37:25 +000014696#endif
14697#ifdef _SC_RE_DUP_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014698 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014699#endif
14700#ifdef _SC_RTSIG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014701 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014702#endif
14703#ifdef _SC_SAVED_IDS
Victor Stinner8c62be82010-05-06 00:08:46 +000014704 {"SC_SAVED_IDS", _SC_SAVED_IDS},
Fred Drakec9680921999-12-13 16:37:25 +000014705#endif
14706#ifdef _SC_SCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014707 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014708#endif
14709#ifdef _SC_SCHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014710 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014711#endif
14712#ifdef _SC_SELECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014713 {"SC_SELECT", _SC_SELECT},
Fred Drakec9680921999-12-13 16:37:25 +000014714#endif
14715#ifdef _SC_SEMAPHORES
Victor Stinner8c62be82010-05-06 00:08:46 +000014716 {"SC_SEMAPHORES", _SC_SEMAPHORES},
Fred Drakec9680921999-12-13 16:37:25 +000014717#endif
14718#ifdef _SC_SEM_NSEMS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014719 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014720#endif
14721#ifdef _SC_SEM_VALUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014722 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014723#endif
14724#ifdef _SC_SHARED_MEMORY_OBJECTS
Victor Stinner8c62be82010-05-06 00:08:46 +000014725 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
Fred Drakec9680921999-12-13 16:37:25 +000014726#endif
14727#ifdef _SC_SHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014728 {"SC_SHRT_MAX", _SC_SHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014729#endif
14730#ifdef _SC_SHRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014731 {"SC_SHRT_MIN", _SC_SHRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014732#endif
14733#ifdef _SC_SIGQUEUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014734 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014735#endif
14736#ifdef _SC_SIGRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014737 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014738#endif
14739#ifdef _SC_SIGRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014740 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014741#endif
Fred Draked86ed291999-12-15 15:34:33 +000014742#ifdef _SC_SOFTPOWER
Victor Stinner8c62be82010-05-06 00:08:46 +000014743 {"SC_SOFTPOWER", _SC_SOFTPOWER},
Fred Draked86ed291999-12-15 15:34:33 +000014744#endif
Fred Drakec9680921999-12-13 16:37:25 +000014745#ifdef _SC_SPLIT_CACHE
Victor Stinner8c62be82010-05-06 00:08:46 +000014746 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
Fred Drakec9680921999-12-13 16:37:25 +000014747#endif
14748#ifdef _SC_SSIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014749 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014750#endif
14751#ifdef _SC_STACK_PROT
Victor Stinner8c62be82010-05-06 00:08:46 +000014752 {"SC_STACK_PROT", _SC_STACK_PROT},
Fred Drakec9680921999-12-13 16:37:25 +000014753#endif
14754#ifdef _SC_STREAM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014755 {"SC_STREAM_MAX", _SC_STREAM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014756#endif
14757#ifdef _SC_SYNCHRONIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000014758 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000014759#endif
14760#ifdef _SC_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014761 {"SC_THREADS", _SC_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014762#endif
14763#ifdef _SC_THREAD_ATTR_STACKADDR
Victor Stinner8c62be82010-05-06 00:08:46 +000014764 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
Fred Drakec9680921999-12-13 16:37:25 +000014765#endif
14766#ifdef _SC_THREAD_ATTR_STACKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000014767 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
Fred Drakec9680921999-12-13 16:37:25 +000014768#endif
14769#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014770 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014771#endif
14772#ifdef _SC_THREAD_KEYS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014773 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014774#endif
14775#ifdef _SC_THREAD_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000014776 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000014777#endif
14778#ifdef _SC_THREAD_PRIO_INHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014779 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
Fred Drakec9680921999-12-13 16:37:25 +000014780#endif
14781#ifdef _SC_THREAD_PRIO_PROTECT
Victor Stinner8c62be82010-05-06 00:08:46 +000014782 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
Fred Drakec9680921999-12-13 16:37:25 +000014783#endif
14784#ifdef _SC_THREAD_PROCESS_SHARED
Victor Stinner8c62be82010-05-06 00:08:46 +000014785 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
Fred Drakec9680921999-12-13 16:37:25 +000014786#endif
14787#ifdef _SC_THREAD_SAFE_FUNCTIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000014788 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
Fred Drakec9680921999-12-13 16:37:25 +000014789#endif
14790#ifdef _SC_THREAD_STACK_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000014791 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000014792#endif
14793#ifdef _SC_THREAD_THREADS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014794 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014795#endif
14796#ifdef _SC_TIMERS
Victor Stinner8c62be82010-05-06 00:08:46 +000014797 {"SC_TIMERS", _SC_TIMERS},
Fred Drakec9680921999-12-13 16:37:25 +000014798#endif
14799#ifdef _SC_TIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014800 {"SC_TIMER_MAX", _SC_TIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014801#endif
14802#ifdef _SC_TTY_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014803 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014804#endif
14805#ifdef _SC_TZNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014806 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014807#endif
14808#ifdef _SC_T_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014809 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014810#endif
14811#ifdef _SC_UCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014812 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014813#endif
14814#ifdef _SC_UINT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014815 {"SC_UINT_MAX", _SC_UINT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014816#endif
14817#ifdef _SC_UIO_MAXIOV
Victor Stinner8c62be82010-05-06 00:08:46 +000014818 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
Fred Drakec9680921999-12-13 16:37:25 +000014819#endif
14820#ifdef _SC_ULONG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014821 {"SC_ULONG_MAX", _SC_ULONG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014822#endif
14823#ifdef _SC_USHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000014824 {"SC_USHRT_MAX", _SC_USHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000014825#endif
14826#ifdef _SC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014827 {"SC_VERSION", _SC_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014828#endif
14829#ifdef _SC_WORD_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000014830 {"SC_WORD_BIT", _SC_WORD_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000014831#endif
14832#ifdef _SC_XBS5_ILP32_OFF32
Victor Stinner8c62be82010-05-06 00:08:46 +000014833 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
Fred Drakec9680921999-12-13 16:37:25 +000014834#endif
14835#ifdef _SC_XBS5_ILP32_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014836 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014837#endif
14838#ifdef _SC_XBS5_LP64_OFF64
Victor Stinner8c62be82010-05-06 00:08:46 +000014839 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
Fred Drakec9680921999-12-13 16:37:25 +000014840#endif
14841#ifdef _SC_XBS5_LPBIG_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000014842 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000014843#endif
14844#ifdef _SC_XOPEN_CRYPT
Victor Stinner8c62be82010-05-06 00:08:46 +000014845 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
Fred Drakec9680921999-12-13 16:37:25 +000014846#endif
14847#ifdef _SC_XOPEN_ENH_I18N
Victor Stinner8c62be82010-05-06 00:08:46 +000014848 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
Fred Drakec9680921999-12-13 16:37:25 +000014849#endif
14850#ifdef _SC_XOPEN_LEGACY
Victor Stinner8c62be82010-05-06 00:08:46 +000014851 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
Fred Drakec9680921999-12-13 16:37:25 +000014852#endif
14853#ifdef _SC_XOPEN_REALTIME
Victor Stinner8c62be82010-05-06 00:08:46 +000014854 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
Fred Drakec9680921999-12-13 16:37:25 +000014855#endif
14856#ifdef _SC_XOPEN_REALTIME_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000014857 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000014858#endif
14859#ifdef _SC_XOPEN_SHM
Victor Stinner8c62be82010-05-06 00:08:46 +000014860 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
Fred Drakec9680921999-12-13 16:37:25 +000014861#endif
14862#ifdef _SC_XOPEN_UNIX
Victor Stinner8c62be82010-05-06 00:08:46 +000014863 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
Fred Drakec9680921999-12-13 16:37:25 +000014864#endif
14865#ifdef _SC_XOPEN_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014866 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014867#endif
14868#ifdef _SC_XOPEN_XCU_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000014869 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000014870#endif
14871#ifdef _SC_XOPEN_XPG2
Victor Stinner8c62be82010-05-06 00:08:46 +000014872 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
Fred Drakec9680921999-12-13 16:37:25 +000014873#endif
14874#ifdef _SC_XOPEN_XPG3
Victor Stinner8c62be82010-05-06 00:08:46 +000014875 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
Fred Drakec9680921999-12-13 16:37:25 +000014876#endif
14877#ifdef _SC_XOPEN_XPG4
Victor Stinner8c62be82010-05-06 00:08:46 +000014878 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
Fred Drakec9680921999-12-13 16:37:25 +000014879#endif
14880};
14881
14882static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014883conv_sysconf_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000014884{
14885 return conv_confname(arg, valuep, posix_constants_sysconf,
14886 sizeof(posix_constants_sysconf)
14887 / sizeof(struct constdef));
14888}
14889
Larry Hastings2f936352014-08-05 14:04:04 +100014890
14891/*[clinic input]
14892os.sysconf -> long
14893 name: sysconf_confname
14894 /
14895
14896Return an integer-valued system configuration variable.
14897[clinic start generated code]*/
14898
14899PyDoc_STRVAR(os_sysconf__doc__,
14900"sysconf($module, name, /)\n"
14901"--\n"
14902"\n"
14903"Return an integer-valued system configuration variable.");
14904
14905#define OS_SYSCONF_METHODDEF \
14906 {"sysconf", (PyCFunction)os_sysconf, METH_VARARGS, os_sysconf__doc__},
14907
14908static long
14909os_sysconf_impl(PyModuleDef *module, int name);
Fred Drakec9680921999-12-13 16:37:25 +000014910
14911static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100014912os_sysconf(PyModuleDef *module, PyObject *args)
Fred Drakec9680921999-12-13 16:37:25 +000014913{
Larry Hastings2f936352014-08-05 14:04:04 +100014914 PyObject *return_value = NULL;
Fred Drakec9680921999-12-13 16:37:25 +000014915 int name;
Larry Hastings2f936352014-08-05 14:04:04 +100014916 long _return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014917
Larry Hastings2f936352014-08-05 14:04:04 +100014918 if (!PyArg_ParseTuple(args,
14919 "O&:sysconf",
14920 conv_sysconf_confname, &name))
14921 goto exit;
14922 _return_value = os_sysconf_impl(module, name);
14923 if ((_return_value == -1) && PyErr_Occurred())
14924 goto exit;
14925 return_value = PyLong_FromLong(_return_value);
Fred Drakec9680921999-12-13 16:37:25 +000014926
Larry Hastings2f936352014-08-05 14:04:04 +100014927exit:
14928 return return_value;
Fred Drakec9680921999-12-13 16:37:25 +000014929}
Larry Hastings2f936352014-08-05 14:04:04 +100014930
14931static long
14932os_sysconf_impl(PyModuleDef *module, int name)
14933/*[clinic end generated code: output=7b06dfdc472431e4 input=279e3430a33f29e4]*/
14934{
14935 long value;
14936
14937 errno = 0;
14938 value = sysconf(name);
14939 if (value == -1 && errno != 0)
14940 posix_error();
14941 return value;
14942}
14943#endif /* HAVE_SYSCONF */
Fred Drakec9680921999-12-13 16:37:25 +000014944
14945
Fred Drakebec628d1999-12-15 18:31:10 +000014946/* This code is used to ensure that the tables of configuration value names
14947 * are in sorted order as required by conv_confname(), and also to build the
14948 * the exported dictionaries that are used to publish information about the
14949 * names available on the host platform.
14950 *
14951 * Sorting the table at runtime ensures that the table is properly ordered
14952 * when used, even for platforms we're not able to test on. It also makes
14953 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +000014954 */
Fred Drakebec628d1999-12-15 18:31:10 +000014955
14956static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014957cmp_constdefs(const void *v1, const void *v2)
Fred Drakebec628d1999-12-15 18:31:10 +000014958{
14959 const struct constdef *c1 =
Victor Stinner8c62be82010-05-06 00:08:46 +000014960 (const struct constdef *) v1;
Fred Drakebec628d1999-12-15 18:31:10 +000014961 const struct constdef *c2 =
Victor Stinner8c62be82010-05-06 00:08:46 +000014962 (const struct constdef *) v2;
Fred Drakebec628d1999-12-15 18:31:10 +000014963
14964 return strcmp(c1->name, c2->name);
14965}
14966
14967static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000014968setup_confname_table(struct constdef *table, size_t tablesize,
Victor Stinner8c62be82010-05-06 00:08:46 +000014969 char *tablename, PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000014970{
Fred Drakebec628d1999-12-15 18:31:10 +000014971 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +000014972 size_t i;
Fred Drakebec628d1999-12-15 18:31:10 +000014973
14974 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
14975 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +000014976 if (d == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +000014977 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000014978
Barry Warsaw3155db32000-04-13 15:20:40 +000014979 for (i=0; i < tablesize; ++i) {
Victor Stinner8c62be82010-05-06 00:08:46 +000014980 PyObject *o = PyLong_FromLong(table[i].value);
14981 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
14982 Py_XDECREF(o);
14983 Py_DECREF(d);
14984 return -1;
14985 }
14986 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +000014987 }
Fred Drake4d1e64b2002-04-15 19:40:07 +000014988 return PyModule_AddObject(module, tablename, d);
Fred Draked86ed291999-12-15 15:34:33 +000014989}
14990
Fred Drakebec628d1999-12-15 18:31:10 +000014991/* Return -1 on failure, 0 on success. */
14992static int
Fred Drake4d1e64b2002-04-15 19:40:07 +000014993setup_confname_tables(PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000014994{
14995#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +000014996 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +000014997 sizeof(posix_constants_pathconf)
14998 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000014999 "pathconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015000 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015001#endif
15002#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +000015003 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +000015004 sizeof(posix_constants_confstr)
15005 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015006 "confstr_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015007 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015008#endif
15009#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +000015010 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +000015011 sizeof(posix_constants_sysconf)
15012 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000015013 "sysconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000015014 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000015015#endif
Fred Drakebec628d1999-12-15 18:31:10 +000015016 return 0;
Fred Draked86ed291999-12-15 15:34:33 +000015017}
Fred Draked86ed291999-12-15 15:34:33 +000015018
15019
Larry Hastings2f936352014-08-05 14:04:04 +100015020/*[clinic input]
15021os.abort
15022
15023Abort the interpreter immediately.
15024
15025This function 'dumps core' or otherwise fails in the hardest way possible
15026on the hosting operating system. This function never returns.
15027[clinic start generated code]*/
15028
15029PyDoc_STRVAR(os_abort__doc__,
15030"abort($module, /)\n"
15031"--\n"
15032"\n"
15033"Abort the interpreter immediately.\n"
15034"\n"
15035"This function \'dumps core\' or otherwise fails in the hardest way possible\n"
15036"on the hosting operating system. This function never returns.");
15037
15038#define OS_ABORT_METHODDEF \
15039 {"abort", (PyCFunction)os_abort, METH_NOARGS, os_abort__doc__},
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015040
15041static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015042os_abort_impl(PyModuleDef *module);
15043
15044static PyObject *
15045os_abort(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15046{
15047 return os_abort_impl(module);
15048}
15049
15050static PyObject *
15051os_abort_impl(PyModuleDef *module)
15052/*[clinic end generated code: output=cded2cc8c5453d3a input=cf2c7d98bc504047]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015053{
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015054 abort();
15055 /*NOTREACHED*/
15056 Py_FatalError("abort() called from Python code didn't abort!");
15057 return NULL;
15058}
Fred Drakebec628d1999-12-15 18:31:10 +000015059
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000015060#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100015061/* AC 3.5: change to path_t? but that might change exceptions */
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015062PyDoc_STRVAR(win32_startfile__doc__,
Larry Hastings2f936352014-08-05 14:04:04 +100015063"startfile(filepath [, operation])\n\
15064\n\
15065Start a file with its associated application.\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015066\n\
Georg Brandlf4f44152006-02-18 22:29:33 +000015067When \"operation\" is not specified or \"open\", this acts like\n\
15068double-clicking the file in Explorer, or giving the file name as an\n\
15069argument to the DOS \"start\" command: the file is opened with whatever\n\
15070application (if any) its extension is associated.\n\
15071When another \"operation\" is given, it specifies what should be done with\n\
15072the file. A typical operation is \"print\".\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000015073\n\
15074startfile returns as soon as the associated application is launched.\n\
15075There is no option to wait for the application to close, and no way\n\
15076to retrieve the application's exit status.\n\
15077\n\
15078The filepath is relative to the current directory. If you want to use\n\
15079an absolute path, make sure the first character is not a slash (\"/\");\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000015080the underlying Win32 ShellExecute function doesn't work if it is.");
Tim Petersf58a7aa2000-09-22 10:05:54 +000015081
15082static PyObject *
15083win32_startfile(PyObject *self, PyObject *args)
15084{
Victor Stinner8c62be82010-05-06 00:08:46 +000015085 PyObject *ofilepath;
15086 char *filepath;
15087 char *operation = NULL;
Victor Stinnereb5657a2011-09-30 01:44:27 +020015088 wchar_t *wpath, *woperation;
Victor Stinner8c62be82010-05-06 00:08:46 +000015089 HINSTANCE rc;
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +000015090
Victor Stinnereb5657a2011-09-30 01:44:27 +020015091 PyObject *unipath, *uoperation = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015092 if (!PyArg_ParseTuple(args, "U|s:startfile",
15093 &unipath, &operation)) {
15094 PyErr_Clear();
15095 goto normal;
15096 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015097
Victor Stinner8c62be82010-05-06 00:08:46 +000015098 if (operation) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015099 uoperation = PyUnicode_DecodeASCII(operation,
Victor Stinner8c62be82010-05-06 00:08:46 +000015100 strlen(operation), NULL);
Victor Stinnereb5657a2011-09-30 01:44:27 +020015101 if (!uoperation) {
Victor Stinner8c62be82010-05-06 00:08:46 +000015102 PyErr_Clear();
15103 operation = NULL;
15104 goto normal;
15105 }
15106 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000015107
Victor Stinnereb5657a2011-09-30 01:44:27 +020015108 wpath = PyUnicode_AsUnicode(unipath);
15109 if (wpath == NULL)
15110 goto normal;
15111 if (uoperation) {
15112 woperation = PyUnicode_AsUnicode(uoperation);
15113 if (woperation == NULL)
15114 goto normal;
15115 }
15116 else
15117 woperation = NULL;
15118
Victor Stinner8c62be82010-05-06 00:08:46 +000015119 Py_BEGIN_ALLOW_THREADS
Victor Stinnereb5657a2011-09-30 01:44:27 +020015120 rc = ShellExecuteW((HWND)0, woperation, wpath,
15121 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000015122 Py_END_ALLOW_THREADS
15123
Victor Stinnereb5657a2011-09-30 01:44:27 +020015124 Py_XDECREF(uoperation);
Victor Stinner8c62be82010-05-06 00:08:46 +000015125 if (rc <= (HINSTANCE)32) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020015126 win32_error_object("startfile", unipath);
15127 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000015128 }
15129 Py_INCREF(Py_None);
15130 return Py_None;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000015131
15132normal:
Victor Stinner8c62be82010-05-06 00:08:46 +000015133 if (!PyArg_ParseTuple(args, "O&|s:startfile",
15134 PyUnicode_FSConverter, &ofilepath,
15135 &operation))
15136 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +010015137 if (win32_warn_bytes_api()) {
15138 Py_DECREF(ofilepath);
15139 return NULL;
15140 }
Victor Stinner8c62be82010-05-06 00:08:46 +000015141 filepath = PyBytes_AsString(ofilepath);
15142 Py_BEGIN_ALLOW_THREADS
15143 rc = ShellExecute((HWND)0, operation, filepath,
15144 NULL, NULL, SW_SHOWNORMAL);
15145 Py_END_ALLOW_THREADS
15146 if (rc <= (HINSTANCE)32) {
15147 PyObject *errval = win32_error("startfile", filepath);
15148 Py_DECREF(ofilepath);
15149 return errval;
15150 }
15151 Py_DECREF(ofilepath);
15152 Py_INCREF(Py_None);
15153 return Py_None;
Tim Petersf58a7aa2000-09-22 10:05:54 +000015154}
Larry Hastings2f936352014-08-05 14:04:04 +100015155#endif /* MS_WINDOWS */
15156
Fred Drake5ab8eaf1999-12-09 21:13:07 +000015157
Martin v. Löwis438b5342002-12-27 10:16:42 +000015158#ifdef HAVE_GETLOADAVG
Larry Hastings2f936352014-08-05 14:04:04 +100015159/*[clinic input]
15160os.getloadavg
15161
15162Return average recent system load information.
15163
15164Return the number of processes in the system run queue averaged over
15165the last 1, 5, and 15 minutes as a tuple of three floats.
15166Raises OSError if the load average was unobtainable.
15167[clinic start generated code]*/
15168
15169PyDoc_STRVAR(os_getloadavg__doc__,
15170"getloadavg($module, /)\n"
15171"--\n"
15172"\n"
15173"Return average recent system load information.\n"
15174"\n"
15175"Return the number of processes in the system run queue averaged over\n"
15176"the last 1, 5, and 15 minutes as a tuple of three floats.\n"
15177"Raises OSError if the load average was unobtainable.");
15178
15179#define OS_GETLOADAVG_METHODDEF \
15180 {"getloadavg", (PyCFunction)os_getloadavg, METH_NOARGS, os_getloadavg__doc__},
Martin v. Löwis438b5342002-12-27 10:16:42 +000015181
15182static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015183os_getloadavg_impl(PyModuleDef *module);
15184
15185static PyObject *
15186os_getloadavg(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15187{
15188 return os_getloadavg_impl(module);
15189}
15190
15191static PyObject *
15192os_getloadavg_impl(PyModuleDef *module)
15193/*[clinic end generated code: output=67593a92457d55af input=3d6d826b76d8a34e]*/
Martin v. Löwis438b5342002-12-27 10:16:42 +000015194{
15195 double loadavg[3];
Martin v. Löwis438b5342002-12-27 10:16:42 +000015196 if (getloadavg(loadavg, 3)!=3) {
Stefan Krah0e803b32010-11-26 16:16:47 +000015197 PyErr_SetString(PyExc_OSError, "Load averages are unobtainable");
15198 return NULL;
Martin v. Löwis438b5342002-12-27 10:16:42 +000015199 } else
Stefan Krah0e803b32010-11-26 16:16:47 +000015200 return Py_BuildValue("ddd", loadavg[0], loadavg[1], loadavg[2]);
Martin v. Löwis438b5342002-12-27 10:16:42 +000015201}
Larry Hastings2f936352014-08-05 14:04:04 +100015202#endif /* HAVE_GETLOADAVG */
Martin v. Löwis438b5342002-12-27 10:16:42 +000015203
Larry Hastings2f936352014-08-05 14:04:04 +100015204
15205/*[clinic input]
15206os.device_encoding
15207 fd: int
15208
15209Return a string describing the encoding of a terminal's file descriptor.
15210
15211The file descriptor must be attached to a terminal.
15212If the device is not a terminal, return None.
15213[clinic start generated code]*/
15214
15215PyDoc_STRVAR(os_device_encoding__doc__,
15216"device_encoding($module, /, fd)\n"
15217"--\n"
15218"\n"
15219"Return a string describing the encoding of a terminal\'s file descriptor.\n"
15220"\n"
15221"The file descriptor must be attached to a terminal.\n"
15222"If the device is not a terminal, return None.");
15223
15224#define OS_DEVICE_ENCODING_METHODDEF \
15225 {"device_encoding", (PyCFunction)os_device_encoding, METH_VARARGS|METH_KEYWORDS, os_device_encoding__doc__},
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015226
15227static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015228os_device_encoding_impl(PyModuleDef *module, int fd);
15229
15230static PyObject *
15231os_device_encoding(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015232{
Larry Hastings2f936352014-08-05 14:04:04 +100015233 PyObject *return_value = NULL;
15234 static char *_keywords[] = {"fd", NULL};
Victor Stinner8c62be82010-05-06 00:08:46 +000015235 int fd;
Brett Cannonefb00c02012-02-29 18:31:31 -050015236
Larry Hastings2f936352014-08-05 14:04:04 +100015237 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15238 "i:device_encoding", _keywords,
15239 &fd))
15240 goto exit;
15241 return_value = os_device_encoding_impl(module, fd);
Brett Cannonefb00c02012-02-29 18:31:31 -050015242
Larry Hastings2f936352014-08-05 14:04:04 +100015243exit:
15244 return return_value;
15245}
15246
15247static PyObject *
15248os_device_encoding_impl(PyModuleDef *module, int fd)
15249/*[clinic end generated code: output=e9f8274d42f5cce3 input=9e1d4a42b66df312]*/
15250{
Brett Cannonefb00c02012-02-29 18:31:31 -050015251 return _Py_device_encoding(fd);
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000015252}
15253
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015254
Larry Hastings2f936352014-08-05 14:04:04 +100015255#ifdef HAVE_SETRESUID
15256/*[clinic input]
15257os.setresuid
15258
15259 ruid: uid_t
15260 euid: uid_t
15261 suid: uid_t
15262 /
15263
15264Set the current process's real, effective, and saved user ids.
15265[clinic start generated code]*/
15266
15267PyDoc_STRVAR(os_setresuid__doc__,
15268"setresuid($module, ruid, euid, suid, /)\n"
15269"--\n"
15270"\n"
15271"Set the current process\'s real, effective, and saved user ids.");
15272
15273#define OS_SETRESUID_METHODDEF \
15274 {"setresuid", (PyCFunction)os_setresuid, METH_VARARGS, os_setresuid__doc__},
15275
15276static PyObject *
15277os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid);
15278
15279static PyObject *
15280os_setresuid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015281{
Larry Hastings2f936352014-08-05 14:04:04 +100015282 PyObject *return_value = NULL;
15283 uid_t ruid;
15284 uid_t euid;
15285 uid_t suid;
15286
15287 if (!PyArg_ParseTuple(args,
15288 "O&O&O&:setresuid",
15289 _Py_Uid_Converter, &ruid, _Py_Uid_Converter, &euid, _Py_Uid_Converter, &suid))
15290 goto exit;
15291 return_value = os_setresuid_impl(module, ruid, euid, suid);
15292
15293exit:
15294 return return_value;
15295}
15296
15297static PyObject *
15298os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid)
15299/*[clinic end generated code: output=2e3457cfe7cd1f94 input=9e33cb79a82792f3]*/
15300{
Victor Stinner8c62be82010-05-06 00:08:46 +000015301 if (setresuid(ruid, euid, suid) < 0)
15302 return posix_error();
15303 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015304}
Larry Hastings2f936352014-08-05 14:04:04 +100015305#endif /* HAVE_SETRESUID */
15306
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015307
15308#ifdef HAVE_SETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015309/*[clinic input]
15310os.setresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015311
Larry Hastings2f936352014-08-05 14:04:04 +100015312 rgid: gid_t
15313 egid: gid_t
15314 sgid: gid_t
15315 /
15316
15317Set the current process's real, effective, and saved group ids.
15318[clinic start generated code]*/
15319
15320PyDoc_STRVAR(os_setresgid__doc__,
15321"setresgid($module, rgid, egid, sgid, /)\n"
15322"--\n"
15323"\n"
15324"Set the current process\'s real, effective, and saved group ids.");
15325
15326#define OS_SETRESGID_METHODDEF \
15327 {"setresgid", (PyCFunction)os_setresgid, METH_VARARGS, os_setresgid__doc__},
15328
15329static PyObject *
15330os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid);
15331
15332static PyObject *
15333os_setresgid(PyModuleDef *module, PyObject *args)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015334{
Larry Hastings2f936352014-08-05 14:04:04 +100015335 PyObject *return_value = NULL;
15336 gid_t rgid;
15337 gid_t egid;
15338 gid_t sgid;
15339
15340 if (!PyArg_ParseTuple(args,
15341 "O&O&O&:setresgid",
15342 _Py_Gid_Converter, &rgid, _Py_Gid_Converter, &egid, _Py_Gid_Converter, &sgid))
15343 goto exit;
15344 return_value = os_setresgid_impl(module, rgid, egid, sgid);
15345
15346exit:
15347 return return_value;
15348}
15349
15350static PyObject *
15351os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid)
15352/*[clinic end generated code: output=8a7ee6c1f2482362 input=33e9e0785ef426b1]*/
15353{
Victor Stinner8c62be82010-05-06 00:08:46 +000015354 if (setresgid(rgid, egid, sgid) < 0)
15355 return posix_error();
15356 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015357}
Larry Hastings2f936352014-08-05 14:04:04 +100015358#endif /* HAVE_SETRESGID */
15359
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015360
15361#ifdef HAVE_GETRESUID
Larry Hastings2f936352014-08-05 14:04:04 +100015362/*[clinic input]
15363os.getresuid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015364
Larry Hastings2f936352014-08-05 14:04:04 +100015365Return a tuple of the current process's real, effective, and saved user ids.
15366[clinic start generated code]*/
15367
15368PyDoc_STRVAR(os_getresuid__doc__,
15369"getresuid($module, /)\n"
15370"--\n"
15371"\n"
15372"Return a tuple of the current process\'s real, effective, and saved user ids.");
15373
15374#define OS_GETRESUID_METHODDEF \
15375 {"getresuid", (PyCFunction)os_getresuid, METH_NOARGS, os_getresuid__doc__},
15376
15377static PyObject *
15378os_getresuid_impl(PyModuleDef *module);
15379
15380static PyObject *
15381os_getresuid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
15382{
15383 return os_getresuid_impl(module);
15384}
15385
15386static PyObject *
15387os_getresuid_impl(PyModuleDef *module)
15388/*[clinic end generated code: output=d0786686a6ef1320 input=41ccfa8e1f6517ad]*/
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015389{
Victor Stinner8c62be82010-05-06 00:08:46 +000015390 uid_t ruid, euid, suid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015391 if (getresuid(&ruid, &euid, &suid) < 0)
15392 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015393 return Py_BuildValue("(NNN)", _PyLong_FromUid(ruid),
15394 _PyLong_FromUid(euid),
15395 _PyLong_FromUid(suid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015396}
Larry Hastings2f936352014-08-05 14:04:04 +100015397#endif /* HAVE_GETRESUID */
15398
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015399
15400#ifdef HAVE_GETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100015401/*[clinic input]
15402os.getresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015403
Larry Hastings2f936352014-08-05 14:04:04 +100015404Return a tuple of the current process's real, effective, and saved group ids.
15405[clinic start generated code]*/
15406
15407PyDoc_STRVAR(os_getresgid__doc__,
15408"getresgid($module, /)\n"
15409"--\n"
15410"\n"
15411"Return a tuple of the current process\'s real, effective, and saved group ids.");
15412
15413#define OS_GETRESGID_METHODDEF \
15414 {"getresgid", (PyCFunction)os_getresgid, METH_NOARGS, os_getresgid__doc__},
15415
15416static PyObject *
15417os_getresgid_impl(PyModuleDef *module);
15418
15419static PyObject *
15420os_getresgid(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015421{
Larry Hastings2f936352014-08-05 14:04:04 +100015422 return os_getresgid_impl(module);
15423}
15424
15425static PyObject *
15426os_getresgid_impl(PyModuleDef *module)
15427/*[clinic end generated code: output=05249ac795fa759f input=517e68db9ca32df6]*/
15428{
15429 gid_t rgid, egid, sgid;
Victor Stinner8c62be82010-05-06 00:08:46 +000015430 if (getresgid(&rgid, &egid, &sgid) < 0)
15431 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020015432 return Py_BuildValue("(NNN)", _PyLong_FromGid(rgid),
15433 _PyLong_FromGid(egid),
15434 _PyLong_FromGid(sgid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015435}
Larry Hastings2f936352014-08-05 14:04:04 +100015436#endif /* HAVE_GETRESGID */
15437
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000015438
Benjamin Peterson9428d532011-09-14 11:45:52 -040015439#ifdef USE_XATTRS
Larry Hastings2f936352014-08-05 14:04:04 +100015440/*[clinic input]
15441os.getxattr
Benjamin Peterson799bd802011-08-31 22:15:17 -040015442
Larry Hastings2f936352014-08-05 14:04:04 +100015443 path: path_t(allow_fd=True)
15444 attribute: path_t
15445 *
15446 follow_symlinks: bool = True
15447
15448Return the value of extended attribute attribute on path.
15449
15450path may be either a string or an open file descriptor.
15451If follow_symlinks is False, and the last element of the path is a symbolic
15452 link, getxattr will examine the symbolic link itself instead of the file
15453 the link points to.
15454
15455[clinic start generated code]*/
15456
15457PyDoc_STRVAR(os_getxattr__doc__,
15458"getxattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15459"--\n"
15460"\n"
15461"Return the value of extended attribute attribute on path.\n"
15462"\n"
15463"path may be either a string or an open file descriptor.\n"
15464"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15465" link, getxattr will examine the symbolic link itself instead of the file\n"
15466" the link points to.");
15467
15468#define OS_GETXATTR_METHODDEF \
15469 {"getxattr", (PyCFunction)os_getxattr, METH_VARARGS|METH_KEYWORDS, os_getxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015470
15471static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015472os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15473
15474static PyObject *
15475os_getxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015476{
Larry Hastings2f936352014-08-05 14:04:04 +100015477 PyObject *return_value = NULL;
15478 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15479 path_t path = PATH_T_INITIALIZE("getxattr", "path", 0, 1);
15480 path_t attribute = PATH_T_INITIALIZE("getxattr", "attribute", 0, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015481 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015482
Larry Hastings2f936352014-08-05 14:04:04 +100015483 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15484 "O&O&|$p:getxattr", _keywords,
15485 path_converter, &path, path_converter, &attribute, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015486 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015487 return_value = os_getxattr_impl(module, &path, &attribute, follow_symlinks);
15488
15489exit:
15490 /* Cleanup for path */
15491 path_cleanup(&path);
15492 /* Cleanup for attribute */
15493 path_cleanup(&attribute);
15494
15495 return return_value;
15496}
15497
15498static PyObject *
15499os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15500/*[clinic end generated code: output=bbc9454fe2b9ea86 input=8c8ea3bab78d89c2]*/
15501{
15502 Py_ssize_t i;
15503 PyObject *buffer = NULL;
15504
15505 if (fd_and_follow_symlinks_invalid("getxattr", path->fd, follow_symlinks))
15506 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015507
Larry Hastings9cf065c2012-06-22 16:30:09 -070015508 for (i = 0; ; i++) {
15509 void *ptr;
15510 ssize_t result;
15511 static Py_ssize_t buffer_sizes[] = {128, XATTR_SIZE_MAX, 0};
15512 Py_ssize_t buffer_size = buffer_sizes[i];
15513 if (!buffer_size) {
Larry Hastings2f936352014-08-05 14:04:04 +100015514 path_error(path);
15515 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015516 }
15517 buffer = PyBytes_FromStringAndSize(NULL, buffer_size);
15518 if (!buffer)
Larry Hastings2f936352014-08-05 14:04:04 +100015519 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015520 ptr = PyBytes_AS_STRING(buffer);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015521
Larry Hastings9cf065c2012-06-22 16:30:09 -070015522 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015523 if (path->fd >= 0)
15524 result = fgetxattr(path->fd, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015525 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015526 result = getxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015527 else
Larry Hastings2f936352014-08-05 14:04:04 +100015528 result = lgetxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015529 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015530
Larry Hastings9cf065c2012-06-22 16:30:09 -070015531 if (result < 0) {
15532 Py_DECREF(buffer);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015533 if (errno == ERANGE)
15534 continue;
Larry Hastings2f936352014-08-05 14:04:04 +100015535 path_error(path);
15536 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015537 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015538
Larry Hastings9cf065c2012-06-22 16:30:09 -070015539 if (result != buffer_size) {
15540 /* Can only shrink. */
15541 _PyBytes_Resize(&buffer, result);
15542 }
15543 break;
15544 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015545
Larry Hastings9cf065c2012-06-22 16:30:09 -070015546 return buffer;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015547}
15548
Larry Hastings2f936352014-08-05 14:04:04 +100015549
15550/*[clinic input]
15551os.setxattr
15552
15553 path: path_t(allow_fd=True)
15554 attribute: path_t
15555 value: Py_buffer
15556 flags: int = 0
15557 *
15558 follow_symlinks: bool = True
15559
15560Set extended attribute attribute on path to value.
15561
15562path may be either a string or an open file descriptor.
15563If follow_symlinks is False, and the last element of the path is a symbolic
15564 link, setxattr will modify the symbolic link itself instead of the file
15565 the link points to.
15566
15567[clinic start generated code]*/
15568
15569PyDoc_STRVAR(os_setxattr__doc__,
15570"setxattr($module, /, path, attribute, value, flags=0, *,\n"
15571" follow_symlinks=True)\n"
15572"--\n"
15573"\n"
15574"Set extended attribute attribute on path to value.\n"
15575"\n"
15576"path may be either a string or an open file descriptor.\n"
15577"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15578" link, setxattr will modify the symbolic link itself instead of the file\n"
15579" the link points to.");
15580
15581#define OS_SETXATTR_METHODDEF \
15582 {"setxattr", (PyCFunction)os_setxattr, METH_VARARGS|METH_KEYWORDS, os_setxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015583
15584static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015585os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks);
15586
15587static PyObject *
15588os_setxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015589{
Larry Hastings2f936352014-08-05 14:04:04 +100015590 PyObject *return_value = NULL;
15591 static char *_keywords[] = {"path", "attribute", "value", "flags", "follow_symlinks", NULL};
15592 path_t path = PATH_T_INITIALIZE("setxattr", "path", 0, 1);
15593 path_t attribute = PATH_T_INITIALIZE("setxattr", "attribute", 0, 0);
15594 Py_buffer value = {NULL, NULL};
Larry Hastings9cf065c2012-06-22 16:30:09 -070015595 int flags = 0;
15596 int follow_symlinks = 1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015597
Larry Hastings2f936352014-08-05 14:04:04 +100015598 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15599 "O&O&y*|i$p:setxattr", _keywords,
15600 path_converter, &path, path_converter, &attribute, &value, &flags, &follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015601 goto exit;
Larry Hastings2f936352014-08-05 14:04:04 +100015602 return_value = os_setxattr_impl(module, &path, &attribute, &value, flags, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015603
Larry Hastings9cf065c2012-06-22 16:30:09 -070015604exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015605 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015606 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015607 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015608 path_cleanup(&attribute);
Larry Hastings2f936352014-08-05 14:04:04 +100015609 /* Cleanup for value */
15610 if (value.obj)
15611 PyBuffer_Release(&value);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015612
Larry Hastings9cf065c2012-06-22 16:30:09 -070015613 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015614}
15615
Benjamin Peterson799bd802011-08-31 22:15:17 -040015616static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015617os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, Py_buffer *value, int flags, int follow_symlinks)
15618/*[clinic end generated code: output=2ff845d8e024b218 input=f0d26833992015c2]*/
Benjamin Peterson799bd802011-08-31 22:15:17 -040015619{
Larry Hastings2f936352014-08-05 14:04:04 +100015620 ssize_t result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015621
Larry Hastings2f936352014-08-05 14:04:04 +100015622 if (fd_and_follow_symlinks_invalid("setxattr", path->fd, follow_symlinks))
Benjamin Peterson799bd802011-08-31 22:15:17 -040015623 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015624
Benjamin Peterson799bd802011-08-31 22:15:17 -040015625 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015626 if (path->fd > -1)
15627 result = fsetxattr(path->fd, attribute->narrow,
15628 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015629 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100015630 result = setxattr(path->narrow, attribute->narrow,
15631 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015632 else
Larry Hastings2f936352014-08-05 14:04:04 +100015633 result = lsetxattr(path->narrow, attribute->narrow,
15634 value->buf, value->len, flags);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015635 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015636
Larry Hastings9cf065c2012-06-22 16:30:09 -070015637 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100015638 path_error(path);
15639 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015640 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015641
Larry Hastings2f936352014-08-05 14:04:04 +100015642 Py_RETURN_NONE;
15643}
15644
15645
15646/*[clinic input]
15647os.removexattr
15648
15649 path: path_t(allow_fd=True)
15650 attribute: path_t
15651 *
15652 follow_symlinks: bool = True
15653
15654Remove extended attribute attribute on path.
15655
15656path may be either a string or an open file descriptor.
15657If follow_symlinks is False, and the last element of the path is a symbolic
15658 link, removexattr will modify the symbolic link itself instead of the file
15659 the link points to.
15660
15661[clinic start generated code]*/
15662
15663PyDoc_STRVAR(os_removexattr__doc__,
15664"removexattr($module, /, path, attribute, *, follow_symlinks=True)\n"
15665"--\n"
15666"\n"
15667"Remove extended attribute attribute on path.\n"
15668"\n"
15669"path may be either a string or an open file descriptor.\n"
15670"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15671" link, removexattr will modify the symbolic link itself instead of the file\n"
15672" the link points to.");
15673
15674#define OS_REMOVEXATTR_METHODDEF \
15675 {"removexattr", (PyCFunction)os_removexattr, METH_VARARGS|METH_KEYWORDS, os_removexattr__doc__},
15676
15677static PyObject *
15678os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks);
15679
15680static PyObject *
15681os_removexattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
15682{
15683 PyObject *return_value = NULL;
15684 static char *_keywords[] = {"path", "attribute", "follow_symlinks", NULL};
15685 path_t path = PATH_T_INITIALIZE("removexattr", "path", 0, 1);
15686 path_t attribute = PATH_T_INITIALIZE("removexattr", "attribute", 0, 0);
15687 int follow_symlinks = 1;
15688
15689 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15690 "O&O&|$p:removexattr", _keywords,
15691 path_converter, &path, path_converter, &attribute, &follow_symlinks))
15692 goto exit;
15693 return_value = os_removexattr_impl(module, &path, &attribute, follow_symlinks);
Benjamin Peterson799bd802011-08-31 22:15:17 -040015694
Larry Hastings9cf065c2012-06-22 16:30:09 -070015695exit:
Larry Hastings2f936352014-08-05 14:04:04 +100015696 /* Cleanup for path */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015697 path_cleanup(&path);
Larry Hastings2f936352014-08-05 14:04:04 +100015698 /* Cleanup for attribute */
Larry Hastings9cf065c2012-06-22 16:30:09 -070015699 path_cleanup(&attribute);
15700
15701 return return_value;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015702}
15703
Larry Hastings2f936352014-08-05 14:04:04 +100015704static PyObject *
15705os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute, int follow_symlinks)
15706/*[clinic end generated code: output=8dfc715bf607c4cf input=cdb54834161e3329]*/
15707{
15708 ssize_t result;
15709
15710 if (fd_and_follow_symlinks_invalid("removexattr", path->fd, follow_symlinks))
15711 return NULL;
15712
15713 Py_BEGIN_ALLOW_THREADS;
15714 if (path->fd > -1)
15715 result = fremovexattr(path->fd, attribute->narrow);
15716 else if (follow_symlinks)
15717 result = removexattr(path->narrow, attribute->narrow);
15718 else
15719 result = lremovexattr(path->narrow, attribute->narrow);
15720 Py_END_ALLOW_THREADS;
15721
15722 if (result) {
15723 return path_error(path);
15724 }
15725
15726 Py_RETURN_NONE;
15727}
15728
15729
15730/*[clinic input]
15731os.listxattr
15732
15733 path: path_t(allow_fd=True, nullable=True) = None
15734 *
15735 follow_symlinks: bool = True
15736
15737Return a list of extended attributes on path.
15738
15739path may be either None, a string, or an open file descriptor.
15740if path is None, listxattr will examine the current directory.
15741If follow_symlinks is False, and the last element of the path is a symbolic
15742 link, listxattr will examine the symbolic link itself instead of the file
15743 the link points to.
15744[clinic start generated code]*/
15745
15746PyDoc_STRVAR(os_listxattr__doc__,
15747"listxattr($module, /, path=None, *, follow_symlinks=True)\n"
15748"--\n"
15749"\n"
15750"Return a list of extended attributes on path.\n"
15751"\n"
15752"path may be either None, a string, or an open file descriptor.\n"
15753"if path is None, listxattr will examine the current directory.\n"
15754"If follow_symlinks is False, and the last element of the path is a symbolic\n"
15755" link, listxattr will examine the symbolic link itself instead of the file\n"
15756" the link points to.");
15757
15758#define OS_LISTXATTR_METHODDEF \
15759 {"listxattr", (PyCFunction)os_listxattr, METH_VARARGS|METH_KEYWORDS, os_listxattr__doc__},
Benjamin Peterson799bd802011-08-31 22:15:17 -040015760
15761static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015762os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks);
15763
15764static PyObject *
15765os_listxattr(PyModuleDef *module, PyObject *args, PyObject *kwargs)
Benjamin Peterson799bd802011-08-31 22:15:17 -040015766{
Larry Hastings2f936352014-08-05 14:04:04 +100015767 PyObject *return_value = NULL;
15768 static char *_keywords[] = {"path", "follow_symlinks", NULL};
15769 path_t path = PATH_T_INITIALIZE("listxattr", "path", 1, 1);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015770 int follow_symlinks = 1;
Larry Hastings2f936352014-08-05 14:04:04 +100015771
15772 if (!PyArg_ParseTupleAndKeywords(args, kwargs,
15773 "|O&$p:listxattr", _keywords,
15774 path_converter, &path, &follow_symlinks))
15775 goto exit;
15776 return_value = os_listxattr_impl(module, &path, follow_symlinks);
15777
15778exit:
15779 /* Cleanup for path */
15780 path_cleanup(&path);
15781
15782 return return_value;
15783}
15784
15785static PyObject *
15786os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks)
15787/*[clinic end generated code: output=3104cafda1a3d887 input=08cca53ac0b07c13]*/
15788{
Larry Hastings9cf065c2012-06-22 16:30:09 -070015789 Py_ssize_t i;
15790 PyObject *result = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100015791 const char *name;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015792 char *buffer = NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015793
Larry Hastings2f936352014-08-05 14:04:04 +100015794 if (fd_and_follow_symlinks_invalid("listxattr", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070015795 goto exit;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015796
Larry Hastings2f936352014-08-05 14:04:04 +100015797 name = path->narrow ? path->narrow : ".";
15798
Larry Hastings9cf065c2012-06-22 16:30:09 -070015799 for (i = 0; ; i++) {
15800 char *start, *trace, *end;
15801 ssize_t length;
15802 static Py_ssize_t buffer_sizes[] = { 256, XATTR_LIST_MAX, 0 };
15803 Py_ssize_t buffer_size = buffer_sizes[i];
15804 if (!buffer_size) {
Christian Heimes3b9493b2012-09-23 16:11:15 +020015805 /* ERANGE */
Larry Hastings2f936352014-08-05 14:04:04 +100015806 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015807 break;
15808 }
15809 buffer = PyMem_MALLOC(buffer_size);
15810 if (!buffer) {
15811 PyErr_NoMemory();
15812 break;
15813 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015814
Larry Hastings9cf065c2012-06-22 16:30:09 -070015815 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100015816 if (path->fd > -1)
15817 length = flistxattr(path->fd, buffer, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015818 else if (follow_symlinks)
15819 length = listxattr(name, buffer, buffer_size);
15820 else
15821 length = llistxattr(name, buffer, buffer_size);
15822 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015823
Larry Hastings9cf065c2012-06-22 16:30:09 -070015824 if (length < 0) {
Antoine Pitrou7f987392013-05-13 19:46:29 +020015825 if (errno == ERANGE) {
15826 PyMem_FREE(buffer);
Benjamin Petersondedac522013-05-13 19:55:40 -050015827 buffer = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070015828 continue;
Antoine Pitrou7f987392013-05-13 19:46:29 +020015829 }
Larry Hastings2f936352014-08-05 14:04:04 +100015830 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070015831 break;
15832 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015833
Larry Hastings9cf065c2012-06-22 16:30:09 -070015834 result = PyList_New(0);
15835 if (!result) {
15836 goto exit;
15837 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040015838
Larry Hastings9cf065c2012-06-22 16:30:09 -070015839 end = buffer + length;
15840 for (trace = start = buffer; trace != end; trace++) {
15841 if (!*trace) {
15842 int error;
15843 PyObject *attribute = PyUnicode_DecodeFSDefaultAndSize(start,
15844 trace - start);
15845 if (!attribute) {
15846 Py_DECREF(result);
15847 result = NULL;
15848 goto exit;
15849 }
15850 error = PyList_Append(result, attribute);
15851 Py_DECREF(attribute);
15852 if (error) {
15853 Py_DECREF(result);
15854 result = NULL;
15855 goto exit;
15856 }
15857 start = trace + 1;
15858 }
15859 }
15860 break;
15861 }
15862exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070015863 if (buffer)
15864 PyMem_FREE(buffer);
15865 return result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040015866}
Benjamin Peterson9428d532011-09-14 11:45:52 -040015867#endif /* USE_XATTRS */
Benjamin Peterson799bd802011-08-31 22:15:17 -040015868
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015869
Larry Hastings2f936352014-08-05 14:04:04 +100015870/*[clinic input]
15871os.urandom
15872
15873 size: Py_ssize_t
15874 /
15875
15876Return a bytes object containing random bytes suitable for cryptographic use.
15877[clinic start generated code]*/
15878
15879PyDoc_STRVAR(os_urandom__doc__,
15880"urandom($module, size, /)\n"
15881"--\n"
15882"\n"
15883"Return a bytes object containing random bytes suitable for cryptographic use.");
15884
15885#define OS_URANDOM_METHODDEF \
15886 {"urandom", (PyCFunction)os_urandom, METH_VARARGS, os_urandom__doc__},
Georg Brandl2fb477c2012-02-21 00:33:36 +010015887
15888static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100015889os_urandom_impl(PyModuleDef *module, Py_ssize_t size);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015890
Larry Hastings2f936352014-08-05 14:04:04 +100015891static PyObject *
15892os_urandom(PyModuleDef *module, PyObject *args)
15893{
15894 PyObject *return_value = NULL;
15895 Py_ssize_t size;
15896
15897 if (!PyArg_ParseTuple(args,
15898 "n:urandom",
15899 &size))
15900 goto exit;
15901 return_value = os_urandom_impl(module, size);
15902
15903exit:
15904 return return_value;
15905}
15906
15907static PyObject *
15908os_urandom_impl(PyModuleDef *module, Py_ssize_t size)
15909/*[clinic end generated code: output=5dbff582cab94cb9 input=4067cdb1b6776c29]*/
15910{
15911 PyObject *bytes;
15912 int result;
15913
Georg Brandl2fb477c2012-02-21 00:33:36 +010015914 if (size < 0)
15915 return PyErr_Format(PyExc_ValueError,
15916 "negative argument not allowed");
Larry Hastings2f936352014-08-05 14:04:04 +100015917 bytes = PyBytes_FromStringAndSize(NULL, size);
15918 if (bytes == NULL)
Georg Brandl2fb477c2012-02-21 00:33:36 +010015919 return NULL;
15920
Larry Hastings2f936352014-08-05 14:04:04 +100015921 result = _PyOS_URandom(PyBytes_AS_STRING(bytes),
15922 PyBytes_GET_SIZE(bytes));
15923 if (result == -1) {
15924 Py_DECREF(bytes);
Georg Brandl2fb477c2012-02-21 00:33:36 +010015925 return NULL;
15926 }
Larry Hastings2f936352014-08-05 14:04:04 +100015927 return bytes;
Georg Brandl2fb477c2012-02-21 00:33:36 +010015928}
15929
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015930/* Terminal size querying */
15931
15932static PyTypeObject TerminalSizeType;
15933
15934PyDoc_STRVAR(TerminalSize_docstring,
15935 "A tuple of (columns, lines) for holding terminal window size");
15936
15937static PyStructSequence_Field TerminalSize_fields[] = {
15938 {"columns", "width of the terminal window in characters"},
15939 {"lines", "height of the terminal window in characters"},
15940 {NULL, NULL}
15941};
15942
15943static PyStructSequence_Desc TerminalSize_desc = {
15944 "os.terminal_size",
15945 TerminalSize_docstring,
15946 TerminalSize_fields,
15947 2,
15948};
15949
15950#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
Larry Hastings2f936352014-08-05 14:04:04 +100015951/* AC 3.5: fd should accept None */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010015952PyDoc_STRVAR(termsize__doc__,
15953 "Return the size of the terminal window as (columns, lines).\n" \
15954 "\n" \
15955 "The optional argument fd (default standard output) specifies\n" \
15956 "which file descriptor should be queried.\n" \
15957 "\n" \
15958 "If the file descriptor is not connected to a terminal, an OSError\n" \
15959 "is thrown.\n" \
15960 "\n" \
15961 "This function will only be defined if an implementation is\n" \
15962 "available for this system.\n" \
15963 "\n" \
15964 "shutil.get_terminal_size is the high-level function which should \n" \
15965 "normally be used, os.get_terminal_size is the low-level implementation.");
15966
15967static PyObject*
15968get_terminal_size(PyObject *self, PyObject *args)
15969{
15970 int columns, lines;
15971 PyObject *termsize;
15972
15973 int fd = fileno(stdout);
15974 /* Under some conditions stdout may not be connected and
15975 * fileno(stdout) may point to an invalid file descriptor. For example
15976 * GUI apps don't have valid standard streams by default.
15977 *
15978 * If this happens, and the optional fd argument is not present,
15979 * the ioctl below will fail returning EBADF. This is what we want.
15980 */
15981
15982 if (!PyArg_ParseTuple(args, "|i", &fd))
15983 return NULL;
15984
15985#ifdef TERMSIZE_USE_IOCTL
15986 {
15987 struct winsize w;
15988 if (ioctl(fd, TIOCGWINSZ, &w))
15989 return PyErr_SetFromErrno(PyExc_OSError);
15990 columns = w.ws_col;
15991 lines = w.ws_row;
15992 }
15993#endif /* TERMSIZE_USE_IOCTL */
15994
15995#ifdef TERMSIZE_USE_CONIO
15996 {
15997 DWORD nhandle;
15998 HANDLE handle;
15999 CONSOLE_SCREEN_BUFFER_INFO csbi;
16000 switch (fd) {
16001 case 0: nhandle = STD_INPUT_HANDLE;
16002 break;
16003 case 1: nhandle = STD_OUTPUT_HANDLE;
16004 break;
16005 case 2: nhandle = STD_ERROR_HANDLE;
16006 break;
16007 default:
16008 return PyErr_Format(PyExc_ValueError, "bad file descriptor");
16009 }
16010 handle = GetStdHandle(nhandle);
16011 if (handle == NULL)
16012 return PyErr_Format(PyExc_OSError, "handle cannot be retrieved");
16013 if (handle == INVALID_HANDLE_VALUE)
16014 return PyErr_SetFromWindowsErr(0);
16015
16016 if (!GetConsoleScreenBufferInfo(handle, &csbi))
16017 return PyErr_SetFromWindowsErr(0);
16018
16019 columns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
16020 lines = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
16021 }
16022#endif /* TERMSIZE_USE_CONIO */
16023
16024 termsize = PyStructSequence_New(&TerminalSizeType);
16025 if (termsize == NULL)
16026 return NULL;
16027 PyStructSequence_SET_ITEM(termsize, 0, PyLong_FromLong(columns));
16028 PyStructSequence_SET_ITEM(termsize, 1, PyLong_FromLong(lines));
16029 if (PyErr_Occurred()) {
16030 Py_DECREF(termsize);
16031 return NULL;
16032 }
16033 return termsize;
16034}
16035#endif /* defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL) */
16036
Larry Hastings2f936352014-08-05 14:04:04 +100016037
16038/*[clinic input]
16039os.cpu_count
16040
16041Return the number of CPUs in the system; return None if indeterminable.
16042[clinic start generated code]*/
16043
16044PyDoc_STRVAR(os_cpu_count__doc__,
16045"cpu_count($module, /)\n"
16046"--\n"
16047"\n"
16048"Return the number of CPUs in the system; return None if indeterminable.");
16049
16050#define OS_CPU_COUNT_METHODDEF \
16051 {"cpu_count", (PyCFunction)os_cpu_count, METH_NOARGS, os_cpu_count__doc__},
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016052
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016053static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +100016054os_cpu_count_impl(PyModuleDef *module);
16055
16056static PyObject *
16057os_cpu_count(PyModuleDef *module, PyObject *Py_UNUSED(ignored))
16058{
16059 return os_cpu_count_impl(module);
16060}
16061
16062static PyObject *
16063os_cpu_count_impl(PyModuleDef *module)
16064/*[clinic end generated code: output=92e2a4a729eb7740 input=d55e2f8f3823a628]*/
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016065{
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016066 int ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016067#ifdef MS_WINDOWS
16068 SYSTEM_INFO sysinfo;
16069 GetSystemInfo(&sysinfo);
16070 ncpu = sysinfo.dwNumberOfProcessors;
16071#elif defined(__hpux)
16072 ncpu = mpctl(MPC_GETNUMSPUS, NULL, NULL);
16073#elif defined(HAVE_SYSCONF) && defined(_SC_NPROCESSORS_ONLN)
16074 ncpu = sysconf(_SC_NPROCESSORS_ONLN);
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016075#elif defined(__DragonFly__) || \
16076 defined(__OpenBSD__) || \
16077 defined(__FreeBSD__) || \
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020016078 defined(__NetBSD__) || \
16079 defined(__APPLE__)
Charles-Francois Natali7c4f8da2013-05-20 17:40:32 +020016080 int mib[2];
16081 size_t len = sizeof(ncpu);
16082 mib[0] = CTL_HW;
16083 mib[1] = HW_NCPU;
16084 if (sysctl(mib, 2, &ncpu, &len, NULL, 0) != 0)
16085 ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020016086#endif
16087 if (ncpu >= 1)
16088 return PyLong_FromLong(ncpu);
16089 else
16090 Py_RETURN_NONE;
16091}
16092
Victor Stinnerdaf45552013-08-28 00:53:59 +020016093
Larry Hastings2f936352014-08-05 14:04:04 +100016094/*[clinic input]
16095os.get_inheritable -> bool
16096
16097 fd: int
16098 /
16099
16100Get the close-on-exe flag of the specified file descriptor.
16101[clinic start generated code]*/
16102
16103PyDoc_STRVAR(os_get_inheritable__doc__,
16104"get_inheritable($module, fd, /)\n"
16105"--\n"
16106"\n"
16107"Get the close-on-exe flag of the specified file descriptor.");
16108
16109#define OS_GET_INHERITABLE_METHODDEF \
16110 {"get_inheritable", (PyCFunction)os_get_inheritable, METH_VARARGS, os_get_inheritable__doc__},
16111
16112static int
16113os_get_inheritable_impl(PyModuleDef *module, int fd);
16114
16115static PyObject *
16116os_get_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016117{
Larry Hastings2f936352014-08-05 14:04:04 +100016118 PyObject *return_value = NULL;
16119 int fd;
16120 int _return_value;
16121
16122 if (!PyArg_ParseTuple(args,
16123 "i:get_inheritable",
16124 &fd))
16125 goto exit;
16126 _return_value = os_get_inheritable_impl(module, fd);
16127 if ((_return_value == -1) && PyErr_Occurred())
16128 goto exit;
16129 return_value = PyBool_FromLong((long)_return_value);
16130
16131exit:
16132 return return_value;
16133}
16134
16135static int
16136os_get_inheritable_impl(PyModuleDef *module, int fd)
16137/*[clinic end generated code: output=261d1dd2b0dbdc35 input=89ac008dc9ab6b95]*/
16138{
16139 if (!_PyVerify_fd(fd)){
16140 posix_error();
16141 return -1;
16142 }
16143
16144 return _Py_get_inheritable(fd);
16145}
16146
16147
16148/*[clinic input]
16149os.set_inheritable
16150 fd: int
16151 inheritable: int
16152 /
16153
16154Set the inheritable flag of the specified file descriptor.
16155[clinic start generated code]*/
16156
16157PyDoc_STRVAR(os_set_inheritable__doc__,
16158"set_inheritable($module, fd, inheritable, /)\n"
16159"--\n"
16160"\n"
16161"Set the inheritable flag of the specified file descriptor.");
16162
16163#define OS_SET_INHERITABLE_METHODDEF \
16164 {"set_inheritable", (PyCFunction)os_set_inheritable, METH_VARARGS, os_set_inheritable__doc__},
16165
16166static PyObject *
16167os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable);
16168
16169static PyObject *
16170os_set_inheritable(PyModuleDef *module, PyObject *args)
16171{
16172 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016173 int fd;
16174 int inheritable;
16175
Larry Hastings2f936352014-08-05 14:04:04 +100016176 if (!PyArg_ParseTuple(args,
16177 "ii:set_inheritable",
16178 &fd, &inheritable))
16179 goto exit;
16180 return_value = os_set_inheritable_impl(module, fd, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016181
Larry Hastings2f936352014-08-05 14:04:04 +100016182exit:
16183 return return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016184}
16185
Larry Hastings2f936352014-08-05 14:04:04 +100016186static PyObject *
16187os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable)
16188/*[clinic end generated code: output=64dfe5e15c906539 input=9ceaead87a1e2402]*/
Victor Stinnerdaf45552013-08-28 00:53:59 +020016189{
Victor Stinnerdaf45552013-08-28 00:53:59 +020016190 if (!_PyVerify_fd(fd))
16191 return posix_error();
16192
16193 if (_Py_set_inheritable(fd, inheritable, NULL) < 0)
16194 return NULL;
16195 Py_RETURN_NONE;
16196}
16197
16198
16199#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100016200/*[clinic input]
16201os.get_handle_inheritable -> bool
16202 handle: Py_intptr_t
16203 /
Victor Stinnerdaf45552013-08-28 00:53:59 +020016204
Larry Hastings2f936352014-08-05 14:04:04 +100016205Get the close-on-exe flag of the specified file descriptor.
16206[clinic start generated code]*/
16207
16208PyDoc_STRVAR(os_get_handle_inheritable__doc__,
16209"get_handle_inheritable($module, handle, /)\n"
16210"--\n"
16211"\n"
16212"Get the close-on-exe flag of the specified file descriptor.");
16213
16214#define OS_GET_HANDLE_INHERITABLE_METHODDEF \
16215 {"get_handle_inheritable", (PyCFunction)os_get_handle_inheritable, METH_VARARGS, os_get_handle_inheritable__doc__},
16216
16217static int
16218os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle);
16219
16220static PyObject *
16221os_get_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016222{
Larry Hastings2f936352014-08-05 14:04:04 +100016223 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016224 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016225 int _return_value;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016226
Larry Hastings2f936352014-08-05 14:04:04 +100016227 if (!PyArg_ParseTuple(args,
16228 "" _Py_PARSE_INTPTR ":get_handle_inheritable",
16229 &handle))
16230 goto exit;
16231 _return_value = os_get_handle_inheritable_impl(module, handle);
16232 if ((_return_value == -1) && PyErr_Occurred())
16233 goto exit;
16234 return_value = PyBool_FromLong((long)_return_value);
16235
16236exit:
16237 return return_value;
16238}
16239
16240static int
16241os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle)
16242/*[clinic end generated code: output=d5bf9d86900bf457 input=5f7759443aae3dc5]*/
16243{
16244 DWORD flags;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016245
16246 if (!GetHandleInformation((HANDLE)handle, &flags)) {
16247 PyErr_SetFromWindowsErr(0);
Larry Hastings2f936352014-08-05 14:04:04 +100016248 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016249 }
16250
Larry Hastings2f936352014-08-05 14:04:04 +100016251 return flags & HANDLE_FLAG_INHERIT;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016252}
16253
Victor Stinnerdaf45552013-08-28 00:53:59 +020016254
Larry Hastings2f936352014-08-05 14:04:04 +100016255/*[clinic input]
16256os.set_handle_inheritable
16257 handle: Py_intptr_t
16258 inheritable: bool
16259 /
16260
16261Set the inheritable flag of the specified handle.
16262[clinic start generated code]*/
16263
16264PyDoc_STRVAR(os_set_handle_inheritable__doc__,
16265"set_handle_inheritable($module, handle, inheritable, /)\n"
16266"--\n"
16267"\n"
16268"Set the inheritable flag of the specified handle.");
16269
16270#define OS_SET_HANDLE_INHERITABLE_METHODDEF \
16271 {"set_handle_inheritable", (PyCFunction)os_set_handle_inheritable, METH_VARARGS, os_set_handle_inheritable__doc__},
16272
16273static PyObject *
16274os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable);
16275
16276static PyObject *
16277os_set_handle_inheritable(PyModuleDef *module, PyObject *args)
Victor Stinnerdaf45552013-08-28 00:53:59 +020016278{
Larry Hastings2f936352014-08-05 14:04:04 +100016279 PyObject *return_value = NULL;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016280 Py_intptr_t handle;
Larry Hastings2f936352014-08-05 14:04:04 +100016281 int inheritable;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016282
Larry Hastings2f936352014-08-05 14:04:04 +100016283 if (!PyArg_ParseTuple(args,
16284 "" _Py_PARSE_INTPTR "p:set_handle_inheritable",
16285 &handle, &inheritable))
16286 goto exit;
16287 return_value = os_set_handle_inheritable_impl(module, handle, inheritable);
Victor Stinnerdaf45552013-08-28 00:53:59 +020016288
Larry Hastings2f936352014-08-05 14:04:04 +100016289exit:
16290 return return_value;
16291}
16292
16293static PyObject *
16294os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle, int inheritable)
16295/*[clinic end generated code: output=ee5fcc6d9f0d4f8b input=e64b2b2730469def]*/
16296{
16297 DWORD flags = inheritable ? HANDLE_FLAG_INHERIT : 0;
Victor Stinnerdaf45552013-08-28 00:53:59 +020016298 if (!SetHandleInformation((HANDLE)handle, HANDLE_FLAG_INHERIT, flags)) {
16299 PyErr_SetFromWindowsErr(0);
16300 return NULL;
16301 }
16302 Py_RETURN_NONE;
16303}
Larry Hastings2f936352014-08-05 14:04:04 +100016304#endif /* MS_WINDOWS */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010016305
Victor Stinner1db9e7b2014-07-29 22:32:47 +020016306#ifndef MS_WINDOWS
16307PyDoc_STRVAR(get_blocking__doc__,
16308 "get_blocking(fd) -> bool\n" \
16309 "\n" \
16310 "Get the blocking mode of the file descriptor:\n" \
16311 "False if the O_NONBLOCK flag is set, True if the flag is cleared.");
16312
16313static PyObject*
16314posix_get_blocking(PyObject *self, PyObject *args)
16315{
16316 int fd;
16317 int blocking;
16318
16319 if (!PyArg_ParseTuple(args, "i:get_blocking", &fd))
16320 return NULL;
16321
16322 if (!_PyVerify_fd(fd))
16323 return posix_error();
16324
16325 blocking = _Py_get_blocking(fd);
16326 if (blocking < 0)
16327 return NULL;
16328 return PyBool_FromLong(blocking);
16329}
16330
16331PyDoc_STRVAR(set_blocking__doc__,
16332 "set_blocking(fd, blocking)\n" \
16333 "\n" \
16334 "Set the blocking mode of the specified file descriptor.\n" \
16335 "Set the O_NONBLOCK flag if blocking is False,\n" \
16336 "clear the O_NONBLOCK flag otherwise.");
16337
16338static PyObject*
16339posix_set_blocking(PyObject *self, PyObject *args)
16340{
16341 int fd, blocking;
16342
16343 if (!PyArg_ParseTuple(args, "ii:set_blocking", &fd, &blocking))
16344 return NULL;
16345
16346 if (!_PyVerify_fd(fd))
16347 return posix_error();
16348
16349 if (_Py_set_blocking(fd, blocking) < 0)
16350 return NULL;
16351 Py_RETURN_NONE;
16352}
16353#endif /* !MS_WINDOWS */
16354
16355
Larry Hastings7726ac92014-01-31 22:03:12 -080016356/*[clinic input]
16357dump buffer
16358[clinic start generated code]*/
16359
16360#ifndef OS_TTYNAME_METHODDEF
16361 #define OS_TTYNAME_METHODDEF
16362#endif /* !defined(OS_TTYNAME_METHODDEF) */
Larry Hastings2f936352014-08-05 14:04:04 +100016363
16364#ifndef OS_CTERMID_METHODDEF
16365 #define OS_CTERMID_METHODDEF
16366#endif /* !defined(OS_CTERMID_METHODDEF) */
16367
16368#ifndef OS_FCHDIR_METHODDEF
16369 #define OS_FCHDIR_METHODDEF
16370#endif /* !defined(OS_FCHDIR_METHODDEF) */
16371
16372#ifndef OS_FCHMOD_METHODDEF
16373 #define OS_FCHMOD_METHODDEF
16374#endif /* !defined(OS_FCHMOD_METHODDEF) */
16375
16376#ifndef OS_LCHMOD_METHODDEF
16377 #define OS_LCHMOD_METHODDEF
16378#endif /* !defined(OS_LCHMOD_METHODDEF) */
16379
16380#ifndef OS_CHFLAGS_METHODDEF
16381 #define OS_CHFLAGS_METHODDEF
16382#endif /* !defined(OS_CHFLAGS_METHODDEF) */
16383
16384#ifndef OS_LCHFLAGS_METHODDEF
16385 #define OS_LCHFLAGS_METHODDEF
16386#endif /* !defined(OS_LCHFLAGS_METHODDEF) */
16387
16388#ifndef OS_CHROOT_METHODDEF
16389 #define OS_CHROOT_METHODDEF
16390#endif /* !defined(OS_CHROOT_METHODDEF) */
16391
16392#ifndef OS_FSYNC_METHODDEF
16393 #define OS_FSYNC_METHODDEF
16394#endif /* !defined(OS_FSYNC_METHODDEF) */
16395
16396#ifndef OS_SYNC_METHODDEF
16397 #define OS_SYNC_METHODDEF
16398#endif /* !defined(OS_SYNC_METHODDEF) */
16399
16400#ifndef OS_FDATASYNC_METHODDEF
16401 #define OS_FDATASYNC_METHODDEF
16402#endif /* !defined(OS_FDATASYNC_METHODDEF) */
16403
16404#ifndef OS_CHOWN_METHODDEF
16405 #define OS_CHOWN_METHODDEF
16406#endif /* !defined(OS_CHOWN_METHODDEF) */
16407
16408#ifndef OS_FCHOWN_METHODDEF
16409 #define OS_FCHOWN_METHODDEF
16410#endif /* !defined(OS_FCHOWN_METHODDEF) */
16411
16412#ifndef OS_LCHOWN_METHODDEF
16413 #define OS_LCHOWN_METHODDEF
16414#endif /* !defined(OS_LCHOWN_METHODDEF) */
16415
16416#ifndef OS_LINK_METHODDEF
16417 #define OS_LINK_METHODDEF
16418#endif /* !defined(OS_LINK_METHODDEF) */
16419
16420#ifndef OS__GETFINALPATHNAME_METHODDEF
16421 #define OS__GETFINALPATHNAME_METHODDEF
16422#endif /* !defined(OS__GETFINALPATHNAME_METHODDEF) */
16423
16424#ifndef OS__GETVOLUMEPATHNAME_METHODDEF
16425 #define OS__GETVOLUMEPATHNAME_METHODDEF
16426#endif /* !defined(OS__GETVOLUMEPATHNAME_METHODDEF) */
16427
16428#ifndef OS_NICE_METHODDEF
16429 #define OS_NICE_METHODDEF
16430#endif /* !defined(OS_NICE_METHODDEF) */
16431
16432#ifndef OS_GETPRIORITY_METHODDEF
16433 #define OS_GETPRIORITY_METHODDEF
16434#endif /* !defined(OS_GETPRIORITY_METHODDEF) */
16435
16436#ifndef OS_SETPRIORITY_METHODDEF
16437 #define OS_SETPRIORITY_METHODDEF
16438#endif /* !defined(OS_SETPRIORITY_METHODDEF) */
16439
16440#ifndef OS_SYSTEM_METHODDEF
16441 #define OS_SYSTEM_METHODDEF
16442#endif /* !defined(OS_SYSTEM_METHODDEF) */
16443
16444#ifndef OS_SYSTEM_METHODDEF
16445 #define OS_SYSTEM_METHODDEF
16446#endif /* !defined(OS_SYSTEM_METHODDEF) */
16447
16448#ifndef OS_UNAME_METHODDEF
16449 #define OS_UNAME_METHODDEF
16450#endif /* !defined(OS_UNAME_METHODDEF) */
16451
16452#ifndef OS_EXECV_METHODDEF
16453 #define OS_EXECV_METHODDEF
16454#endif /* !defined(OS_EXECV_METHODDEF) */
16455
16456#ifndef OS_EXECVE_METHODDEF
16457 #define OS_EXECVE_METHODDEF
16458#endif /* !defined(OS_EXECVE_METHODDEF) */
16459
16460#ifndef OS_SPAWNV_METHODDEF
16461 #define OS_SPAWNV_METHODDEF
16462#endif /* !defined(OS_SPAWNV_METHODDEF) */
16463
16464#ifndef OS_SPAWNVE_METHODDEF
16465 #define OS_SPAWNVE_METHODDEF
16466#endif /* !defined(OS_SPAWNVE_METHODDEF) */
16467
16468#ifndef OS_FORK1_METHODDEF
16469 #define OS_FORK1_METHODDEF
16470#endif /* !defined(OS_FORK1_METHODDEF) */
16471
16472#ifndef OS_FORK_METHODDEF
16473 #define OS_FORK_METHODDEF
16474#endif /* !defined(OS_FORK_METHODDEF) */
16475
16476#ifndef OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16477 #define OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16478#endif /* !defined(OS_SCHED_GET_PRIORITY_MAX_METHODDEF) */
16479
16480#ifndef OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16481 #define OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16482#endif /* !defined(OS_SCHED_GET_PRIORITY_MIN_METHODDEF) */
16483
16484#ifndef OS_SCHED_GETSCHEDULER_METHODDEF
16485 #define OS_SCHED_GETSCHEDULER_METHODDEF
16486#endif /* !defined(OS_SCHED_GETSCHEDULER_METHODDEF) */
16487
16488#ifndef OS_SCHED_SETSCHEDULER_METHODDEF
16489 #define OS_SCHED_SETSCHEDULER_METHODDEF
16490#endif /* !defined(OS_SCHED_SETSCHEDULER_METHODDEF) */
16491
16492#ifndef OS_SCHED_GETPARAM_METHODDEF
16493 #define OS_SCHED_GETPARAM_METHODDEF
16494#endif /* !defined(OS_SCHED_GETPARAM_METHODDEF) */
16495
16496#ifndef OS_SCHED_SETPARAM_METHODDEF
16497 #define OS_SCHED_SETPARAM_METHODDEF
16498#endif /* !defined(OS_SCHED_SETPARAM_METHODDEF) */
16499
16500#ifndef OS_SCHED_RR_GET_INTERVAL_METHODDEF
16501 #define OS_SCHED_RR_GET_INTERVAL_METHODDEF
16502#endif /* !defined(OS_SCHED_RR_GET_INTERVAL_METHODDEF) */
16503
16504#ifndef OS_SCHED_YIELD_METHODDEF
16505 #define OS_SCHED_YIELD_METHODDEF
16506#endif /* !defined(OS_SCHED_YIELD_METHODDEF) */
16507
16508#ifndef OS_SCHED_SETAFFINITY_METHODDEF
16509 #define OS_SCHED_SETAFFINITY_METHODDEF
16510#endif /* !defined(OS_SCHED_SETAFFINITY_METHODDEF) */
16511
16512#ifndef OS_SCHED_GETAFFINITY_METHODDEF
16513 #define OS_SCHED_GETAFFINITY_METHODDEF
16514#endif /* !defined(OS_SCHED_GETAFFINITY_METHODDEF) */
16515
16516#ifndef OS_OPENPTY_METHODDEF
16517 #define OS_OPENPTY_METHODDEF
16518#endif /* !defined(OS_OPENPTY_METHODDEF) */
16519
16520#ifndef OS_FORKPTY_METHODDEF
16521 #define OS_FORKPTY_METHODDEF
16522#endif /* !defined(OS_FORKPTY_METHODDEF) */
16523
16524#ifndef OS_GETEGID_METHODDEF
16525 #define OS_GETEGID_METHODDEF
16526#endif /* !defined(OS_GETEGID_METHODDEF) */
16527
16528#ifndef OS_GETEUID_METHODDEF
16529 #define OS_GETEUID_METHODDEF
16530#endif /* !defined(OS_GETEUID_METHODDEF) */
16531
16532#ifndef OS_GETGID_METHODDEF
16533 #define OS_GETGID_METHODDEF
16534#endif /* !defined(OS_GETGID_METHODDEF) */
16535
16536#ifndef OS_GETGROUPS_METHODDEF
16537 #define OS_GETGROUPS_METHODDEF
16538#endif /* !defined(OS_GETGROUPS_METHODDEF) */
16539
16540#ifndef OS_GETPGID_METHODDEF
16541 #define OS_GETPGID_METHODDEF
16542#endif /* !defined(OS_GETPGID_METHODDEF) */
16543
16544#ifndef OS_GETPGRP_METHODDEF
16545 #define OS_GETPGRP_METHODDEF
16546#endif /* !defined(OS_GETPGRP_METHODDEF) */
16547
16548#ifndef OS_SETPGRP_METHODDEF
16549 #define OS_SETPGRP_METHODDEF
16550#endif /* !defined(OS_SETPGRP_METHODDEF) */
16551
16552#ifndef OS_GETPPID_METHODDEF
16553 #define OS_GETPPID_METHODDEF
16554#endif /* !defined(OS_GETPPID_METHODDEF) */
16555
16556#ifndef OS_GETLOGIN_METHODDEF
16557 #define OS_GETLOGIN_METHODDEF
16558#endif /* !defined(OS_GETLOGIN_METHODDEF) */
16559
16560#ifndef OS_GETUID_METHODDEF
16561 #define OS_GETUID_METHODDEF
16562#endif /* !defined(OS_GETUID_METHODDEF) */
16563
16564#ifndef OS_KILL_METHODDEF
16565 #define OS_KILL_METHODDEF
16566#endif /* !defined(OS_KILL_METHODDEF) */
16567
16568#ifndef OS_KILLPG_METHODDEF
16569 #define OS_KILLPG_METHODDEF
16570#endif /* !defined(OS_KILLPG_METHODDEF) */
16571
16572#ifndef OS_PLOCK_METHODDEF
16573 #define OS_PLOCK_METHODDEF
16574#endif /* !defined(OS_PLOCK_METHODDEF) */
16575
16576#ifndef OS_SETUID_METHODDEF
16577 #define OS_SETUID_METHODDEF
16578#endif /* !defined(OS_SETUID_METHODDEF) */
16579
16580#ifndef OS_SETEUID_METHODDEF
16581 #define OS_SETEUID_METHODDEF
16582#endif /* !defined(OS_SETEUID_METHODDEF) */
16583
16584#ifndef OS_SETEGID_METHODDEF
16585 #define OS_SETEGID_METHODDEF
16586#endif /* !defined(OS_SETEGID_METHODDEF) */
16587
16588#ifndef OS_SETREUID_METHODDEF
16589 #define OS_SETREUID_METHODDEF
16590#endif /* !defined(OS_SETREUID_METHODDEF) */
16591
16592#ifndef OS_SETREGID_METHODDEF
16593 #define OS_SETREGID_METHODDEF
16594#endif /* !defined(OS_SETREGID_METHODDEF) */
16595
16596#ifndef OS_SETGID_METHODDEF
16597 #define OS_SETGID_METHODDEF
16598#endif /* !defined(OS_SETGID_METHODDEF) */
16599
16600#ifndef OS_SETGROUPS_METHODDEF
16601 #define OS_SETGROUPS_METHODDEF
16602#endif /* !defined(OS_SETGROUPS_METHODDEF) */
16603
16604#ifndef OS_WAIT3_METHODDEF
16605 #define OS_WAIT3_METHODDEF
16606#endif /* !defined(OS_WAIT3_METHODDEF) */
16607
16608#ifndef OS_WAIT4_METHODDEF
16609 #define OS_WAIT4_METHODDEF
16610#endif /* !defined(OS_WAIT4_METHODDEF) */
16611
16612#ifndef OS_WAITID_METHODDEF
16613 #define OS_WAITID_METHODDEF
16614#endif /* !defined(OS_WAITID_METHODDEF) */
16615
16616#ifndef OS_WAITPID_METHODDEF
16617 #define OS_WAITPID_METHODDEF
16618#endif /* !defined(OS_WAITPID_METHODDEF) */
16619
16620#ifndef OS_WAITPID_METHODDEF
16621 #define OS_WAITPID_METHODDEF
16622#endif /* !defined(OS_WAITPID_METHODDEF) */
16623
16624#ifndef OS_WAIT_METHODDEF
16625 #define OS_WAIT_METHODDEF
16626#endif /* !defined(OS_WAIT_METHODDEF) */
16627
16628#ifndef OS_SYMLINK_METHODDEF
16629 #define OS_SYMLINK_METHODDEF
16630#endif /* !defined(OS_SYMLINK_METHODDEF) */
16631
16632#ifndef OS_TIMES_METHODDEF
16633 #define OS_TIMES_METHODDEF
16634#endif /* !defined(OS_TIMES_METHODDEF) */
16635
16636#ifndef OS_GETSID_METHODDEF
16637 #define OS_GETSID_METHODDEF
16638#endif /* !defined(OS_GETSID_METHODDEF) */
16639
16640#ifndef OS_SETSID_METHODDEF
16641 #define OS_SETSID_METHODDEF
16642#endif /* !defined(OS_SETSID_METHODDEF) */
16643
16644#ifndef OS_SETPGID_METHODDEF
16645 #define OS_SETPGID_METHODDEF
16646#endif /* !defined(OS_SETPGID_METHODDEF) */
16647
16648#ifndef OS_TCGETPGRP_METHODDEF
16649 #define OS_TCGETPGRP_METHODDEF
16650#endif /* !defined(OS_TCGETPGRP_METHODDEF) */
16651
16652#ifndef OS_TCSETPGRP_METHODDEF
16653 #define OS_TCSETPGRP_METHODDEF
16654#endif /* !defined(OS_TCSETPGRP_METHODDEF) */
16655
16656#ifndef OS_LOCKF_METHODDEF
16657 #define OS_LOCKF_METHODDEF
16658#endif /* !defined(OS_LOCKF_METHODDEF) */
16659
16660#ifndef OS_READV_METHODDEF
16661 #define OS_READV_METHODDEF
16662#endif /* !defined(OS_READV_METHODDEF) */
16663
16664#ifndef OS_PREAD_METHODDEF
16665 #define OS_PREAD_METHODDEF
16666#endif /* !defined(OS_PREAD_METHODDEF) */
16667
16668#ifndef OS_PIPE_METHODDEF
16669 #define OS_PIPE_METHODDEF
16670#endif /* !defined(OS_PIPE_METHODDEF) */
16671
16672#ifndef OS_PIPE2_METHODDEF
16673 #define OS_PIPE2_METHODDEF
16674#endif /* !defined(OS_PIPE2_METHODDEF) */
16675
16676#ifndef OS_WRITEV_METHODDEF
16677 #define OS_WRITEV_METHODDEF
16678#endif /* !defined(OS_WRITEV_METHODDEF) */
16679
16680#ifndef OS_PWRITE_METHODDEF
16681 #define OS_PWRITE_METHODDEF
16682#endif /* !defined(OS_PWRITE_METHODDEF) */
16683
16684#ifndef OS_MKFIFO_METHODDEF
16685 #define OS_MKFIFO_METHODDEF
16686#endif /* !defined(OS_MKFIFO_METHODDEF) */
16687
16688#ifndef OS_MKNOD_METHODDEF
16689 #define OS_MKNOD_METHODDEF
16690#endif /* !defined(OS_MKNOD_METHODDEF) */
16691
16692#ifndef OS_MAJOR_METHODDEF
16693 #define OS_MAJOR_METHODDEF
16694#endif /* !defined(OS_MAJOR_METHODDEF) */
16695
16696#ifndef OS_MINOR_METHODDEF
16697 #define OS_MINOR_METHODDEF
16698#endif /* !defined(OS_MINOR_METHODDEF) */
16699
16700#ifndef OS_MAKEDEV_METHODDEF
16701 #define OS_MAKEDEV_METHODDEF
16702#endif /* !defined(OS_MAKEDEV_METHODDEF) */
16703
16704#ifndef OS_FTRUNCATE_METHODDEF
16705 #define OS_FTRUNCATE_METHODDEF
16706#endif /* !defined(OS_FTRUNCATE_METHODDEF) */
16707
16708#ifndef OS_TRUNCATE_METHODDEF
16709 #define OS_TRUNCATE_METHODDEF
16710#endif /* !defined(OS_TRUNCATE_METHODDEF) */
16711
16712#ifndef OS_POSIX_FALLOCATE_METHODDEF
16713 #define OS_POSIX_FALLOCATE_METHODDEF
16714#endif /* !defined(OS_POSIX_FALLOCATE_METHODDEF) */
16715
16716#ifndef OS_POSIX_FADVISE_METHODDEF
16717 #define OS_POSIX_FADVISE_METHODDEF
16718#endif /* !defined(OS_POSIX_FADVISE_METHODDEF) */
16719
16720#ifndef OS_PUTENV_METHODDEF
16721 #define OS_PUTENV_METHODDEF
16722#endif /* !defined(OS_PUTENV_METHODDEF) */
16723
16724#ifndef OS_PUTENV_METHODDEF
16725 #define OS_PUTENV_METHODDEF
16726#endif /* !defined(OS_PUTENV_METHODDEF) */
16727
16728#ifndef OS_UNSETENV_METHODDEF
16729 #define OS_UNSETENV_METHODDEF
16730#endif /* !defined(OS_UNSETENV_METHODDEF) */
16731
16732#ifndef OS_WCOREDUMP_METHODDEF
16733 #define OS_WCOREDUMP_METHODDEF
16734#endif /* !defined(OS_WCOREDUMP_METHODDEF) */
16735
16736#ifndef OS_WIFCONTINUED_METHODDEF
16737 #define OS_WIFCONTINUED_METHODDEF
16738#endif /* !defined(OS_WIFCONTINUED_METHODDEF) */
16739
16740#ifndef OS_WIFSTOPPED_METHODDEF
16741 #define OS_WIFSTOPPED_METHODDEF
16742#endif /* !defined(OS_WIFSTOPPED_METHODDEF) */
16743
16744#ifndef OS_WIFSIGNALED_METHODDEF
16745 #define OS_WIFSIGNALED_METHODDEF
16746#endif /* !defined(OS_WIFSIGNALED_METHODDEF) */
16747
16748#ifndef OS_WIFEXITED_METHODDEF
16749 #define OS_WIFEXITED_METHODDEF
16750#endif /* !defined(OS_WIFEXITED_METHODDEF) */
16751
16752#ifndef OS_WEXITSTATUS_METHODDEF
16753 #define OS_WEXITSTATUS_METHODDEF
16754#endif /* !defined(OS_WEXITSTATUS_METHODDEF) */
16755
16756#ifndef OS_WTERMSIG_METHODDEF
16757 #define OS_WTERMSIG_METHODDEF
16758#endif /* !defined(OS_WTERMSIG_METHODDEF) */
16759
16760#ifndef OS_WSTOPSIG_METHODDEF
16761 #define OS_WSTOPSIG_METHODDEF
16762#endif /* !defined(OS_WSTOPSIG_METHODDEF) */
16763
16764#ifndef OS_FSTATVFS_METHODDEF
16765 #define OS_FSTATVFS_METHODDEF
16766#endif /* !defined(OS_FSTATVFS_METHODDEF) */
16767
16768#ifndef OS_STATVFS_METHODDEF
16769 #define OS_STATVFS_METHODDEF
16770#endif /* !defined(OS_STATVFS_METHODDEF) */
16771
16772#ifndef OS__GETDISKUSAGE_METHODDEF
16773 #define OS__GETDISKUSAGE_METHODDEF
16774#endif /* !defined(OS__GETDISKUSAGE_METHODDEF) */
16775
16776#ifndef OS_FPATHCONF_METHODDEF
16777 #define OS_FPATHCONF_METHODDEF
16778#endif /* !defined(OS_FPATHCONF_METHODDEF) */
16779
16780#ifndef OS_PATHCONF_METHODDEF
16781 #define OS_PATHCONF_METHODDEF
16782#endif /* !defined(OS_PATHCONF_METHODDEF) */
16783
16784#ifndef OS_CONFSTR_METHODDEF
16785 #define OS_CONFSTR_METHODDEF
16786#endif /* !defined(OS_CONFSTR_METHODDEF) */
16787
16788#ifndef OS_SYSCONF_METHODDEF
16789 #define OS_SYSCONF_METHODDEF
16790#endif /* !defined(OS_SYSCONF_METHODDEF) */
16791
16792#ifndef OS_GETLOADAVG_METHODDEF
16793 #define OS_GETLOADAVG_METHODDEF
16794#endif /* !defined(OS_GETLOADAVG_METHODDEF) */
16795
16796#ifndef OS_SETRESUID_METHODDEF
16797 #define OS_SETRESUID_METHODDEF
16798#endif /* !defined(OS_SETRESUID_METHODDEF) */
16799
16800#ifndef OS_SETRESGID_METHODDEF
16801 #define OS_SETRESGID_METHODDEF
16802#endif /* !defined(OS_SETRESGID_METHODDEF) */
16803
16804#ifndef OS_GETRESUID_METHODDEF
16805 #define OS_GETRESUID_METHODDEF
16806#endif /* !defined(OS_GETRESUID_METHODDEF) */
16807
16808#ifndef OS_GETRESGID_METHODDEF
16809 #define OS_GETRESGID_METHODDEF
16810#endif /* !defined(OS_GETRESGID_METHODDEF) */
16811
16812#ifndef OS_GETXATTR_METHODDEF
16813 #define OS_GETXATTR_METHODDEF
16814#endif /* !defined(OS_GETXATTR_METHODDEF) */
16815
16816#ifndef OS_SETXATTR_METHODDEF
16817 #define OS_SETXATTR_METHODDEF
16818#endif /* !defined(OS_SETXATTR_METHODDEF) */
16819
16820#ifndef OS_REMOVEXATTR_METHODDEF
16821 #define OS_REMOVEXATTR_METHODDEF
16822#endif /* !defined(OS_REMOVEXATTR_METHODDEF) */
16823
16824#ifndef OS_LISTXATTR_METHODDEF
16825 #define OS_LISTXATTR_METHODDEF
16826#endif /* !defined(OS_LISTXATTR_METHODDEF) */
16827
16828#ifndef OS_GET_HANDLE_INHERITABLE_METHODDEF
16829 #define OS_GET_HANDLE_INHERITABLE_METHODDEF
16830#endif /* !defined(OS_GET_HANDLE_INHERITABLE_METHODDEF) */
16831
16832#ifndef OS_SET_HANDLE_INHERITABLE_METHODDEF
16833 #define OS_SET_HANDLE_INHERITABLE_METHODDEF
16834#endif /* !defined(OS_SET_HANDLE_INHERITABLE_METHODDEF) */
16835/*[clinic end generated code: output=52a6140b0b052ce6 input=524ce2e021e4eba6]*/
Larry Hastings7726ac92014-01-31 22:03:12 -080016836
Larry Hastings31826802013-10-19 00:09:25 -070016837
Fred Drake5ab8eaf1999-12-09 21:13:07 +000016838static PyMethodDef posix_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -070016839
16840 OS_STAT_METHODDEF
16841 OS_ACCESS_METHODDEF
16842 OS_TTYNAME_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100016843 OS_CHDIR_METHODDEF
16844 OS_CHFLAGS_METHODDEF
16845 OS_CHMOD_METHODDEF
16846 OS_FCHMOD_METHODDEF
16847 OS_LCHMOD_METHODDEF
16848 OS_CHOWN_METHODDEF
16849 OS_FCHOWN_METHODDEF
16850 OS_LCHOWN_METHODDEF
16851 OS_LCHFLAGS_METHODDEF
16852 OS_CHROOT_METHODDEF
16853 OS_CTERMID_METHODDEF
16854 OS_GETCWD_METHODDEF
16855 OS_GETCWDB_METHODDEF
16856 OS_LINK_METHODDEF
16857 OS_LISTDIR_METHODDEF
16858 OS_LSTAT_METHODDEF
16859 OS_MKDIR_METHODDEF
16860 OS_NICE_METHODDEF
16861 OS_GETPRIORITY_METHODDEF
16862 OS_SETPRIORITY_METHODDEF
Guido van Rossumb6775db1994-08-01 11:34:53 +000016863#ifdef HAVE_READLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070016864 {"readlink", (PyCFunction)posix_readlink,
16865 METH_VARARGS | METH_KEYWORDS,
16866 readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000016867#endif /* HAVE_READLINK */
Brian Curtind40e6f72010-07-08 21:39:08 +000016868#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
Larry Hastings9cf065c2012-06-22 16:30:09 -070016869 {"readlink", (PyCFunction)win_readlink,
16870 METH_VARARGS | METH_KEYWORDS,
16871 readlink__doc__},
Brian Curtind40e6f72010-07-08 21:39:08 +000016872#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
Larry Hastings2f936352014-08-05 14:04:04 +100016873 OS_RENAME_METHODDEF
16874 OS_REPLACE_METHODDEF
16875 OS_RMDIR_METHODDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000016876 {"stat_float_times", stat_float_times, METH_VARARGS, stat_float_times__doc__},
Larry Hastings2f936352014-08-05 14:04:04 +100016877 OS_SYMLINK_METHODDEF
16878 OS_SYSTEM_METHODDEF
16879 OS_UMASK_METHODDEF
16880 OS_UNAME_METHODDEF
16881 OS_UNLINK_METHODDEF
16882 OS_REMOVE_METHODDEF
16883 OS_UTIME_METHODDEF
16884 OS_TIMES_METHODDEF
16885 OS__EXIT_METHODDEF
16886 OS_EXECV_METHODDEF
16887 OS_EXECVE_METHODDEF
16888 OS_SPAWNV_METHODDEF
16889 OS_SPAWNVE_METHODDEF
16890 OS_FORK1_METHODDEF
16891 OS_FORK_METHODDEF
16892 OS_SCHED_GET_PRIORITY_MAX_METHODDEF
16893 OS_SCHED_GET_PRIORITY_MIN_METHODDEF
16894 OS_SCHED_GETPARAM_METHODDEF
16895 OS_SCHED_GETSCHEDULER_METHODDEF
16896 OS_SCHED_RR_GET_INTERVAL_METHODDEF
16897 OS_SCHED_SETPARAM_METHODDEF
16898 OS_SCHED_SETSCHEDULER_METHODDEF
16899 OS_SCHED_YIELD_METHODDEF
16900 OS_SCHED_SETAFFINITY_METHODDEF
16901 OS_SCHED_GETAFFINITY_METHODDEF
16902 OS_OPENPTY_METHODDEF
16903 OS_FORKPTY_METHODDEF
16904 OS_GETEGID_METHODDEF
16905 OS_GETEUID_METHODDEF
16906 OS_GETGID_METHODDEF
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +020016907#ifdef HAVE_GETGROUPLIST
16908 {"getgrouplist", posix_getgrouplist, METH_VARARGS, posix_getgrouplist__doc__},
16909#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016910 OS_GETGROUPS_METHODDEF
16911 OS_GETPID_METHODDEF
16912 OS_GETPGRP_METHODDEF
16913 OS_GETPPID_METHODDEF
16914 OS_GETUID_METHODDEF
16915 OS_GETLOGIN_METHODDEF
16916 OS_KILL_METHODDEF
16917 OS_KILLPG_METHODDEF
16918 OS_PLOCK_METHODDEF
Thomas Heller8b7a9572007-08-31 06:44:36 +000016919#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000016920 {"startfile", win32_startfile, METH_VARARGS, win32_startfile__doc__},
Thomas Heller8b7a9572007-08-31 06:44:36 +000016921#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016922 OS_SETUID_METHODDEF
16923 OS_SETEUID_METHODDEF
16924 OS_SETREUID_METHODDEF
16925 OS_SETGID_METHODDEF
16926 OS_SETEGID_METHODDEF
16927 OS_SETREGID_METHODDEF
16928 OS_SETGROUPS_METHODDEF
Antoine Pitroub7572f02009-12-02 20:46:48 +000016929#ifdef HAVE_INITGROUPS
Victor Stinner8c62be82010-05-06 00:08:46 +000016930 {"initgroups", posix_initgroups, METH_VARARGS, posix_initgroups__doc__},
Antoine Pitroub7572f02009-12-02 20:46:48 +000016931#endif /* HAVE_INITGROUPS */
Larry Hastings2f936352014-08-05 14:04:04 +100016932 OS_GETPGID_METHODDEF
16933 OS_SETPGRP_METHODDEF
16934 OS_WAIT_METHODDEF
16935 OS_WAIT3_METHODDEF
16936 OS_WAIT4_METHODDEF
16937 OS_WAITID_METHODDEF
16938 OS_WAITPID_METHODDEF
16939 OS_GETSID_METHODDEF
16940 OS_SETSID_METHODDEF
16941 OS_SETPGID_METHODDEF
16942 OS_TCGETPGRP_METHODDEF
16943 OS_TCSETPGRP_METHODDEF
16944 OS_OPEN_METHODDEF
16945 OS_CLOSE_METHODDEF
16946 OS_CLOSERANGE_METHODDEF
16947 OS_DEVICE_ENCODING_METHODDEF
16948 OS_DUP_METHODDEF
16949 OS_DUP2_METHODDEF
16950 OS_LOCKF_METHODDEF
16951 OS_LSEEK_METHODDEF
16952 OS_READ_METHODDEF
16953 OS_READV_METHODDEF
16954 OS_PREAD_METHODDEF
16955 OS_WRITE_METHODDEF
16956 OS_WRITEV_METHODDEF
16957 OS_PWRITE_METHODDEF
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000016958#ifdef HAVE_SENDFILE
16959 {"sendfile", (PyCFunction)posix_sendfile, METH_VARARGS | METH_KEYWORDS,
16960 posix_sendfile__doc__},
16961#endif
Larry Hastings2f936352014-08-05 14:04:04 +100016962 OS_FSTAT_METHODDEF
16963 OS_ISATTY_METHODDEF
16964 OS_PIPE_METHODDEF
16965 OS_PIPE2_METHODDEF
16966 OS_MKFIFO_METHODDEF
16967 OS_MKNOD_METHODDEF
16968 OS_MAJOR_METHODDEF
16969 OS_MINOR_METHODDEF
16970 OS_MAKEDEV_METHODDEF
16971 OS_FTRUNCATE_METHODDEF
16972 OS_TRUNCATE_METHODDEF
16973 OS_POSIX_FALLOCATE_METHODDEF
16974 OS_POSIX_FADVISE_METHODDEF
16975 OS_PUTENV_METHODDEF
16976 OS_UNSETENV_METHODDEF
16977 OS_STRERROR_METHODDEF
16978 OS_FCHDIR_METHODDEF
16979 OS_FSYNC_METHODDEF
16980 OS_SYNC_METHODDEF
16981 OS_FDATASYNC_METHODDEF
16982 OS_WCOREDUMP_METHODDEF
16983 OS_WIFCONTINUED_METHODDEF
16984 OS_WIFSTOPPED_METHODDEF
16985 OS_WIFSIGNALED_METHODDEF
16986 OS_WIFEXITED_METHODDEF
16987 OS_WEXITSTATUS_METHODDEF
16988 OS_WTERMSIG_METHODDEF
16989 OS_WSTOPSIG_METHODDEF
16990 OS_FSTATVFS_METHODDEF
16991 OS_STATVFS_METHODDEF
16992 OS_CONFSTR_METHODDEF
16993 OS_SYSCONF_METHODDEF
16994 OS_FPATHCONF_METHODDEF
16995 OS_PATHCONF_METHODDEF
16996 OS_ABORT_METHODDEF
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000016997#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000016998 {"_getfullpathname", posix__getfullpathname, METH_VARARGS, NULL},
Brian Curtin95d028f2011-06-09 09:10:38 -050016999 {"_isdir", posix__isdir, METH_VARARGS, posix__isdir__doc__},
Mark Hammondef8b6542001-05-13 08:04:26 +000017000#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017001 OS__GETDISKUSAGE_METHODDEF
17002 OS__GETFINALPATHNAME_METHODDEF
17003 OS__GETVOLUMEPATHNAME_METHODDEF
17004 OS_GETLOADAVG_METHODDEF
17005 OS_URANDOM_METHODDEF
17006 OS_SETRESUID_METHODDEF
17007 OS_SETRESGID_METHODDEF
17008 OS_GETRESUID_METHODDEF
17009 OS_GETRESGID_METHODDEF
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000017010
Larry Hastings2f936352014-08-05 14:04:04 +100017011 OS_GETXATTR_METHODDEF
17012 OS_SETXATTR_METHODDEF
17013 OS_REMOVEXATTR_METHODDEF
17014 OS_LISTXATTR_METHODDEF
17015
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017016#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
17017 {"get_terminal_size", get_terminal_size, METH_VARARGS, termsize__doc__},
17018#endif
Larry Hastings2f936352014-08-05 14:04:04 +100017019 OS_CPU_COUNT_METHODDEF
17020 OS_GET_INHERITABLE_METHODDEF
17021 OS_SET_INHERITABLE_METHODDEF
17022 OS_GET_HANDLE_INHERITABLE_METHODDEF
17023 OS_SET_HANDLE_INHERITABLE_METHODDEF
Victor Stinner1db9e7b2014-07-29 22:32:47 +020017024#ifndef MS_WINDOWS
17025 {"get_blocking", posix_get_blocking, METH_VARARGS, get_blocking__doc__},
17026 {"set_blocking", posix_set_blocking, METH_VARARGS, set_blocking__doc__},
17027#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017028 {NULL, NULL} /* Sentinel */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000017029};
17030
17031
Brian Curtin52173d42010-12-02 18:29:18 +000017032#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017033static int
Brian Curtin52173d42010-12-02 18:29:18 +000017034enable_symlink()
17035{
17036 HANDLE tok;
17037 TOKEN_PRIVILEGES tok_priv;
17038 LUID luid;
17039 int meth_idx = 0;
17040
17041 if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &tok))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017042 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017043
17044 if (!LookupPrivilegeValue(NULL, SE_CREATE_SYMBOLIC_LINK_NAME, &luid))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017045 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017046
17047 tok_priv.PrivilegeCount = 1;
17048 tok_priv.Privileges[0].Luid = luid;
17049 tok_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
17050
17051 if (!AdjustTokenPrivileges(tok, FALSE, &tok_priv,
17052 sizeof(TOKEN_PRIVILEGES),
17053 (PTOKEN_PRIVILEGES) NULL, (PDWORD) NULL))
Brian Curtin3b4499c2010-12-28 14:31:47 +000017054 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000017055
Brian Curtin3b4499c2010-12-28 14:31:47 +000017056 /* ERROR_NOT_ALL_ASSIGNED returned when the privilege can't be assigned. */
17057 return GetLastError() == ERROR_NOT_ALL_ASSIGNED ? 0 : 1;
Brian Curtin52173d42010-12-02 18:29:18 +000017058}
17059#endif /* defined(HAVE_SYMLINK) && defined(MS_WINDOWS) */
17060
Barry Warsaw4a342091996-12-19 23:50:02 +000017061static int
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017062all_ins(PyObject *m)
Barry Warsaw4a342091996-12-19 23:50:02 +000017063{
Guido van Rossum94f6f721999-01-06 18:42:14 +000017064#ifdef F_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017065 if (PyModule_AddIntMacro(m, F_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017066#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017067#ifdef R_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017068 if (PyModule_AddIntMacro(m, R_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017069#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017070#ifdef W_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017071 if (PyModule_AddIntMacro(m, W_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017072#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000017073#ifdef X_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017074 if (PyModule_AddIntMacro(m, X_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017075#endif
Fred Drakec9680921999-12-13 16:37:25 +000017076#ifdef NGROUPS_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017077 if (PyModule_AddIntMacro(m, NGROUPS_MAX)) return -1;
Fred Drakec9680921999-12-13 16:37:25 +000017078#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017079#ifdef TMP_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017080 if (PyModule_AddIntMacro(m, TMP_MAX)) return -1;
Fred Drake5ab8eaf1999-12-09 21:13:07 +000017081#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017082#ifdef WCONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017083 if (PyModule_AddIntMacro(m, WCONTINUED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017084#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017085#ifdef WNOHANG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017086 if (PyModule_AddIntMacro(m, WNOHANG)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017087#endif
Fred Drake106c1a02002-04-23 15:58:02 +000017088#ifdef WUNTRACED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017089 if (PyModule_AddIntMacro(m, WUNTRACED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000017090#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000017091#ifdef O_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017092 if (PyModule_AddIntMacro(m, O_RDONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017093#endif
17094#ifdef O_WRONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017095 if (PyModule_AddIntMacro(m, O_WRONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017096#endif
17097#ifdef O_RDWR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017098 if (PyModule_AddIntMacro(m, O_RDWR)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017099#endif
17100#ifdef O_NDELAY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017101 if (PyModule_AddIntMacro(m, O_NDELAY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017102#endif
17103#ifdef O_NONBLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017104 if (PyModule_AddIntMacro(m, O_NONBLOCK)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017105#endif
17106#ifdef O_APPEND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017107 if (PyModule_AddIntMacro(m, O_APPEND)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017108#endif
17109#ifdef O_DSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017110 if (PyModule_AddIntMacro(m, O_DSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017111#endif
17112#ifdef O_RSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017113 if (PyModule_AddIntMacro(m, O_RSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017114#endif
17115#ifdef O_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017116 if (PyModule_AddIntMacro(m, O_SYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017117#endif
17118#ifdef O_NOCTTY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017119 if (PyModule_AddIntMacro(m, O_NOCTTY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017120#endif
17121#ifdef O_CREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017122 if (PyModule_AddIntMacro(m, O_CREAT)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017123#endif
17124#ifdef O_EXCL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017125 if (PyModule_AddIntMacro(m, O_EXCL)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017126#endif
17127#ifdef O_TRUNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017128 if (PyModule_AddIntMacro(m, O_TRUNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000017129#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +000017130#ifdef O_BINARY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017131 if (PyModule_AddIntMacro(m, O_BINARY)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017132#endif
17133#ifdef O_TEXT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017134 if (PyModule_AddIntMacro(m, O_TEXT)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000017135#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017136#ifdef O_XATTR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017137 if (PyModule_AddIntMacro(m, O_XATTR)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017138#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017139#ifdef O_LARGEFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017140 if (PyModule_AddIntMacro(m, O_LARGEFILE)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017141#endif
Skip Montanaro5ff14922005-05-16 02:42:22 +000017142#ifdef O_SHLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017143 if (PyModule_AddIntMacro(m, O_SHLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017144#endif
17145#ifdef O_EXLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017146 if (PyModule_AddIntMacro(m, O_EXLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000017147#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017148#ifdef O_EXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017149 if (PyModule_AddIntMacro(m, O_EXEC)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017150#endif
17151#ifdef O_SEARCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017152 if (PyModule_AddIntMacro(m, O_SEARCH)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017153#endif
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017154#ifdef O_PATH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017155 if (PyModule_AddIntMacro(m, O_PATH)) return -1;
Benjamin Peterson3b965a22013-03-13 10:27:41 -050017156#endif
Jesus Ceacf381202012-04-24 20:44:40 +020017157#ifdef O_TTY_INIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017158 if (PyModule_AddIntMacro(m, O_TTY_INIT)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020017159#endif
Christian Heimes177b3f92013-08-16 14:35:09 +020017160#ifdef O_TMPFILE
17161 if (PyModule_AddIntMacro(m, O_TMPFILE)) return -1;
17162#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017163#ifdef PRIO_PROCESS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017164 if (PyModule_AddIntMacro(m, PRIO_PROCESS)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017165#endif
17166#ifdef PRIO_PGRP
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017167 if (PyModule_AddIntMacro(m, PRIO_PGRP)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017168#endif
17169#ifdef PRIO_USER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017170 if (PyModule_AddIntMacro(m, PRIO_USER)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017171#endif
Charles-François Natali1e045b12011-05-22 20:42:32 +020017172#ifdef O_CLOEXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017173 if (PyModule_AddIntMacro(m, O_CLOEXEC)) return -1;
Charles-François Natali1e045b12011-05-22 20:42:32 +020017174#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017175#ifdef O_ACCMODE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017176 if (PyModule_AddIntMacro(m, O_ACCMODE)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017177#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000017178
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017179
Jesus Cea94363612012-06-22 18:32:07 +020017180#ifdef SEEK_HOLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017181 if (PyModule_AddIntMacro(m, SEEK_HOLE)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017182#endif
17183#ifdef SEEK_DATA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017184 if (PyModule_AddIntMacro(m, SEEK_DATA)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020017185#endif
17186
Tim Peters5aa91602002-01-30 05:46:57 +000017187/* MS Windows */
17188#ifdef O_NOINHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000017189 /* Don't inherit in child processes. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017190 if (PyModule_AddIntMacro(m, O_NOINHERIT)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017191#endif
17192#ifdef _O_SHORT_LIVED
Victor Stinner8c62be82010-05-06 00:08:46 +000017193 /* Optimize for short life (keep in memory). */
17194 /* MS forgot to define this one with a non-underscore form too. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017195 if (PyModule_AddIntConstant(m, "O_SHORT_LIVED", _O_SHORT_LIVED)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017196#endif
17197#ifdef O_TEMPORARY
Victor Stinner8c62be82010-05-06 00:08:46 +000017198 /* Automatically delete when last handle is closed. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017199 if (PyModule_AddIntMacro(m, O_TEMPORARY)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017200#endif
17201#ifdef O_RANDOM
Victor Stinner8c62be82010-05-06 00:08:46 +000017202 /* Optimize for random access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017203 if (PyModule_AddIntMacro(m, O_RANDOM)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017204#endif
17205#ifdef O_SEQUENTIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000017206 /* Optimize for sequential access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017207 if (PyModule_AddIntMacro(m, O_SEQUENTIAL)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000017208#endif
17209
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017210/* GNU extensions. */
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017211#ifdef O_ASYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000017212 /* Send a SIGIO signal whenever input or output
17213 becomes available on file descriptor */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017214 if (PyModule_AddIntMacro(m, O_ASYNC)) return -1;
Alexandre Vassalottibee32532008-05-16 18:15:12 +000017215#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017216#ifdef O_DIRECT
Victor Stinner8c62be82010-05-06 00:08:46 +000017217 /* Direct disk access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017218 if (PyModule_AddIntMacro(m, O_DIRECT)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017219#endif
17220#ifdef O_DIRECTORY
Victor Stinner8c62be82010-05-06 00:08:46 +000017221 /* Must be a directory. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017222 if (PyModule_AddIntMacro(m, O_DIRECTORY)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017223#endif
17224#ifdef O_NOFOLLOW
Victor Stinner8c62be82010-05-06 00:08:46 +000017225 /* Do not follow links. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017226 if (PyModule_AddIntMacro(m, O_NOFOLLOW)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000017227#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020017228#ifdef O_NOLINKS
17229 /* Fails if link count of the named file is greater than 1 */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017230 if (PyModule_AddIntMacro(m, O_NOLINKS)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020017231#endif
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017232#ifdef O_NOATIME
Victor Stinner8c62be82010-05-06 00:08:46 +000017233 /* Do not update the access time. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017234 if (PyModule_AddIntMacro(m, O_NOATIME)) return -1;
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000017235#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +000017236
Victor Stinner8c62be82010-05-06 00:08:46 +000017237 /* These come from sysexits.h */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017238#ifdef EX_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017239 if (PyModule_AddIntMacro(m, EX_OK)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017240#endif /* EX_OK */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017241#ifdef EX_USAGE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017242 if (PyModule_AddIntMacro(m, EX_USAGE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017243#endif /* EX_USAGE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017244#ifdef EX_DATAERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017245 if (PyModule_AddIntMacro(m, EX_DATAERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017246#endif /* EX_DATAERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017247#ifdef EX_NOINPUT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017248 if (PyModule_AddIntMacro(m, EX_NOINPUT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017249#endif /* EX_NOINPUT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017250#ifdef EX_NOUSER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017251 if (PyModule_AddIntMacro(m, EX_NOUSER)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017252#endif /* EX_NOUSER */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017253#ifdef EX_NOHOST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017254 if (PyModule_AddIntMacro(m, EX_NOHOST)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017255#endif /* EX_NOHOST */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017256#ifdef EX_UNAVAILABLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017257 if (PyModule_AddIntMacro(m, EX_UNAVAILABLE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017258#endif /* EX_UNAVAILABLE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017259#ifdef EX_SOFTWARE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017260 if (PyModule_AddIntMacro(m, EX_SOFTWARE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017261#endif /* EX_SOFTWARE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017262#ifdef EX_OSERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017263 if (PyModule_AddIntMacro(m, EX_OSERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017264#endif /* EX_OSERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017265#ifdef EX_OSFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017266 if (PyModule_AddIntMacro(m, EX_OSFILE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017267#endif /* EX_OSFILE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017268#ifdef EX_CANTCREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017269 if (PyModule_AddIntMacro(m, EX_CANTCREAT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017270#endif /* EX_CANTCREAT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017271#ifdef EX_IOERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017272 if (PyModule_AddIntMacro(m, EX_IOERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017273#endif /* EX_IOERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017274#ifdef EX_TEMPFAIL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017275 if (PyModule_AddIntMacro(m, EX_TEMPFAIL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017276#endif /* EX_TEMPFAIL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017277#ifdef EX_PROTOCOL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017278 if (PyModule_AddIntMacro(m, EX_PROTOCOL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017279#endif /* EX_PROTOCOL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017280#ifdef EX_NOPERM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017281 if (PyModule_AddIntMacro(m, EX_NOPERM)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017282#endif /* EX_NOPERM */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017283#ifdef EX_CONFIG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017284 if (PyModule_AddIntMacro(m, EX_CONFIG)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017285#endif /* EX_CONFIG */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017286#ifdef EX_NOTFOUND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017287 if (PyModule_AddIntMacro(m, EX_NOTFOUND)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000017288#endif /* EX_NOTFOUND */
Barry Warsaw5676bd12003-01-07 20:57:09 +000017289
Amaury Forgeot d'Arc66d00ad2010-09-10 18:11:45 +000017290 /* statvfs */
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017291#ifdef ST_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017292 if (PyModule_AddIntMacro(m, ST_RDONLY)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017293#endif /* ST_RDONLY */
17294#ifdef ST_NOSUID
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017295 if (PyModule_AddIntMacro(m, ST_NOSUID)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000017296#endif /* ST_NOSUID */
17297
doko@ubuntu.comca616a22013-12-08 15:23:07 +010017298 /* GNU extensions */
17299#ifdef ST_NODEV
17300 if (PyModule_AddIntMacro(m, ST_NODEV)) return -1;
17301#endif /* ST_NODEV */
17302#ifdef ST_NOEXEC
17303 if (PyModule_AddIntMacro(m, ST_NOEXEC)) return -1;
17304#endif /* ST_NOEXEC */
17305#ifdef ST_SYNCHRONOUS
17306 if (PyModule_AddIntMacro(m, ST_SYNCHRONOUS)) return -1;
17307#endif /* ST_SYNCHRONOUS */
17308#ifdef ST_MANDLOCK
17309 if (PyModule_AddIntMacro(m, ST_MANDLOCK)) return -1;
17310#endif /* ST_MANDLOCK */
17311#ifdef ST_WRITE
17312 if (PyModule_AddIntMacro(m, ST_WRITE)) return -1;
17313#endif /* ST_WRITE */
17314#ifdef ST_APPEND
17315 if (PyModule_AddIntMacro(m, ST_APPEND)) return -1;
17316#endif /* ST_APPEND */
17317#ifdef ST_NOATIME
17318 if (PyModule_AddIntMacro(m, ST_NOATIME)) return -1;
17319#endif /* ST_NOATIME */
17320#ifdef ST_NODIRATIME
17321 if (PyModule_AddIntMacro(m, ST_NODIRATIME)) return -1;
17322#endif /* ST_NODIRATIME */
17323#ifdef ST_RELATIME
17324 if (PyModule_AddIntMacro(m, ST_RELATIME)) return -1;
17325#endif /* ST_RELATIME */
17326
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017327 /* FreeBSD sendfile() constants */
17328#ifdef SF_NODISKIO
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017329 if (PyModule_AddIntMacro(m, SF_NODISKIO)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017330#endif
17331#ifdef SF_MNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017332 if (PyModule_AddIntMacro(m, SF_MNOWAIT)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017333#endif
17334#ifdef SF_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017335 if (PyModule_AddIntMacro(m, SF_SYNC)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000017336#endif
17337
Ross Lagerwall7807c352011-03-17 20:20:30 +020017338 /* constants for posix_fadvise */
17339#ifdef POSIX_FADV_NORMAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017340 if (PyModule_AddIntMacro(m, POSIX_FADV_NORMAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017341#endif
17342#ifdef POSIX_FADV_SEQUENTIAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017343 if (PyModule_AddIntMacro(m, POSIX_FADV_SEQUENTIAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017344#endif
17345#ifdef POSIX_FADV_RANDOM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017346 if (PyModule_AddIntMacro(m, POSIX_FADV_RANDOM)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017347#endif
17348#ifdef POSIX_FADV_NOREUSE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017349 if (PyModule_AddIntMacro(m, POSIX_FADV_NOREUSE)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017350#endif
17351#ifdef POSIX_FADV_WILLNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017352 if (PyModule_AddIntMacro(m, POSIX_FADV_WILLNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017353#endif
17354#ifdef POSIX_FADV_DONTNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017355 if (PyModule_AddIntMacro(m, POSIX_FADV_DONTNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017356#endif
17357
17358 /* constants for waitid */
17359#if defined(HAVE_SYS_WAIT_H) && defined(HAVE_WAITID)
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017360 if (PyModule_AddIntMacro(m, P_PID)) return -1;
17361 if (PyModule_AddIntMacro(m, P_PGID)) return -1;
17362 if (PyModule_AddIntMacro(m, P_ALL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017363#endif
17364#ifdef WEXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017365 if (PyModule_AddIntMacro(m, WEXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017366#endif
17367#ifdef WNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017368 if (PyModule_AddIntMacro(m, WNOWAIT)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017369#endif
17370#ifdef WSTOPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017371 if (PyModule_AddIntMacro(m, WSTOPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017372#endif
17373#ifdef CLD_EXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017374 if (PyModule_AddIntMacro(m, CLD_EXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017375#endif
17376#ifdef CLD_DUMPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017377 if (PyModule_AddIntMacro(m, CLD_DUMPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017378#endif
17379#ifdef CLD_TRAPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017380 if (PyModule_AddIntMacro(m, CLD_TRAPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017381#endif
17382#ifdef CLD_CONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017383 if (PyModule_AddIntMacro(m, CLD_CONTINUED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017384#endif
17385
17386 /* constants for lockf */
17387#ifdef F_LOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017388 if (PyModule_AddIntMacro(m, F_LOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017389#endif
17390#ifdef F_TLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017391 if (PyModule_AddIntMacro(m, F_TLOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017392#endif
17393#ifdef F_ULOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017394 if (PyModule_AddIntMacro(m, F_ULOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017395#endif
17396#ifdef F_TEST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017397 if (PyModule_AddIntMacro(m, F_TEST)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017398#endif
17399
Guido van Rossum246bc171999-02-01 23:54:31 +000017400#ifdef HAVE_SPAWNV
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017401 if (PyModule_AddIntConstant(m, "P_WAIT", _P_WAIT)) return -1;
17402 if (PyModule_AddIntConstant(m, "P_NOWAIT", _P_NOWAIT)) return -1;
17403 if (PyModule_AddIntConstant(m, "P_OVERLAY", _OLD_P_OVERLAY)) return -1;
17404 if (PyModule_AddIntConstant(m, "P_NOWAITO", _P_NOWAITO)) return -1;
17405 if (PyModule_AddIntConstant(m, "P_DETACH", _P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +000017406#endif
17407
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017408#ifdef HAVE_SCHED_H
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017409 if (PyModule_AddIntMacro(m, SCHED_OTHER)) return -1;
17410 if (PyModule_AddIntMacro(m, SCHED_FIFO)) return -1;
17411 if (PyModule_AddIntMacro(m, SCHED_RR)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017412#ifdef SCHED_SPORADIC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017413 if (PyModule_AddIntMacro(m, SCHED_SPORADIC) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017414#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017415#ifdef SCHED_BATCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017416 if (PyModule_AddIntMacro(m, SCHED_BATCH)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017417#endif
17418#ifdef SCHED_IDLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017419 if (PyModule_AddIntMacro(m, SCHED_IDLE)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017420#endif
17421#ifdef SCHED_RESET_ON_FORK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017422 if (PyModule_AddIntMacro(m, SCHED_RESET_ON_FORK)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017423#endif
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017424#ifdef SCHED_SYS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017425 if (PyModule_AddIntMacro(m, SCHED_SYS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017426#endif
17427#ifdef SCHED_IA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017428 if (PyModule_AddIntMacro(m, SCHED_IA)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017429#endif
17430#ifdef SCHED_FSS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017431 if (PyModule_AddIntMacro(m, SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017432#endif
17433#ifdef SCHED_FX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017434 if (PyModule_AddIntConstant(m, "SCHED_FX", SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020017435#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017436#endif
17437
Benjamin Peterson9428d532011-09-14 11:45:52 -040017438#ifdef USE_XATTRS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017439 if (PyModule_AddIntMacro(m, XATTR_CREATE)) return -1;
17440 if (PyModule_AddIntMacro(m, XATTR_REPLACE)) return -1;
17441 if (PyModule_AddIntMacro(m, XATTR_SIZE_MAX)) return -1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040017442#endif
17443
Victor Stinner8b905bd2011-10-25 13:34:04 +020017444#ifdef RTLD_LAZY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017445 if (PyModule_AddIntMacro(m, RTLD_LAZY)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017446#endif
17447#ifdef RTLD_NOW
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017448 if (PyModule_AddIntMacro(m, RTLD_NOW)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017449#endif
17450#ifdef RTLD_GLOBAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017451 if (PyModule_AddIntMacro(m, RTLD_GLOBAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017452#endif
17453#ifdef RTLD_LOCAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017454 if (PyModule_AddIntMacro(m, RTLD_LOCAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017455#endif
17456#ifdef RTLD_NODELETE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017457 if (PyModule_AddIntMacro(m, RTLD_NODELETE)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017458#endif
17459#ifdef RTLD_NOLOAD
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017460 if (PyModule_AddIntMacro(m, RTLD_NOLOAD)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017461#endif
17462#ifdef RTLD_DEEPBIND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020017463 if (PyModule_AddIntMacro(m, RTLD_DEEPBIND)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020017464#endif
17465
Victor Stinner8c62be82010-05-06 00:08:46 +000017466 return 0;
Barry Warsaw4a342091996-12-19 23:50:02 +000017467}
17468
17469
Victor Stinnerd42c4282014-10-10 00:09:47 +020017470#ifdef MS_WINDOWS
Martin v. Löwis1a214512008-06-11 05:26:20 +000017471#define INITFUNC PyInit_nt
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017472#define MODNAME "nt"
Tim Peters58e0a8c2001-05-14 22:32:33 +000017473
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000017474#else
Martin v. Löwis1a214512008-06-11 05:26:20 +000017475#define INITFUNC PyInit_posix
Guido van Rossum0cb96de1997-10-01 04:29:29 +000017476#define MODNAME "posix"
17477#endif
17478
Martin v. Löwis1a214512008-06-11 05:26:20 +000017479static struct PyModuleDef posixmodule = {
Victor Stinner8c62be82010-05-06 00:08:46 +000017480 PyModuleDef_HEAD_INIT,
17481 MODNAME,
17482 posix__doc__,
17483 -1,
17484 posix_methods,
17485 NULL,
17486 NULL,
17487 NULL,
17488 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +000017489};
17490
17491
Larry Hastings9cf065c2012-06-22 16:30:09 -070017492static char *have_functions[] = {
17493
17494#ifdef HAVE_FACCESSAT
17495 "HAVE_FACCESSAT",
17496#endif
17497
17498#ifdef HAVE_FCHDIR
17499 "HAVE_FCHDIR",
17500#endif
17501
17502#ifdef HAVE_FCHMOD
17503 "HAVE_FCHMOD",
17504#endif
17505
17506#ifdef HAVE_FCHMODAT
17507 "HAVE_FCHMODAT",
17508#endif
17509
17510#ifdef HAVE_FCHOWN
17511 "HAVE_FCHOWN",
17512#endif
17513
Larry Hastings00964ed2013-08-12 13:49:30 -040017514#ifdef HAVE_FCHOWNAT
17515 "HAVE_FCHOWNAT",
17516#endif
17517
Larry Hastings9cf065c2012-06-22 16:30:09 -070017518#ifdef HAVE_FEXECVE
17519 "HAVE_FEXECVE",
17520#endif
17521
17522#ifdef HAVE_FDOPENDIR
17523 "HAVE_FDOPENDIR",
17524#endif
17525
Georg Brandl306336b2012-06-24 12:55:33 +020017526#ifdef HAVE_FPATHCONF
17527 "HAVE_FPATHCONF",
17528#endif
17529
Larry Hastings9cf065c2012-06-22 16:30:09 -070017530#ifdef HAVE_FSTATAT
17531 "HAVE_FSTATAT",
17532#endif
17533
17534#ifdef HAVE_FSTATVFS
17535 "HAVE_FSTATVFS",
17536#endif
17537
Georg Brandl306336b2012-06-24 12:55:33 +020017538#ifdef HAVE_FTRUNCATE
17539 "HAVE_FTRUNCATE",
17540#endif
17541
Larry Hastings9cf065c2012-06-22 16:30:09 -070017542#ifdef HAVE_FUTIMENS
17543 "HAVE_FUTIMENS",
17544#endif
17545
17546#ifdef HAVE_FUTIMES
17547 "HAVE_FUTIMES",
17548#endif
17549
17550#ifdef HAVE_FUTIMESAT
17551 "HAVE_FUTIMESAT",
17552#endif
17553
17554#ifdef HAVE_LINKAT
17555 "HAVE_LINKAT",
17556#endif
17557
17558#ifdef HAVE_LCHFLAGS
17559 "HAVE_LCHFLAGS",
17560#endif
17561
17562#ifdef HAVE_LCHMOD
17563 "HAVE_LCHMOD",
17564#endif
17565
17566#ifdef HAVE_LCHOWN
17567 "HAVE_LCHOWN",
17568#endif
17569
17570#ifdef HAVE_LSTAT
17571 "HAVE_LSTAT",
17572#endif
17573
17574#ifdef HAVE_LUTIMES
17575 "HAVE_LUTIMES",
17576#endif
17577
17578#ifdef HAVE_MKDIRAT
17579 "HAVE_MKDIRAT",
17580#endif
17581
17582#ifdef HAVE_MKFIFOAT
17583 "HAVE_MKFIFOAT",
17584#endif
17585
17586#ifdef HAVE_MKNODAT
17587 "HAVE_MKNODAT",
17588#endif
17589
17590#ifdef HAVE_OPENAT
17591 "HAVE_OPENAT",
17592#endif
17593
17594#ifdef HAVE_READLINKAT
17595 "HAVE_READLINKAT",
17596#endif
17597
17598#ifdef HAVE_RENAMEAT
17599 "HAVE_RENAMEAT",
17600#endif
17601
17602#ifdef HAVE_SYMLINKAT
17603 "HAVE_SYMLINKAT",
17604#endif
17605
17606#ifdef HAVE_UNLINKAT
17607 "HAVE_UNLINKAT",
17608#endif
17609
17610#ifdef HAVE_UTIMENSAT
17611 "HAVE_UTIMENSAT",
17612#endif
17613
17614#ifdef MS_WINDOWS
17615 "MS_WINDOWS",
17616#endif
17617
17618 NULL
17619};
17620
17621
Mark Hammondfe51c6d2002-08-02 02:27:13 +000017622PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +000017623INITFUNC(void)
Guido van Rossumb6775db1994-08-01 11:34:53 +000017624{
Victor Stinner8c62be82010-05-06 00:08:46 +000017625 PyObject *m, *v;
Larry Hastings9cf065c2012-06-22 16:30:09 -070017626 PyObject *list;
17627 char **trace;
Tim Peters5aa91602002-01-30 05:46:57 +000017628
Brian Curtin52173d42010-12-02 18:29:18 +000017629#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000017630 win32_can_symlink = enable_symlink();
Brian Curtin52173d42010-12-02 18:29:18 +000017631#endif
17632
Victor Stinner8c62be82010-05-06 00:08:46 +000017633 m = PyModule_Create(&posixmodule);
17634 if (m == NULL)
17635 return NULL;
Tim Peters5aa91602002-01-30 05:46:57 +000017636
Victor Stinner8c62be82010-05-06 00:08:46 +000017637 /* Initialize environ dictionary */
17638 v = convertenviron();
17639 Py_XINCREF(v);
17640 if (v == NULL || PyModule_AddObject(m, "environ", v) != 0)
17641 return NULL;
17642 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +000017643
Victor Stinner8c62be82010-05-06 00:08:46 +000017644 if (all_ins(m))
17645 return NULL;
Barry Warsaw4a342091996-12-19 23:50:02 +000017646
Victor Stinner8c62be82010-05-06 00:08:46 +000017647 if (setup_confname_tables(m))
17648 return NULL;
Fred Drakebec628d1999-12-15 18:31:10 +000017649
Victor Stinner8c62be82010-05-06 00:08:46 +000017650 Py_INCREF(PyExc_OSError);
17651 PyModule_AddObject(m, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +000017652
Guido van Rossumb3d39562000-01-31 18:41:26 +000017653#ifdef HAVE_PUTENV
Victor Stinner8c62be82010-05-06 00:08:46 +000017654 if (posix_putenv_garbage == NULL)
17655 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +000017656#endif
Guido van Rossum98bf58f2001-10-18 20:34:25 +000017657
Victor Stinner8c62be82010-05-06 00:08:46 +000017658 if (!initialized) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020017659#if defined(HAVE_WAITID) && !defined(__APPLE__)
17660 waitid_result_desc.name = MODNAME ".waitid_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017661 if (PyStructSequence_InitType2(&WaitidResultType, &waitid_result_desc) < 0)
17662 return NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020017663#endif
17664
Christian Heimes25827622013-10-12 01:27:08 +020017665 stat_result_desc.name = "os.stat_result"; /* see issue #19209 */
Victor Stinner8c62be82010-05-06 00:08:46 +000017666 stat_result_desc.fields[7].name = PyStructSequence_UnnamedField;
17667 stat_result_desc.fields[8].name = PyStructSequence_UnnamedField;
17668 stat_result_desc.fields[9].name = PyStructSequence_UnnamedField;
Victor Stinner1c8f0592013-07-22 22:24:54 +020017669 if (PyStructSequence_InitType2(&StatResultType, &stat_result_desc) < 0)
17670 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017671 structseq_new = StatResultType.tp_new;
17672 StatResultType.tp_new = statresult_new;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017673
Christian Heimes25827622013-10-12 01:27:08 +020017674 statvfs_result_desc.name = "os.statvfs_result"; /* see issue #19209 */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017675 if (PyStructSequence_InitType2(&StatVFSResultType,
17676 &statvfs_result_desc) < 0)
17677 return NULL;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017678#ifdef NEED_TICKS_PER_SECOND
17679# if defined(HAVE_SYSCONF) && defined(_SC_CLK_TCK)
Victor Stinner8c62be82010-05-06 00:08:46 +000017680 ticks_per_second = sysconf(_SC_CLK_TCK);
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017681# elif defined(HZ)
Victor Stinner8c62be82010-05-06 00:08:46 +000017682 ticks_per_second = HZ;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017683# else
Victor Stinner8c62be82010-05-06 00:08:46 +000017684 ticks_per_second = 60; /* magic fallback value; may be bogus */
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000017685# endif
17686#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017687
Benjamin Peterson0163c9a2011-08-02 18:11:38 -050017688#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017689 sched_param_desc.name = MODNAME ".sched_param";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017690 if (PyStructSequence_InitType2(&SchedParamType, &sched_param_desc) < 0)
17691 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100017692 SchedParamType.tp_new = os_sched_param;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017693#endif
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017694
17695 /* initialize TerminalSize_info */
Victor Stinner1c8f0592013-07-22 22:24:54 +020017696 if (PyStructSequence_InitType2(&TerminalSizeType,
17697 &TerminalSize_desc) < 0)
17698 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000017699 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020017700#if defined(HAVE_WAITID) && !defined(__APPLE__)
17701 Py_INCREF((PyObject*) &WaitidResultType);
17702 PyModule_AddObject(m, "waitid_result", (PyObject*) &WaitidResultType);
17703#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000017704 Py_INCREF((PyObject*) &StatResultType);
17705 PyModule_AddObject(m, "stat_result", (PyObject*) &StatResultType);
17706 Py_INCREF((PyObject*) &StatVFSResultType);
17707 PyModule_AddObject(m, "statvfs_result",
17708 (PyObject*) &StatVFSResultType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017709
17710#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050017711 Py_INCREF(&SchedParamType);
17712 PyModule_AddObject(m, "sched_param", (PyObject *)&SchedParamType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050017713#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +000017714
Larry Hastings605a62d2012-06-24 04:33:36 -070017715 times_result_desc.name = MODNAME ".times_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017716 if (PyStructSequence_InitType2(&TimesResultType, &times_result_desc) < 0)
17717 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017718 PyModule_AddObject(m, "times_result", (PyObject *)&TimesResultType);
17719
17720 uname_result_desc.name = MODNAME ".uname_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020017721 if (PyStructSequence_InitType2(&UnameResultType, &uname_result_desc) < 0)
17722 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070017723 PyModule_AddObject(m, "uname_result", (PyObject *)&UnameResultType);
17724
Thomas Wouters477c8d52006-05-27 19:21:47 +000017725#ifdef __APPLE__
Victor Stinner8c62be82010-05-06 00:08:46 +000017726 /*
17727 * Step 2 of weak-linking support on Mac OS X.
17728 *
17729 * The code below removes functions that are not available on the
17730 * currently active platform.
17731 *
17732 * This block allow one to use a python binary that was build on
Larry Hastings9cf065c2012-06-22 16:30:09 -070017733 * OSX 10.4 on OSX 10.3, without losing access to new APIs on
Victor Stinner8c62be82010-05-06 00:08:46 +000017734 * OSX 10.4.
17735 */
Thomas Wouters477c8d52006-05-27 19:21:47 +000017736#ifdef HAVE_FSTATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017737 if (fstatvfs == NULL) {
17738 if (PyObject_DelAttrString(m, "fstatvfs") == -1) {
17739 return NULL;
17740 }
17741 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017742#endif /* HAVE_FSTATVFS */
17743
17744#ifdef HAVE_STATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000017745 if (statvfs == NULL) {
17746 if (PyObject_DelAttrString(m, "statvfs") == -1) {
17747 return NULL;
17748 }
17749 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017750#endif /* HAVE_STATVFS */
17751
17752# ifdef HAVE_LCHOWN
Victor Stinner8c62be82010-05-06 00:08:46 +000017753 if (lchown == NULL) {
17754 if (PyObject_DelAttrString(m, "lchown") == -1) {
17755 return NULL;
17756 }
17757 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000017758#endif /* HAVE_LCHOWN */
17759
17760
17761#endif /* __APPLE__ */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017762
Antoine Pitrou9d20e0e2012-09-12 18:01:36 +020017763 Py_INCREF(&TerminalSizeType);
Antoine Pitroubcf2b592012-02-08 23:28:36 +010017764 PyModule_AddObject(m, "terminal_size", (PyObject*) &TerminalSizeType);
17765
Larry Hastings6fe20b32012-04-19 15:07:49 -070017766 billion = PyLong_FromLong(1000000000);
17767 if (!billion)
17768 return NULL;
17769
Larry Hastings9cf065c2012-06-22 16:30:09 -070017770 /* suppress "function not used" warnings */
17771 {
17772 int ignored;
17773 fd_specified("", -1);
17774 follow_symlinks_specified("", 1);
17775 dir_fd_and_follow_symlinks_invalid("chmod", DEFAULT_DIR_FD, 1);
17776 dir_fd_converter(Py_None, &ignored);
17777 dir_fd_unavailable(Py_None, &ignored);
17778 }
17779
17780 /*
17781 * provide list of locally available functions
17782 * so os.py can populate support_* lists
17783 */
17784 list = PyList_New(0);
17785 if (!list)
17786 return NULL;
17787 for (trace = have_functions; *trace; trace++) {
17788 PyObject *unicode = PyUnicode_DecodeASCII(*trace, strlen(*trace), NULL);
17789 if (!unicode)
17790 return NULL;
17791 if (PyList_Append(list, unicode))
17792 return NULL;
17793 Py_DECREF(unicode);
17794 }
17795 PyModule_AddObject(m, "_have_functions", list);
17796
17797 initialized = 1;
17798
Victor Stinner8c62be82010-05-06 00:08:46 +000017799 return m;
Guido van Rossumb6775db1994-08-01 11:34:53 +000017800}
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000017801
17802#ifdef __cplusplus
17803}
17804#endif