blob: 89fb08b6743a979d0a16f935a507ce5e78bd26f5 [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"
Victor Stinner6036e442015-03-08 01:58:04 +010028#include "structmember.h"
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020029#ifndef MS_WINDOWS
30#include "posixmodule.h"
Tim Golden0321cf22014-05-05 19:46:17 +010031#else
32#include "winreparse.h"
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020033#endif
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000034
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000035#ifdef __cplusplus
36extern "C" {
37#endif
38
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000039PyDoc_STRVAR(posix__doc__,
Guido van Rossumec4f4ac1997-06-02 22:20:51 +000040"This module provides access to operating system functionality that is\n\
41standardized by the C Standard and the POSIX standard (a thinly\n\
42disguised Unix interface). Refer to the library manual and\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000043corresponding Unix manual entries for more information on calls.");
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000044
Martin v. Löwis0073f2e2002-11-21 23:52:35 +000045
Ross Lagerwall4d076da2011-03-18 06:56:53 +020046#ifdef HAVE_SYS_UIO_H
47#include <sys/uio.h>
48#endif
49
Thomas Wouters0e3f5912006-08-11 14:57:12 +000050#ifdef HAVE_SYS_TYPES_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000051#include <sys/types.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000052#endif /* HAVE_SYS_TYPES_H */
53
54#ifdef HAVE_SYS_STAT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +000055#include <sys/stat.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000056#endif /* HAVE_SYS_STAT_H */
Guido van Rossuma6535fd2001-10-18 19:44:10 +000057
Guido van Rossum36bc6801995-06-14 22:54:23 +000058#ifdef HAVE_SYS_WAIT_H
Victor Stinner8c62be82010-05-06 00:08:46 +000059#include <sys/wait.h> /* For WNOHANG */
Guido van Rossum36bc6801995-06-14 22:54:23 +000060#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +000061
Thomas Wouters0e3f5912006-08-11 14:57:12 +000062#ifdef HAVE_SIGNAL_H
Guido van Rossuma376cc51996-12-05 23:43:35 +000063#include <signal.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +000064#endif
Guido van Rossuma376cc51996-12-05 23:43:35 +000065
Guido van Rossumb6775db1994-08-01 11:34:53 +000066#ifdef HAVE_FCNTL_H
67#include <fcntl.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000068#endif /* HAVE_FCNTL_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +000069
Guido van Rossuma6535fd2001-10-18 19:44:10 +000070#ifdef HAVE_GRP_H
71#include <grp.h>
72#endif
73
Barry Warsaw5676bd12003-01-07 20:57:09 +000074#ifdef HAVE_SYSEXITS_H
75#include <sysexits.h>
76#endif /* HAVE_SYSEXITS_H */
77
Anthony Baxter8a560de2004-10-13 15:30:56 +000078#ifdef HAVE_SYS_LOADAVG_H
79#include <sys/loadavg.h>
80#endif
81
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000082#ifdef HAVE_LANGINFO_H
83#include <langinfo.h>
84#endif
85
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000086#ifdef HAVE_SYS_SENDFILE_H
87#include <sys/sendfile.h>
88#endif
89
Benjamin Peterson94b580d2011-08-02 17:30:04 -050090#ifdef HAVE_SCHED_H
91#include <sched.h>
92#endif
93
Benjamin Peterson2dbda072012-03-16 10:12:55 -050094#if !defined(CPU_ALLOC) && defined(HAVE_SCHED_SETAFFINITY)
Benjamin Peterson7b51b8d2012-03-14 22:28:25 -050095#undef HAVE_SCHED_SETAFFINITY
96#endif
97
doko@ubuntu.com4a173bc2014-04-17 19:47:16 +020098#if defined(HAVE_SYS_XATTR_H) && defined(__GLIBC__) && !defined(__FreeBSD_kernel__) && !defined(__GNU__)
Benjamin Peterson9428d532011-09-14 11:45:52 -040099#define USE_XATTRS
100#endif
101
102#ifdef USE_XATTRS
Benjamin Petersonb77fe172011-09-13 17:20:47 -0400103#include <sys/xattr.h>
Benjamin Peterson799bd802011-08-31 22:15:17 -0400104#endif
105
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000106#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
107#ifdef HAVE_SYS_SOCKET_H
108#include <sys/socket.h>
109#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000110#endif
111
Victor Stinner8b905bd2011-10-25 13:34:04 +0200112#ifdef HAVE_DLFCN_H
113#include <dlfcn.h>
114#endif
115
Charles-Francois Natali44feda32013-05-20 14:40:46 +0200116#ifdef __hpux
117#include <sys/mpctl.h>
118#endif
119
120#if defined(__DragonFly__) || \
121 defined(__OpenBSD__) || \
122 defined(__FreeBSD__) || \
123 defined(__NetBSD__) || \
124 defined(__APPLE__)
125#include <sys/sysctl.h>
126#endif
127
Antoine Pitroubcf2b592012-02-08 23:28:36 +0100128#if defined(MS_WINDOWS)
129# define TERMSIZE_USE_CONIO
130#elif defined(HAVE_SYS_IOCTL_H)
131# include <sys/ioctl.h>
132# if defined(HAVE_TERMIOS_H)
133# include <termios.h>
134# endif
135# if defined(TIOCGWINSZ)
136# define TERMSIZE_USE_IOCTL
137# endif
138#endif /* MS_WINDOWS */
139
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000140/* Various compilers have only certain posix functions */
Martin v. Löwis4f1cd8b2001-07-26 13:41:06 +0000141/* XXX Gosh I wish these were all moved into pyconfig.h */
Victor Stinner8c62be82010-05-06 00:08:46 +0000142#if defined(__WATCOMC__) && !defined(__QNX__) /* Watcom compiler */
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000143#define HAVE_OPENDIR 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000144#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000145#include <process.h>
146#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000147#ifdef _MSC_VER /* Microsoft compiler */
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +0000148#define HAVE_GETPPID 1
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +0000149#define HAVE_GETLOGIN 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000150#define HAVE_SPAWNV 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000151#define HAVE_EXECV 1
152#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000153#define HAVE_SYSTEM 1
154#define HAVE_CWAIT 1
155#define HAVE_FSYNC 1
Tim Peters11b23062003-04-23 02:39:17 +0000156#define fsync _commit
Andrew MacIntyre6c73af22002-03-03 03:07:07 +0000157#else
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000158/* Unix functions that the configure script doesn't check for */
159#define HAVE_EXECV 1
160#define HAVE_FORK 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000161#if defined(__USLC__) && defined(__SCO_VERSION__) /* SCO UDK Compiler */
Guido van Rossum2242f2f2001-04-11 20:58:20 +0000162#define HAVE_FORK1 1
163#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000164#define HAVE_GETEGID 1
165#define HAVE_GETEUID 1
166#define HAVE_GETGID 1
167#define HAVE_GETPPID 1
168#define HAVE_GETUID 1
169#define HAVE_KILL 1
170#define HAVE_OPENDIR 1
171#define HAVE_PIPE 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000172#define HAVE_SYSTEM 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000173#define HAVE_WAIT 1
Victor Stinner8c62be82010-05-06 00:08:46 +0000174#define HAVE_TTYNAME 1
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000175#endif /* _MSC_VER */
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000176#endif /* ! __WATCOMC__ || __QNX__ */
Guido van Rossumad0ee831995-03-01 10:34:45 +0000177
Victor Stinnera2f7c002012-02-08 03:36:25 +0100178
Larry Hastings61272b72014-01-07 12:41:53 -0800179/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +1000180# one of the few times we lie about this name!
Larry Hastings44e2eaa2013-11-23 15:37:55 -0800181module os
Larry Hastings61272b72014-01-07 12:41:53 -0800182[clinic start generated code]*/
Larry Hastings2f936352014-08-05 14:04:04 +1000183/*[clinic end generated code: output=da39a3ee5e6b4b0d input=94a0f0f978acae17]*/
Victor Stinnera2f7c002012-02-08 03:36:25 +0100184
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000185#ifndef _MSC_VER
Guido van Rossum36bc6801995-06-14 22:54:23 +0000186
Martin v. Löwis8eb92a02002-09-19 08:03:21 +0000187#if defined(__sgi)&&_COMPILER_VERSION>=700
188/* declare ctermid_r if compiling with MIPSPro 7.x in ANSI C mode
189 (default) */
190extern char *ctermid_r(char *);
191#endif
192
Thomas Wouters1e0c2f42000-07-24 16:06:23 +0000193#ifndef HAVE_UNISTD_H
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000194#if defined(PYCC_VACPP)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000195extern int mkdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000196#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000197#if ( defined(__WATCOMC__) || defined(_MSC_VER) ) && !defined(__QNX__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000198extern int mkdir(const char *);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000199#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000200extern int mkdir(const char *, mode_t);
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000201#endif
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000202#endif
203#if defined(__IBMC__) || defined(__IBMCPP__)
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000204extern int chdir(char *);
205extern int rmdir(char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000206#else
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000207extern int chdir(const char *);
208extern int rmdir(const char *);
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +0000209#endif
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000210extern int chmod(const char *, mode_t);
Christian Heimes4e30a842007-11-30 22:12:06 +0000211/*#ifdef HAVE_FCHMOD
212extern int fchmod(int, mode_t);
213#endif*/
214/*#ifdef HAVE_LCHMOD
215extern int lchmod(const char *, mode_t);
216#endif*/
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000217extern int chown(const char *, uid_t, gid_t);
218extern char *getcwd(char *, int);
219extern char *strerror(int);
220extern int link(const char *, const char *);
221extern int rename(const char *, const char *);
222extern int stat(const char *, struct stat *);
223extern int unlink(const char *);
Guido van Rossumb6775db1994-08-01 11:34:53 +0000224#ifdef HAVE_SYMLINK
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000225extern int symlink(const char *, const char *);
Guido van Rossuma38a5031995-02-17 15:11:36 +0000226#endif /* HAVE_SYMLINK */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000227#ifdef HAVE_LSTAT
Fredrik Lundhff7df9d2000-07-08 22:48:53 +0000228extern int lstat(const char *, struct stat *);
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000229#endif /* HAVE_LSTAT */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000230#endif /* !HAVE_UNISTD_H */
Guido van Rossum36bc6801995-06-14 22:54:23 +0000231
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000232#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +0000233
Guido van Rossumb6775db1994-08-01 11:34:53 +0000234#ifdef HAVE_UTIME_H
235#include <utime.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000236#endif /* HAVE_UTIME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000237
Guido van Rossum14ed0b21994-09-29 09:50:09 +0000238#ifdef HAVE_SYS_UTIME_H
239#include <sys/utime.h>
240#define HAVE_UTIME_H /* pretend we do for the rest of this file */
241#endif /* HAVE_SYS_UTIME_H */
242
Guido van Rossumb6775db1994-08-01 11:34:53 +0000243#ifdef HAVE_SYS_TIMES_H
244#include <sys/times.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000245#endif /* HAVE_SYS_TIMES_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000246
247#ifdef HAVE_SYS_PARAM_H
248#include <sys/param.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000249#endif /* HAVE_SYS_PARAM_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000250
251#ifdef HAVE_SYS_UTSNAME_H
252#include <sys/utsname.h>
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +0000253#endif /* HAVE_SYS_UTSNAME_H */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000254
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000255#ifdef HAVE_DIRENT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000256#include <dirent.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000257#define NAMLEN(dirent) strlen((dirent)->d_name)
258#else
Guido van Rossumc5a0f531997-12-02 20:36:02 +0000259#if defined(__WATCOMC__) && !defined(__QNX__)
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000260#include <direct.h>
261#define NAMLEN(dirent) strlen((dirent)->d_name)
262#else
Guido van Rossumb6775db1994-08-01 11:34:53 +0000263#define dirent direct
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000264#define NAMLEN(dirent) (dirent)->d_namlen
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000265#endif
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000266#ifdef HAVE_SYS_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000267#include <sys/ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000268#endif
269#ifdef HAVE_SYS_DIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000270#include <sys/dir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000271#endif
272#ifdef HAVE_NDIR_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000273#include <ndir.h>
Guido van Rossum3bbc62e1995-01-02 19:30:30 +0000274#endif
275#endif
Guido van Rossumb6775db1994-08-01 11:34:53 +0000276
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000277#ifdef _MSC_VER
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000278#ifdef HAVE_DIRECT_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000279#include <direct.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000280#endif
281#ifdef HAVE_IO_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000282#include <io.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000283#endif
284#ifdef HAVE_PROCESS_H
Guido van Rossumb6775db1994-08-01 11:34:53 +0000285#include <process.h>
Thomas Wouters0e3f5912006-08-11 14:57:12 +0000286#endif
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000287#ifndef VOLUME_NAME_DOS
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000288#define VOLUME_NAME_DOS 0x0
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000289#endif
290#ifndef VOLUME_NAME_NT
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000291#define VOLUME_NAME_NT 0x2
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000292#endif
293#ifndef IO_REPARSE_TAG_SYMLINK
Amaury Forgeot d'Arc844807e2010-08-16 22:16:51 +0000294#define IO_REPARSE_TAG_SYMLINK (0xA000000CL)
Raymond Hettinger0291c9f2010-08-01 21:10:35 +0000295#endif
Tim Golden0321cf22014-05-05 19:46:17 +0100296#ifndef IO_REPARSE_TAG_MOUNT_POINT
297#define IO_REPARSE_TAG_MOUNT_POINT (0xA0000003L)
298#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000299#include "osdefs.h"
Kristján Valur Jónssonf64e6512009-04-13 10:16:14 +0000300#include <malloc.h>
Guido van Rossumb6775db1994-08-01 11:34:53 +0000301#include <windows.h>
Victor Stinner8c62be82010-05-06 00:08:46 +0000302#include <shellapi.h> /* for ShellExecute() */
Brian Curtine8e4b3b2010-09-23 20:04:14 +0000303#include <lmcons.h> /* for UNLEN */
Brian Curtin52173d42010-12-02 18:29:18 +0000304#ifdef SE_CREATE_SYMBOLIC_LINK_NAME /* Available starting with Vista */
305#define HAVE_SYMLINK
Brian Curtin3b4499c2010-12-28 14:31:47 +0000306static int win32_can_symlink = 0;
Brian Curtin52173d42010-12-02 18:29:18 +0000307#endif
Guido van Rossuma4916fa1996-05-23 22:58:55 +0000308#endif /* _MSC_VER */
Guido van Rossumb6775db1994-08-01 11:34:53 +0000309
Tim Petersbc2e10e2002-03-03 23:17:02 +0000310#ifndef MAXPATHLEN
Thomas Wouters477c8d52006-05-27 19:21:47 +0000311#if defined(PATH_MAX) && PATH_MAX > 1024
312#define MAXPATHLEN PATH_MAX
313#else
Tim Petersbc2e10e2002-03-03 23:17:02 +0000314#define MAXPATHLEN 1024
Thomas Wouters477c8d52006-05-27 19:21:47 +0000315#endif
Tim Petersbc2e10e2002-03-03 23:17:02 +0000316#endif /* MAXPATHLEN */
317
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000318#ifdef UNION_WAIT
319/* Emulate some macros on systems that have a union instead of macros */
320
321#ifndef WIFEXITED
322#define WIFEXITED(u_wait) (!(u_wait).w_termsig && !(u_wait).w_coredump)
323#endif
324
325#ifndef WEXITSTATUS
326#define WEXITSTATUS(u_wait) (WIFEXITED(u_wait)?((u_wait).w_retcode):-1)
327#endif
328
329#ifndef WTERMSIG
330#define WTERMSIG(u_wait) ((u_wait).w_termsig)
331#endif
332
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000333#define WAIT_TYPE union wait
334#define WAIT_STATUS_INT(s) (s.w_status)
335
336#else /* !UNION_WAIT */
337#define WAIT_TYPE int
338#define WAIT_STATUS_INT(s) (s)
Guido van Rossum54ecc3d1999-01-27 17:53:11 +0000339#endif /* UNION_WAIT */
340
Greg Wardb48bc172000-03-01 21:51:56 +0000341/* Don't use the "_r" form if we don't need it (also, won't have a
342 prototype for it, at least on Solaris -- maybe others as well?). */
343#if defined(HAVE_CTERMID_R) && defined(WITH_THREAD)
344#define USE_CTERMID_R
345#endif
346
Fred Drake699f3522000-06-29 21:12:41 +0000347/* choose the appropriate stat and fstat functions and return structs */
Guido van Rossum64529cd2000-06-30 22:45:12 +0000348#undef STAT
Antoine Pitroue47e0932011-01-19 15:21:35 +0000349#undef FSTAT
350#undef STRUCT_STAT
Victor Stinner14b9b112013-06-25 00:37:25 +0200351#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +0000352# define STAT win32_stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700353# define LSTAT win32_lstat
Victor Stinnere134a7f2015-03-30 10:09:31 +0200354# define FSTAT _Py_fstat_noraise
Steve Dowerf2f373f2015-02-21 08:44:05 -0800355# define STRUCT_STAT struct _Py_stat_struct
Fred Drake699f3522000-06-29 21:12:41 +0000356#else
Victor Stinner8c62be82010-05-06 00:08:46 +0000357# define STAT stat
Larry Hastings9cf065c2012-06-22 16:30:09 -0700358# define LSTAT lstat
Victor Stinner8c62be82010-05-06 00:08:46 +0000359# define FSTAT fstat
360# define STRUCT_STAT struct stat
Fred Drake699f3522000-06-29 21:12:41 +0000361#endif
362
Tim Peters11b23062003-04-23 02:39:17 +0000363#if defined(MAJOR_IN_MKDEV)
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000364#include <sys/mkdev.h>
365#else
366#if defined(MAJOR_IN_SYSMACROS)
367#include <sys/sysmacros.h>
368#endif
Neal Norwitz3d949422002-04-20 13:46:43 +0000369#if defined(HAVE_MKNOD) && defined(HAVE_SYS_MKDEV_H)
370#include <sys/mkdev.h>
371#endif
Martin v. Löwisdbe3f762002-10-10 14:27:30 +0000372#endif
Fred Drake699f3522000-06-29 21:12:41 +0000373
Victor Stinner6edddfa2013-11-24 19:22:57 +0100374#define DWORD_MAX 4294967295U
375
Serhiy Storchaka06a13f82015-02-22 21:34:54 +0200376#ifdef MS_WINDOWS
Victor Stinner6036e442015-03-08 01:58:04 +0100377#define INITFUNC PyInit_nt
378#define MODNAME "nt"
379#else
380#define INITFUNC PyInit_posix
381#define MODNAME "posix"
382#endif
383
384#ifdef MS_WINDOWS
Serhiy Storchaka06a13f82015-02-22 21:34:54 +0200385/* defined in fileutils.c */
386PyAPI_FUNC(void) _Py_time_t_to_FILE_TIME(time_t, int, FILETIME *);
387PyAPI_FUNC(void) _Py_attribute_data_to_stat(BY_HANDLE_FILE_INFORMATION *,
388 ULONG, struct _Py_stat_struct *);
389#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -0700390
391#ifdef MS_WINDOWS
392static int
393win32_warn_bytes_api()
394{
395 return PyErr_WarnEx(PyExc_DeprecationWarning,
396 "The Windows bytes API has been deprecated, "
397 "use Unicode filenames instead",
398 1);
399}
400#endif
401
402
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200403#ifndef MS_WINDOWS
404PyObject *
405_PyLong_FromUid(uid_t uid)
406{
407 if (uid == (uid_t)-1)
408 return PyLong_FromLong(-1);
409 return PyLong_FromUnsignedLong(uid);
410}
411
412PyObject *
413_PyLong_FromGid(gid_t gid)
414{
415 if (gid == (gid_t)-1)
416 return PyLong_FromLong(-1);
417 return PyLong_FromUnsignedLong(gid);
418}
419
420int
421_Py_Uid_Converter(PyObject *obj, void *p)
422{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700423 uid_t uid;
424 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200425 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200426 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700427 unsigned long uresult;
428
429 index = PyNumber_Index(obj);
430 if (index == NULL) {
431 PyErr_Format(PyExc_TypeError,
432 "uid should be integer, not %.200s",
433 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200434 return 0;
435 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700436
437 /*
438 * Handling uid_t is complicated for two reasons:
439 * * Although uid_t is (always?) unsigned, it still
440 * accepts -1.
441 * * We don't know its size in advance--it may be
442 * bigger than an int, or it may be smaller than
443 * a long.
444 *
445 * So a bit of defensive programming is in order.
446 * Start with interpreting the value passed
447 * in as a signed long and see if it works.
448 */
449
450 result = PyLong_AsLongAndOverflow(index, &overflow);
451
452 if (!overflow) {
453 uid = (uid_t)result;
454
455 if (result == -1) {
456 if (PyErr_Occurred())
457 goto fail;
458 /* It's a legitimate -1, we're done. */
459 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200460 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700461
462 /* Any other negative number is disallowed. */
463 if (result < 0)
464 goto underflow;
465
466 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200467 if (sizeof(uid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700468 (long)uid != result)
469 goto underflow;
470 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200471 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700472
473 if (overflow < 0)
474 goto underflow;
475
476 /*
477 * Okay, the value overflowed a signed long. If it
478 * fits in an *unsigned* long, it may still be okay,
479 * as uid_t may be unsigned long on this platform.
480 */
481 uresult = PyLong_AsUnsignedLong(index);
482 if (PyErr_Occurred()) {
483 if (PyErr_ExceptionMatches(PyExc_OverflowError))
484 goto overflow;
485 goto fail;
486 }
487
488 uid = (uid_t)uresult;
489
490 /*
491 * If uid == (uid_t)-1, the user actually passed in ULONG_MAX,
492 * but this value would get interpreted as (uid_t)-1 by chown
493 * and its siblings. That's not what the user meant! So we
494 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100495 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700496 */
497 if (uid == (uid_t)-1)
498 goto overflow;
499
500 /* Ensure the value wasn't truncated. */
501 if (sizeof(uid_t) < sizeof(long) &&
502 (unsigned long)uid != uresult)
503 goto overflow;
504 /* fallthrough */
505
506success:
507 Py_DECREF(index);
508 *(uid_t *)p = uid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200509 return 1;
510
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700511underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200512 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700513 "uid is less than minimum");
514 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200515
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700516overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200517 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700518 "uid is greater than maximum");
519 /* fallthrough */
520
521fail:
522 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200523 return 0;
524}
525
526int
527_Py_Gid_Converter(PyObject *obj, void *p)
528{
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700529 gid_t gid;
530 PyObject *index;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200531 int overflow;
Serhiy Storchakab4621892013-02-10 23:28:02 +0200532 long result;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700533 unsigned long uresult;
534
535 index = PyNumber_Index(obj);
536 if (index == NULL) {
537 PyErr_Format(PyExc_TypeError,
538 "gid should be integer, not %.200s",
539 Py_TYPE(obj)->tp_name);
Serhiy Storchakab4621892013-02-10 23:28:02 +0200540 return 0;
541 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700542
543 /*
544 * Handling gid_t is complicated for two reasons:
545 * * Although gid_t is (always?) unsigned, it still
546 * accepts -1.
547 * * We don't know its size in advance--it may be
548 * bigger than an int, or it may be smaller than
549 * a long.
550 *
551 * So a bit of defensive programming is in order.
552 * Start with interpreting the value passed
553 * in as a signed long and see if it works.
554 */
555
556 result = PyLong_AsLongAndOverflow(index, &overflow);
557
558 if (!overflow) {
559 gid = (gid_t)result;
560
561 if (result == -1) {
562 if (PyErr_Occurred())
563 goto fail;
564 /* It's a legitimate -1, we're done. */
565 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200566 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700567
568 /* Any other negative number is disallowed. */
569 if (result < 0) {
570 goto underflow;
571 }
572
573 /* Ensure the value wasn't truncated. */
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200574 if (sizeof(gid_t) < sizeof(long) &&
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700575 (long)gid != result)
576 goto underflow;
577 goto success;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200578 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700579
580 if (overflow < 0)
581 goto underflow;
582
583 /*
584 * Okay, the value overflowed a signed long. If it
585 * fits in an *unsigned* long, it may still be okay,
586 * as gid_t may be unsigned long on this platform.
587 */
588 uresult = PyLong_AsUnsignedLong(index);
589 if (PyErr_Occurred()) {
590 if (PyErr_ExceptionMatches(PyExc_OverflowError))
591 goto overflow;
592 goto fail;
593 }
594
595 gid = (gid_t)uresult;
596
597 /*
598 * If gid == (gid_t)-1, the user actually passed in ULONG_MAX,
599 * but this value would get interpreted as (gid_t)-1 by chown
600 * and its siblings. That's not what the user meant! So we
601 * throw an overflow exception instead. (We already
Tim Golden23005082013-10-25 11:22:37 +0100602 * handled a real -1 with PyLong_AsLongAndOverflow() above.)
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700603 */
604 if (gid == (gid_t)-1)
605 goto overflow;
606
607 /* Ensure the value wasn't truncated. */
608 if (sizeof(gid_t) < sizeof(long) &&
609 (unsigned long)gid != uresult)
610 goto overflow;
611 /* fallthrough */
612
613success:
614 Py_DECREF(index);
615 *(gid_t *)p = gid;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200616 return 1;
617
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700618underflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200619 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700620 "gid is less than minimum");
621 goto fail;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200622
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700623overflow:
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200624 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700625 "gid is greater than maximum");
626 /* fallthrough */
627
628fail:
629 Py_DECREF(index);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200630 return 0;
631}
632#endif /* MS_WINDOWS */
633
634
Gregory P. Smith702dada2015-01-28 16:07:52 -0800635#ifdef HAVE_LONG_LONG
636# define _PyLong_FromDev PyLong_FromLongLong
637#else
638# define _PyLong_FromDev PyLong_FromLong
639#endif
640
641
Serhiy Storchakab2653b32015-01-18 11:12:11 +0200642#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
643static int
644_Py_Dev_Converter(PyObject *obj, void *p)
645{
646#ifdef HAVE_LONG_LONG
647 *((dev_t *)p) = PyLong_AsUnsignedLongLong(obj);
648#else
649 *((dev_t *)p) = PyLong_AsUnsignedLong(obj);
650#endif
651 if (PyErr_Occurred())
652 return 0;
653 return 1;
654}
Gregory P. Smith702dada2015-01-28 16:07:52 -0800655#endif /* HAVE_MKNOD && HAVE_MAKEDEV */
Serhiy Storchakab2653b32015-01-18 11:12:11 +0200656
657
Larry Hastings9cf065c2012-06-22 16:30:09 -0700658#ifdef AT_FDCWD
Trent Nelson9a461052012-09-18 21:50:06 -0400659/*
660 * Why the (int) cast? Solaris 10 defines AT_FDCWD as 0xffd19553 (-3041965);
661 * without the int cast, the value gets interpreted as uint (4291925331),
662 * which doesn't play nicely with all the initializer lines in this file that
663 * look like this:
664 * int dir_fd = DEFAULT_DIR_FD;
665 */
666#define DEFAULT_DIR_FD (int)AT_FDCWD
Larry Hastings9cf065c2012-06-22 16:30:09 -0700667#else
668#define DEFAULT_DIR_FD (-100)
669#endif
670
671static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200672_fd_converter(PyObject *o, int *p, const char *allowed)
673{
674 int overflow;
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700675 long long_value;
676
677 PyObject *index = PyNumber_Index(o);
678 if (index == NULL) {
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200679 PyErr_Format(PyExc_TypeError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700680 "argument should be %s, not %.200s",
681 allowed, Py_TYPE(o)->tp_name);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700682 return 0;
683 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700684
685 long_value = PyLong_AsLongAndOverflow(index, &overflow);
686 Py_DECREF(index);
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200687 if (overflow > 0 || long_value > INT_MAX) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700688 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700689 "fd is greater than maximum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700690 return 0;
691 }
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200692 if (overflow < 0 || long_value < INT_MIN) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700693 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700694 "fd is less than minimum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700695 return 0;
696 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700697
Larry Hastings9cf065c2012-06-22 16:30:09 -0700698 *p = (int)long_value;
699 return 1;
700}
701
702static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200703dir_fd_converter(PyObject *o, void *p)
704{
705 if (o == Py_None) {
706 *(int *)p = DEFAULT_DIR_FD;
707 return 1;
708 }
709 return _fd_converter(o, (int *)p, "integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700710}
711
712
Larry Hastings9cf065c2012-06-22 16:30:09 -0700713/*
714 * A PyArg_ParseTuple "converter" function
715 * that handles filesystem paths in the manner
716 * preferred by the os module.
717 *
718 * path_converter accepts (Unicode) strings and their
719 * subclasses, and bytes and their subclasses. What
720 * it does with the argument depends on the platform:
721 *
722 * * On Windows, if we get a (Unicode) string we
723 * extract the wchar_t * and return it; if we get
724 * bytes we extract the char * and return that.
725 *
726 * * On all other platforms, strings are encoded
727 * to bytes using PyUnicode_FSConverter, then we
728 * extract the char * from the bytes object and
729 * return that.
730 *
731 * path_converter also optionally accepts signed
732 * integers (representing open file descriptors) instead
733 * of path strings.
734 *
735 * Input fields:
736 * path.nullable
737 * If nonzero, the path is permitted to be None.
738 * path.allow_fd
739 * If nonzero, the path is permitted to be a file handle
740 * (a signed int) instead of a string.
741 * path.function_name
742 * If non-NULL, path_converter will use that as the name
743 * of the function in error messages.
Larry Hastings31826802013-10-19 00:09:25 -0700744 * (If path.function_name is NULL it omits the function name.)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700745 * path.argument_name
746 * If non-NULL, path_converter will use that as the name
747 * of the parameter in error messages.
748 * (If path.argument_name is NULL it uses "path".)
749 *
750 * Output fields:
751 * path.wide
752 * Points to the path if it was expressed as Unicode
753 * and was not encoded. (Only used on Windows.)
754 * path.narrow
755 * Points to the path if it was expressed as bytes,
756 * or it was Unicode and was encoded to bytes.
757 * path.fd
758 * Contains a file descriptor if path.accept_fd was true
759 * and the caller provided a signed integer instead of any
760 * sort of string.
761 *
762 * WARNING: if your "path" parameter is optional, and is
763 * unspecified, path_converter will never get called.
764 * So if you set allow_fd, you *MUST* initialize path.fd = -1
765 * yourself!
766 * path.length
767 * The length of the path in characters, if specified as
768 * a string.
769 * path.object
770 * The original object passed in.
771 * path.cleanup
772 * For internal use only. May point to a temporary object.
773 * (Pay no attention to the man behind the curtain.)
774 *
775 * At most one of path.wide or path.narrow will be non-NULL.
776 * If path was None and path.nullable was set,
777 * or if path was an integer and path.allow_fd was set,
778 * both path.wide and path.narrow will be NULL
779 * and path.length will be 0.
Georg Brandlf7875592012-06-24 13:58:31 +0200780 *
Larry Hastings9cf065c2012-06-22 16:30:09 -0700781 * path_converter takes care to not write to the path_t
782 * unless it's successful. However it must reset the
783 * "cleanup" field each time it's called.
784 *
785 * Use as follows:
786 * path_t path;
787 * memset(&path, 0, sizeof(path));
788 * PyArg_ParseTuple(args, "O&", path_converter, &path);
789 * // ... use values from path ...
790 * path_cleanup(&path);
791 *
792 * (Note that if PyArg_Parse fails you don't need to call
793 * path_cleanup(). However it is safe to do so.)
794 */
795typedef struct {
Victor Stinner292c8352012-10-30 02:17:38 +0100796 const char *function_name;
797 const char *argument_name;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700798 int nullable;
799 int allow_fd;
800 wchar_t *wide;
801 char *narrow;
802 int fd;
803 Py_ssize_t length;
804 PyObject *object;
805 PyObject *cleanup;
806} path_t;
807
Larry Hastings2f936352014-08-05 14:04:04 +1000808#define PATH_T_INITIALIZE(function_name, argument_name, nullable, allow_fd) \
809 {function_name, argument_name, nullable, allow_fd, NULL, NULL, -1, 0, NULL, NULL}
Larry Hastings31826802013-10-19 00:09:25 -0700810
Larry Hastings9cf065c2012-06-22 16:30:09 -0700811static void
812path_cleanup(path_t *path) {
813 if (path->cleanup) {
Serhiy Storchaka505ff752014-02-09 13:33:53 +0200814 Py_CLEAR(path->cleanup);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700815 }
816}
817
818static int
819path_converter(PyObject *o, void *p) {
820 path_t *path = (path_t *)p;
821 PyObject *unicode, *bytes;
822 Py_ssize_t length;
823 char *narrow;
824
825#define FORMAT_EXCEPTION(exc, fmt) \
826 PyErr_Format(exc, "%s%s" fmt, \
827 path->function_name ? path->function_name : "", \
828 path->function_name ? ": " : "", \
829 path->argument_name ? path->argument_name : "path")
830
831 /* Py_CLEANUP_SUPPORTED support */
832 if (o == NULL) {
833 path_cleanup(path);
834 return 1;
835 }
836
837 /* ensure it's always safe to call path_cleanup() */
838 path->cleanup = NULL;
839
840 if (o == Py_None) {
841 if (!path->nullable) {
842 FORMAT_EXCEPTION(PyExc_TypeError,
843 "can't specify None for %s argument");
844 return 0;
845 }
846 path->wide = NULL;
847 path->narrow = NULL;
848 path->length = 0;
849 path->object = o;
850 path->fd = -1;
851 return 1;
852 }
853
854 unicode = PyUnicode_FromObject(o);
855 if (unicode) {
856#ifdef MS_WINDOWS
857 wchar_t *wide;
Victor Stinner59799a82013-11-13 14:17:30 +0100858
859 wide = PyUnicode_AsUnicodeAndSize(unicode, &length);
860 if (!wide) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700861 Py_DECREF(unicode);
862 return 0;
863 }
Victor Stinner59799a82013-11-13 14:17:30 +0100864 if (length > 32767) {
865 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700866 Py_DECREF(unicode);
867 return 0;
868 }
869
870 path->wide = wide;
871 path->narrow = NULL;
872 path->length = length;
873 path->object = o;
874 path->fd = -1;
875 path->cleanup = unicode;
876 return Py_CLEANUP_SUPPORTED;
877#else
878 int converted = PyUnicode_FSConverter(unicode, &bytes);
879 Py_DECREF(unicode);
880 if (!converted)
881 bytes = NULL;
882#endif
883 }
884 else {
885 PyErr_Clear();
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200886 if (PyObject_CheckBuffer(o))
887 bytes = PyBytes_FromObject(o);
888 else
889 bytes = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700890 if (!bytes) {
891 PyErr_Clear();
892 if (path->allow_fd) {
893 int fd;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200894 int result = _fd_converter(o, &fd,
895 "string, bytes or integer");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700896 if (result) {
897 path->wide = NULL;
898 path->narrow = NULL;
899 path->length = 0;
900 path->object = o;
901 path->fd = fd;
902 return result;
903 }
904 }
905 }
906 }
907
908 if (!bytes) {
909 if (!PyErr_Occurred())
910 FORMAT_EXCEPTION(PyExc_TypeError, "illegal type for %s parameter");
911 return 0;
912 }
913
914#ifdef MS_WINDOWS
915 if (win32_warn_bytes_api()) {
916 Py_DECREF(bytes);
917 return 0;
918 }
919#endif
920
921 length = PyBytes_GET_SIZE(bytes);
922#ifdef MS_WINDOWS
Victor Stinner75875072013-11-24 19:23:25 +0100923 if (length > MAX_PATH-1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700924 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
925 Py_DECREF(bytes);
926 return 0;
927 }
928#endif
929
930 narrow = PyBytes_AS_STRING(bytes);
Victor Stinner706768c2014-08-16 01:03:39 +0200931 if ((size_t)length != strlen(narrow)) {
Serhiy Storchakad8a14472014-09-06 20:07:17 +0300932 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700933 Py_DECREF(bytes);
934 return 0;
935 }
936
937 path->wide = NULL;
938 path->narrow = narrow;
939 path->length = length;
940 path->object = o;
941 path->fd = -1;
942 path->cleanup = bytes;
943 return Py_CLEANUP_SUPPORTED;
944}
945
946static void
947argument_unavailable_error(char *function_name, char *argument_name) {
948 PyErr_Format(PyExc_NotImplementedError,
949 "%s%s%s unavailable on this platform",
950 (function_name != NULL) ? function_name : "",
951 (function_name != NULL) ? ": ": "",
952 argument_name);
953}
954
955static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200956dir_fd_unavailable(PyObject *o, void *p)
957{
958 int dir_fd;
959 if (!dir_fd_converter(o, &dir_fd))
Larry Hastings9cf065c2012-06-22 16:30:09 -0700960 return 0;
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200961 if (dir_fd != DEFAULT_DIR_FD) {
962 argument_unavailable_error(NULL, "dir_fd");
963 return 0;
964 }
965 *(int *)p = dir_fd;
966 return 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700967}
968
969static int
970fd_specified(char *function_name, int fd) {
971 if (fd == -1)
972 return 0;
973
974 argument_unavailable_error(function_name, "fd");
975 return 1;
976}
977
978static int
979follow_symlinks_specified(char *function_name, int follow_symlinks) {
980 if (follow_symlinks)
981 return 0;
982
983 argument_unavailable_error(function_name, "follow_symlinks");
984 return 1;
985}
986
987static int
988path_and_dir_fd_invalid(char *function_name, path_t *path, int dir_fd) {
989 if (!path->narrow && !path->wide && (dir_fd != DEFAULT_DIR_FD)) {
990 PyErr_Format(PyExc_ValueError,
991 "%s: can't specify dir_fd without matching path",
992 function_name);
993 return 1;
994 }
995 return 0;
996}
997
998static int
999dir_fd_and_fd_invalid(char *function_name, int dir_fd, int fd) {
1000 if ((dir_fd != DEFAULT_DIR_FD) && (fd != -1)) {
1001 PyErr_Format(PyExc_ValueError,
1002 "%s: can't specify both dir_fd and fd",
1003 function_name);
1004 return 1;
1005 }
1006 return 0;
1007}
1008
1009static int
1010fd_and_follow_symlinks_invalid(char *function_name, int fd,
1011 int follow_symlinks) {
1012 if ((fd > 0) && (!follow_symlinks)) {
1013 PyErr_Format(PyExc_ValueError,
1014 "%s: cannot use fd and follow_symlinks together",
1015 function_name);
1016 return 1;
1017 }
1018 return 0;
1019}
1020
1021static int
1022dir_fd_and_follow_symlinks_invalid(char *function_name, int dir_fd,
1023 int follow_symlinks) {
1024 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
1025 PyErr_Format(PyExc_ValueError,
1026 "%s: cannot use dir_fd and follow_symlinks together",
1027 function_name);
1028 return 1;
1029 }
1030 return 0;
1031}
1032
Larry Hastings2f936352014-08-05 14:04:04 +10001033#ifdef MS_WINDOWS
1034 typedef PY_LONG_LONG Py_off_t;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001035#else
Larry Hastings2f936352014-08-05 14:04:04 +10001036 typedef off_t Py_off_t;
1037#endif
1038
1039static int
1040Py_off_t_converter(PyObject *arg, void *addr)
1041{
1042#ifdef HAVE_LARGEFILE_SUPPORT
1043 *((Py_off_t *)addr) = PyLong_AsLongLong(arg);
1044#else
1045 *((Py_off_t *)addr) = PyLong_AsLong(arg);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001046#endif
1047 if (PyErr_Occurred())
1048 return 0;
1049 return 1;
1050}
Larry Hastings2f936352014-08-05 14:04:04 +10001051
1052static PyObject *
1053PyLong_FromPy_off_t(Py_off_t offset)
1054{
1055#ifdef HAVE_LARGEFILE_SUPPORT
1056 return PyLong_FromLongLong(offset);
1057#else
1058 return PyLong_FromLong(offset);
Ross Lagerwallb1e5d592011-09-19 08:30:43 +02001059#endif
Larry Hastings2f936352014-08-05 14:04:04 +10001060}
1061
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001062
Steve Dowerd81431f2015-03-06 14:47:02 -08001063#if defined _MSC_VER && _MSC_VER >= 1400 && _MSC_VER < 1900
1064/* Legacy implementation of _PyVerify_fd_dup2 while transitioning to
1065 * MSVC 14.0. This should eventually be removed. (issue23524)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001066 */
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001067#define IOINFO_L2E 5
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001068#define IOINFO_ARRAYS 64
Steve Dower65e4cb12014-11-22 12:54:57 -08001069#define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001070#define _NHANDLE_ (IOINFO_ARRAYS * IOINFO_ARRAY_ELTS)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001071#define _NO_CONSOLE_FILENO (intptr_t)-2
1072
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001073/* the special case of checking dup2. The target fd must be in a sensible range */
1074static int
1075_PyVerify_fd_dup2(int fd1, int fd2)
1076{
Victor Stinner8c62be82010-05-06 00:08:46 +00001077 if (!_PyVerify_fd(fd1))
1078 return 0;
1079 if (fd2 == _NO_CONSOLE_FILENO)
1080 return 0;
1081 if ((unsigned)fd2 < _NHANDLE_)
1082 return 1;
1083 else
1084 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001085}
1086#else
Steve Dowerd81431f2015-03-06 14:47:02 -08001087#define _PyVerify_fd_dup2(fd1, fd2) (_PyVerify_fd(fd1) && (fd2) >= 0)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001088#endif
1089
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001090#ifdef MS_WINDOWS
Brian Curtinf5e76d02010-11-24 13:14:05 +00001091
1092static int
Brian Curtind25aef52011-06-13 15:16:04 -05001093win32_get_reparse_tag(HANDLE reparse_point_handle, ULONG *reparse_tag)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001094{
1095 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
1096 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
1097 DWORD n_bytes_returned;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001098
1099 if (0 == DeviceIoControl(
1100 reparse_point_handle,
1101 FSCTL_GET_REPARSE_POINT,
1102 NULL, 0, /* in buffer */
1103 target_buffer, sizeof(target_buffer),
1104 &n_bytes_returned,
1105 NULL)) /* we're not using OVERLAPPED_IO */
Brian Curtind25aef52011-06-13 15:16:04 -05001106 return FALSE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001107
1108 if (reparse_tag)
1109 *reparse_tag = rdb->ReparseTag;
1110
Brian Curtind25aef52011-06-13 15:16:04 -05001111 return TRUE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001112}
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001113
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001114#endif /* MS_WINDOWS */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001115
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001116/* Return a dictionary corresponding to the POSIX environment table */
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001117#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Jack Jansenea0c3822002-08-01 21:57:49 +00001118/* On Darwin/MacOSX a shared library or framework has no access to
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001119** environ directly, we must obtain it with _NSGetEnviron(). See also
1120** man environ(7).
Jack Jansenea0c3822002-08-01 21:57:49 +00001121*/
1122#include <crt_externs.h>
1123static char **environ;
1124#elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001125extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001126#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001127
Barry Warsaw53699e91996-12-10 23:23:01 +00001128static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001129convertenviron(void)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001130{
Victor Stinner8c62be82010-05-06 00:08:46 +00001131 PyObject *d;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001132#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00001133 wchar_t **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001134#else
Victor Stinner8c62be82010-05-06 00:08:46 +00001135 char **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001136#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00001137
Victor Stinner8c62be82010-05-06 00:08:46 +00001138 d = PyDict_New();
1139 if (d == NULL)
1140 return NULL;
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001141#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Victor Stinner8c62be82010-05-06 00:08:46 +00001142 if (environ == NULL)
1143 environ = *_NSGetEnviron();
1144#endif
1145#ifdef MS_WINDOWS
1146 /* _wenviron must be initialized in this way if the program is started
1147 through main() instead of wmain(). */
1148 _wgetenv(L"");
1149 if (_wenviron == NULL)
1150 return d;
1151 /* This part ignores errors */
1152 for (e = _wenviron; *e != NULL; e++) {
1153 PyObject *k;
1154 PyObject *v;
1155 wchar_t *p = wcschr(*e, L'=');
1156 if (p == NULL)
1157 continue;
1158 k = PyUnicode_FromWideChar(*e, (Py_ssize_t)(p-*e));
1159 if (k == NULL) {
1160 PyErr_Clear();
1161 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001162 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001163 v = PyUnicode_FromWideChar(p+1, wcslen(p+1));
1164 if (v == NULL) {
1165 PyErr_Clear();
1166 Py_DECREF(k);
1167 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001168 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001169 if (PyDict_GetItem(d, k) == NULL) {
1170 if (PyDict_SetItem(d, k, v) != 0)
1171 PyErr_Clear();
1172 }
1173 Py_DECREF(k);
1174 Py_DECREF(v);
1175 }
1176#else
1177 if (environ == NULL)
1178 return d;
1179 /* This part ignores errors */
1180 for (e = environ; *e != NULL; e++) {
1181 PyObject *k;
1182 PyObject *v;
1183 char *p = strchr(*e, '=');
1184 if (p == NULL)
1185 continue;
Victor Stinner84ae1182010-05-06 22:05:07 +00001186 k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
Victor Stinner8c62be82010-05-06 00:08:46 +00001187 if (k == NULL) {
1188 PyErr_Clear();
1189 continue;
1190 }
Victor Stinner84ae1182010-05-06 22:05:07 +00001191 v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
Victor Stinner8c62be82010-05-06 00:08:46 +00001192 if (v == NULL) {
1193 PyErr_Clear();
1194 Py_DECREF(k);
1195 continue;
1196 }
1197 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);
Guido van Rossumd48f2521997-12-05 22:19:34 +00001203 }
1204#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001205 return d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001206}
1207
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001208/* Set a POSIX-specific error from errno, and return NULL */
1209
Barry Warsawd58d7641998-07-23 16:14:40 +00001210static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001211posix_error(void)
Guido van Rossumad0ee831995-03-01 10:34:45 +00001212{
Victor Stinner8c62be82010-05-06 00:08:46 +00001213 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001214}
Mark Hammondef8b6542001-05-13 08:04:26 +00001215
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00001216#ifdef MS_WINDOWS
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001217static PyObject *
Brian Curtind40e6f72010-07-08 21:39:08 +00001218win32_error(char* function, const char* filename)
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001219{
Victor Stinner8c62be82010-05-06 00:08:46 +00001220 /* XXX We should pass the function name along in the future.
1221 (winreg.c also wants to pass the function name.)
1222 This would however require an additional param to the
1223 Windows error object, which is non-trivial.
1224 */
1225 errno = GetLastError();
1226 if (filename)
1227 return PyErr_SetFromWindowsErrWithFilename(errno, filename);
1228 else
1229 return PyErr_SetFromWindowsErr(errno);
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001230}
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001231
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001232static PyObject *
Victor Stinnereb5657a2011-09-30 01:44:27 +02001233win32_error_object(char* function, PyObject* filename)
1234{
1235 /* XXX - see win32_error for comments on 'function' */
1236 errno = GetLastError();
1237 if (filename)
1238 return PyErr_SetExcFromWindowsErrWithFilenameObject(
Andrew Svetlov2606a6f2012-12-19 14:33:35 +02001239 PyExc_OSError,
Victor Stinnereb5657a2011-09-30 01:44:27 +02001240 errno,
1241 filename);
1242 else
1243 return PyErr_SetFromWindowsErr(errno);
1244}
1245
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001246#endif /* MS_WINDOWS */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001247
Larry Hastings9cf065c2012-06-22 16:30:09 -07001248static PyObject *
Victor Stinner292c8352012-10-30 02:17:38 +01001249path_error(path_t *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001250{
1251#ifdef MS_WINDOWS
Victor Stinner292c8352012-10-30 02:17:38 +01001252 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
1253 0, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001254#else
Victor Stinner292c8352012-10-30 02:17:38 +01001255 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001256#endif
1257}
1258
Larry Hastings31826802013-10-19 00:09:25 -07001259
Larry Hastingsb0827312014-02-09 22:05:19 -08001260static PyObject *
1261path_error2(path_t *path, path_t *path2)
1262{
1263#ifdef MS_WINDOWS
1264 return PyErr_SetExcFromWindowsErrWithFilenameObjects(PyExc_OSError,
1265 0, path->object, path2->object);
1266#else
1267 return PyErr_SetFromErrnoWithFilenameObjects(PyExc_OSError,
1268 path->object, path2->object);
1269#endif
1270}
1271
1272
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001273/* POSIX generic methods */
1274
Larry Hastings2f936352014-08-05 14:04:04 +10001275static int
1276fildes_converter(PyObject *o, void *p)
Fred Drake4d1e64b2002-04-15 19:40:07 +00001277{
Victor Stinner8c62be82010-05-06 00:08:46 +00001278 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +10001279 int *pointer = (int *)p;
1280 fd = PyObject_AsFileDescriptor(o);
Victor Stinner8c62be82010-05-06 00:08:46 +00001281 if (fd < 0)
Larry Hastings2f936352014-08-05 14:04:04 +10001282 return 0;
Larry Hastings2f936352014-08-05 14:04:04 +10001283 *pointer = fd;
1284 return 1;
1285}
1286
1287static PyObject *
1288posix_fildes_fd(int fd, int (*func)(int))
1289{
1290 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001291 int async_err = 0;
1292
Steve Dower8fc89802015-04-12 00:26:27 -04001293 if (!_PyVerify_fd(fd))
1294 return posix_error();
1295
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001296 do {
1297 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04001298 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001299 res = (*func)(fd);
Steve Dower8fc89802015-04-12 00:26:27 -04001300 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001301 Py_END_ALLOW_THREADS
1302 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
1303 if (res != 0)
1304 return (!async_err) ? posix_error() : NULL;
1305 Py_RETURN_NONE;
Fred Drake4d1e64b2002-04-15 19:40:07 +00001306}
Guido van Rossum21142a01999-01-08 21:05:37 +00001307
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001308
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001309#ifdef MS_WINDOWS
Thomas Wouters477c8d52006-05-27 19:21:47 +00001310/* This is a reimplementation of the C library's chdir function,
1311 but one that produces Win32 errors instead of DOS error codes.
1312 chdir is essentially a wrapper around SetCurrentDirectory; however,
1313 it also needs to set "magic" environment variables indicating
1314 the per-drive current directory, which are of the form =<drive>: */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001315static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001316win32_chdir(LPCSTR path)
1317{
Victor Stinner75875072013-11-24 19:23:25 +01001318 char new_path[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00001319 int result;
1320 char env[4] = "=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001321
Victor Stinner8c62be82010-05-06 00:08:46 +00001322 if(!SetCurrentDirectoryA(path))
1323 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001324 result = GetCurrentDirectoryA(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001325 if (!result)
1326 return FALSE;
1327 /* In the ANSI API, there should not be any paths longer
Victor Stinner75875072013-11-24 19:23:25 +01001328 than MAX_PATH-1 (not including the final null character). */
1329 assert(result < Py_ARRAY_LENGTH(new_path));
Victor Stinner8c62be82010-05-06 00:08:46 +00001330 if (strncmp(new_path, "\\\\", 2) == 0 ||
1331 strncmp(new_path, "//", 2) == 0)
1332 /* UNC path, nothing to do. */
1333 return TRUE;
1334 env[1] = new_path[0];
1335 return SetEnvironmentVariableA(env, new_path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001336}
1337
1338/* The Unicode version differs from the ANSI version
1339 since the current directory might exceed MAX_PATH characters */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001340static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001341win32_wchdir(LPCWSTR path)
1342{
Victor Stinner75875072013-11-24 19:23:25 +01001343 wchar_t _new_path[MAX_PATH], *new_path = _new_path;
Victor Stinner8c62be82010-05-06 00:08:46 +00001344 int result;
1345 wchar_t env[4] = L"=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001346
Victor Stinner8c62be82010-05-06 00:08:46 +00001347 if(!SetCurrentDirectoryW(path))
1348 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001349 result = GetCurrentDirectoryW(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001350 if (!result)
1351 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001352 if (result > Py_ARRAY_LENGTH(new_path)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001353 new_path = PyMem_RawMalloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00001354 if (!new_path) {
1355 SetLastError(ERROR_OUTOFMEMORY);
1356 return FALSE;
1357 }
1358 result = GetCurrentDirectoryW(result, new_path);
1359 if (!result) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001360 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001361 return FALSE;
1362 }
1363 }
1364 if (wcsncmp(new_path, L"\\\\", 2) == 0 ||
1365 wcsncmp(new_path, L"//", 2) == 0)
1366 /* UNC path, nothing to do. */
1367 return TRUE;
1368 env[1] = new_path[0];
1369 result = SetEnvironmentVariableW(env, new_path);
1370 if (new_path != _new_path)
Victor Stinnerb6404912013-07-07 16:21:41 +02001371 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001372 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001373}
1374#endif
1375
Martin v. Löwis14694662006-02-03 12:54:16 +00001376#ifdef MS_WINDOWS
1377/* The CRT of Windows has a number of flaws wrt. its stat() implementation:
1378 - time stamps are restricted to second resolution
1379 - file modification times suffer from forth-and-back conversions between
1380 UTC and local time
1381 Therefore, we implement our own stat, based on the Win32 API directly.
1382*/
Victor Stinner8c62be82010-05-06 00:08:46 +00001383#define HAVE_STAT_NSEC 1
Zachary Ware63f277b2014-06-19 09:46:37 -05001384#define HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES 1
Martin v. Löwis14694662006-02-03 12:54:16 +00001385
Guido van Rossumd8faa362007-04-27 19:54:29 +00001386static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001387attributes_from_dir(LPCSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001388{
Victor Stinner8c62be82010-05-06 00:08:46 +00001389 HANDLE hFindFile;
1390 WIN32_FIND_DATAA FileData;
1391 hFindFile = FindFirstFileA(pszFile, &FileData);
1392 if (hFindFile == INVALID_HANDLE_VALUE)
1393 return FALSE;
1394 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001395 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001396 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001397 info->dwFileAttributes = FileData.dwFileAttributes;
1398 info->ftCreationTime = FileData.ftCreationTime;
1399 info->ftLastAccessTime = FileData.ftLastAccessTime;
1400 info->ftLastWriteTime = FileData.ftLastWriteTime;
1401 info->nFileSizeHigh = FileData.nFileSizeHigh;
1402 info->nFileSizeLow = FileData.nFileSizeLow;
1403/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001404 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1405 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001406 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001407}
1408
Victor Stinner6036e442015-03-08 01:58:04 +01001409static void
1410find_data_to_file_info_w(WIN32_FIND_DATAW *pFileData,
1411 BY_HANDLE_FILE_INFORMATION *info,
1412 ULONG *reparse_tag)
1413{
1414 memset(info, 0, sizeof(*info));
1415 info->dwFileAttributes = pFileData->dwFileAttributes;
1416 info->ftCreationTime = pFileData->ftCreationTime;
1417 info->ftLastAccessTime = pFileData->ftLastAccessTime;
1418 info->ftLastWriteTime = pFileData->ftLastWriteTime;
1419 info->nFileSizeHigh = pFileData->nFileSizeHigh;
1420 info->nFileSizeLow = pFileData->nFileSizeLow;
1421/* info->nNumberOfLinks = 1; */
1422 if (pFileData->dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1423 *reparse_tag = pFileData->dwReserved0;
1424 else
1425 *reparse_tag = 0;
1426}
1427
Guido van Rossumd8faa362007-04-27 19:54:29 +00001428static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001429attributes_from_dir_w(LPCWSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001430{
Victor Stinner8c62be82010-05-06 00:08:46 +00001431 HANDLE hFindFile;
1432 WIN32_FIND_DATAW FileData;
1433 hFindFile = FindFirstFileW(pszFile, &FileData);
1434 if (hFindFile == INVALID_HANDLE_VALUE)
1435 return FALSE;
1436 FindClose(hFindFile);
Victor Stinner6036e442015-03-08 01:58:04 +01001437 find_data_to_file_info_w(&FileData, info, reparse_tag);
Victor Stinner8c62be82010-05-06 00:08:46 +00001438 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001439}
1440
Brian Curtind25aef52011-06-13 15:16:04 -05001441static BOOL
1442get_target_path(HANDLE hdl, wchar_t **target_path)
1443{
1444 int buf_size, result_length;
1445 wchar_t *buf;
1446
1447 /* We have a good handle to the target, use it to determine
1448 the target path name (then we'll call lstat on it). */
Steve Dower2ea51c92015-03-20 21:49:12 -07001449 buf_size = GetFinalPathNameByHandleW(hdl, 0, 0,
1450 VOLUME_NAME_DOS);
Brian Curtind25aef52011-06-13 15:16:04 -05001451 if(!buf_size)
1452 return FALSE;
1453
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02001454 buf = PyMem_New(wchar_t, buf_size+1);
Brian Curtinc8be8402011-06-14 09:52:50 -05001455 if (!buf) {
1456 SetLastError(ERROR_OUTOFMEMORY);
1457 return FALSE;
1458 }
1459
Steve Dower2ea51c92015-03-20 21:49:12 -07001460 result_length = GetFinalPathNameByHandleW(hdl,
Brian Curtind25aef52011-06-13 15:16:04 -05001461 buf, buf_size, VOLUME_NAME_DOS);
1462
1463 if(!result_length) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001464 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001465 return FALSE;
1466 }
1467
1468 if(!CloseHandle(hdl)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001469 PyMem_Free(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001470 return FALSE;
1471 }
1472
1473 buf[result_length] = 0;
1474
1475 *target_path = buf;
1476 return TRUE;
1477}
1478
1479static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001480win32_xstat_impl_w(const wchar_t *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001481 BOOL traverse);
1482static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001483win32_xstat_impl(const char *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001484 BOOL traverse)
1485{
Victor Stinner26de69d2011-06-17 15:15:38 +02001486 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001487 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001488 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001489 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001490 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001491 const char *dot;
1492
1493 hFile = CreateFileA(
1494 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001495 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001496 0, /* share mode */
1497 NULL, /* security attributes */
1498 OPEN_EXISTING,
1499 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001500 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1501 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001502 the symlink path again and not the actual final path. */
Brian Curtind25aef52011-06-13 15:16:04 -05001503 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
1504 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001505 NULL);
1506
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001507 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001508 /* Either the target doesn't exist, or we don't have access to
1509 get a handle to it. If the former, we need to return an error.
1510 If the latter, we can use attributes_from_dir. */
1511 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001512 return -1;
1513 /* Could not get attributes on open file. Fall back to
1514 reading the directory. */
1515 if (!attributes_from_dir(path, &info, &reparse_tag))
1516 /* Very strange. This should not fail now */
1517 return -1;
1518 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1519 if (traverse) {
1520 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001521 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001522 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001523 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001524 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001525 } else {
1526 if (!GetFileInformationByHandle(hFile, &info)) {
1527 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001528 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001529 }
1530 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001531 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1532 return -1;
1533
1534 /* Close the outer open file handle now that we're about to
1535 reopen it with different flags. */
1536 if (!CloseHandle(hFile))
1537 return -1;
1538
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001539 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001540 /* In order to call GetFinalPathNameByHandle we need to open
1541 the file without the reparse handling flag set. */
1542 hFile2 = CreateFileA(
1543 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1544 NULL, OPEN_EXISTING,
1545 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1546 NULL);
1547 if (hFile2 == INVALID_HANDLE_VALUE)
1548 return -1;
1549
1550 if (!get_target_path(hFile2, &target_path))
1551 return -1;
1552
1553 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001554 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001555 return code;
1556 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001557 } else
1558 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001559 }
Steve Dowera2af1a52015-02-21 10:04:10 -08001560 _Py_attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001561
1562 /* Set S_IEXEC if it is an .exe, .bat, ... */
1563 dot = strrchr(path, '.');
1564 if (dot) {
1565 if (stricmp(dot, ".bat") == 0 || stricmp(dot, ".cmd") == 0 ||
1566 stricmp(dot, ".exe") == 0 || stricmp(dot, ".com") == 0)
1567 result->st_mode |= 0111;
1568 }
1569 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001570}
1571
1572static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001573win32_xstat_impl_w(const wchar_t *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001574 BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001575{
1576 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001577 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001578 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001579 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001580 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001581 const wchar_t *dot;
1582
1583 hFile = CreateFileW(
1584 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001585 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001586 0, /* share mode */
1587 NULL, /* security attributes */
1588 OPEN_EXISTING,
1589 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001590 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1591 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001592 the symlink path again and not the actual final path. */
Victor Stinner26de69d2011-06-17 15:15:38 +02001593 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
Brian Curtind25aef52011-06-13 15:16:04 -05001594 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001595 NULL);
1596
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001597 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001598 /* Either the target doesn't exist, or we don't have access to
1599 get a handle to it. If the former, we need to return an error.
1600 If the latter, we can use attributes_from_dir. */
1601 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001602 return -1;
1603 /* Could not get attributes on open file. Fall back to
1604 reading the directory. */
1605 if (!attributes_from_dir_w(path, &info, &reparse_tag))
1606 /* Very strange. This should not fail now */
1607 return -1;
1608 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1609 if (traverse) {
1610 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001611 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001612 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001613 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001614 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001615 } else {
1616 if (!GetFileInformationByHandle(hFile, &info)) {
1617 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001618 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001619 }
1620 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001621 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1622 return -1;
1623
1624 /* Close the outer open file handle now that we're about to
1625 reopen it with different flags. */
1626 if (!CloseHandle(hFile))
1627 return -1;
1628
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001629 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001630 /* In order to call GetFinalPathNameByHandle we need to open
1631 the file without the reparse handling flag set. */
1632 hFile2 = CreateFileW(
1633 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1634 NULL, OPEN_EXISTING,
1635 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1636 NULL);
1637 if (hFile2 == INVALID_HANDLE_VALUE)
1638 return -1;
1639
1640 if (!get_target_path(hFile2, &target_path))
1641 return -1;
1642
1643 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerb6404912013-07-07 16:21:41 +02001644 PyMem_Free(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001645 return code;
1646 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001647 } else
1648 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001649 }
Steve Dowera2af1a52015-02-21 10:04:10 -08001650 _Py_attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001651
1652 /* Set S_IEXEC if it is an .exe, .bat, ... */
1653 dot = wcsrchr(path, '.');
1654 if (dot) {
1655 if (_wcsicmp(dot, L".bat") == 0 || _wcsicmp(dot, L".cmd") == 0 ||
1656 _wcsicmp(dot, L".exe") == 0 || _wcsicmp(dot, L".com") == 0)
1657 result->st_mode |= 0111;
1658 }
1659 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001660}
1661
1662static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001663win32_xstat(const char *path, struct _Py_stat_struct *result, BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001664{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001665 /* Protocol violation: we explicitly clear errno, instead of
1666 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001667 int code = win32_xstat_impl(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001668 errno = 0;
1669 return code;
1670}
Brian Curtinf5e76d02010-11-24 13:14:05 +00001671
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001672static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001673win32_xstat_w(const wchar_t *path, struct _Py_stat_struct *result, BOOL traverse)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001674{
1675 /* Protocol violation: we explicitly clear errno, instead of
1676 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001677 int code = win32_xstat_impl_w(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001678 errno = 0;
1679 return code;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001680}
Brian Curtind25aef52011-06-13 15:16:04 -05001681/* About the following functions: win32_lstat_w, win32_stat, win32_stat_w
Brian Curtind40e6f72010-07-08 21:39:08 +00001682
1683 In Posix, stat automatically traverses symlinks and returns the stat
1684 structure for the target. In Windows, the equivalent GetFileAttributes by
1685 default does not traverse symlinks and instead returns attributes for
1686 the symlink.
1687
1688 Therefore, win32_lstat will get the attributes traditionally, and
1689 win32_stat will first explicitly resolve the symlink target and then will
1690 call win32_lstat on that result.
1691
Ezio Melotti4969f702011-03-15 05:59:46 +02001692 The _w represent Unicode equivalents of the aforementioned ANSI functions. */
Brian Curtind40e6f72010-07-08 21:39:08 +00001693
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001694static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001695win32_lstat(const char* path, struct _Py_stat_struct *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001696{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001697 return win32_xstat(path, result, FALSE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001698}
1699
Victor Stinner8c62be82010-05-06 00:08:46 +00001700static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001701win32_lstat_w(const wchar_t* path, struct _Py_stat_struct *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001702{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001703 return win32_xstat_w(path, result, FALSE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001704}
1705
1706static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001707win32_stat(const char* path, struct _Py_stat_struct *result)
Brian Curtind40e6f72010-07-08 21:39:08 +00001708{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001709 return win32_xstat(path, result, TRUE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001710}
1711
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001712static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001713win32_stat_w(const wchar_t* path, struct _Py_stat_struct *result)
Brian Curtind40e6f72010-07-08 21:39:08 +00001714{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001715 return win32_xstat_w(path, result, TRUE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001716}
1717
Martin v. Löwis14694662006-02-03 12:54:16 +00001718#endif /* MS_WINDOWS */
1719
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001720PyDoc_STRVAR(stat_result__doc__,
Larry Hastings9cf065c2012-06-22 16:30:09 -07001721"stat_result: Result from stat, fstat, or lstat.\n\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001722This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001723 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001724or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
1725\n\
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001726Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
1727or st_flags, they are available as attributes only.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001728\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001729See os.stat for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001730
1731static PyStructSequence_Field stat_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001732 {"st_mode", "protection bits"},
1733 {"st_ino", "inode"},
1734 {"st_dev", "device"},
1735 {"st_nlink", "number of hard links"},
1736 {"st_uid", "user ID of owner"},
1737 {"st_gid", "group ID of owner"},
1738 {"st_size", "total size, in bytes"},
1739 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
1740 {NULL, "integer time of last access"},
1741 {NULL, "integer time of last modification"},
1742 {NULL, "integer time of last change"},
1743 {"st_atime", "time of last access"},
1744 {"st_mtime", "time of last modification"},
1745 {"st_ctime", "time of last change"},
Larry Hastings6fe20b32012-04-19 15:07:49 -07001746 {"st_atime_ns", "time of last access in nanoseconds"},
1747 {"st_mtime_ns", "time of last modification in nanoseconds"},
1748 {"st_ctime_ns", "time of last change in nanoseconds"},
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001749#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00001750 {"st_blksize", "blocksize for filesystem I/O"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001751#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001752#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00001753 {"st_blocks", "number of blocks allocated"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001754#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001755#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00001756 {"st_rdev", "device type (if inode device)"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001757#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001758#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00001759 {"st_flags", "user defined flags for file"},
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001760#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001761#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00001762 {"st_gen", "generation number"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001763#endif
1764#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00001765 {"st_birthtime", "time of creation"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001766#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05001767#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1768 {"st_file_attributes", "Windows file attribute bits"},
1769#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001770 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001771};
1772
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001773#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Larry Hastings6fe20b32012-04-19 15:07:49 -07001774#define ST_BLKSIZE_IDX 16
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001775#else
Larry Hastings6fe20b32012-04-19 15:07:49 -07001776#define ST_BLKSIZE_IDX 15
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001777#endif
1778
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001779#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001780#define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
1781#else
1782#define ST_BLOCKS_IDX ST_BLKSIZE_IDX
1783#endif
1784
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001785#ifdef HAVE_STRUCT_STAT_ST_RDEV
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001786#define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
1787#else
1788#define ST_RDEV_IDX ST_BLOCKS_IDX
1789#endif
1790
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001791#ifdef HAVE_STRUCT_STAT_ST_FLAGS
1792#define ST_FLAGS_IDX (ST_RDEV_IDX+1)
1793#else
1794#define ST_FLAGS_IDX ST_RDEV_IDX
1795#endif
1796
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001797#ifdef HAVE_STRUCT_STAT_ST_GEN
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001798#define ST_GEN_IDX (ST_FLAGS_IDX+1)
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001799#else
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001800#define ST_GEN_IDX ST_FLAGS_IDX
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001801#endif
1802
1803#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
1804#define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
1805#else
1806#define ST_BIRTHTIME_IDX ST_GEN_IDX
1807#endif
1808
Zachary Ware63f277b2014-06-19 09:46:37 -05001809#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1810#define ST_FILE_ATTRIBUTES_IDX (ST_BIRTHTIME_IDX+1)
1811#else
1812#define ST_FILE_ATTRIBUTES_IDX ST_BIRTHTIME_IDX
1813#endif
1814
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001815static PyStructSequence_Desc stat_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001816 "stat_result", /* name */
1817 stat_result__doc__, /* doc */
1818 stat_result_fields,
1819 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001820};
1821
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001822PyDoc_STRVAR(statvfs_result__doc__,
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001823"statvfs_result: Result from statvfs or fstatvfs.\n\n\
1824This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001825 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
Guido van Rossuma4dc73e2001-10-18 20:53:15 +00001826or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001827\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001828See os.statvfs for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001829
1830static PyStructSequence_Field statvfs_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001831 {"f_bsize", },
1832 {"f_frsize", },
1833 {"f_blocks", },
1834 {"f_bfree", },
1835 {"f_bavail", },
1836 {"f_files", },
1837 {"f_ffree", },
1838 {"f_favail", },
1839 {"f_flag", },
1840 {"f_namemax",},
1841 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001842};
1843
1844static PyStructSequence_Desc statvfs_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001845 "statvfs_result", /* name */
1846 statvfs_result__doc__, /* doc */
1847 statvfs_result_fields,
1848 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001849};
1850
Ross Lagerwall7807c352011-03-17 20:20:30 +02001851#if defined(HAVE_WAITID) && !defined(__APPLE__)
1852PyDoc_STRVAR(waitid_result__doc__,
1853"waitid_result: Result from waitid.\n\n\
1854This object may be accessed either as a tuple of\n\
1855 (si_pid, si_uid, si_signo, si_status, si_code),\n\
1856or via the attributes si_pid, si_uid, and so on.\n\
1857\n\
1858See os.waitid for more information.");
1859
1860static PyStructSequence_Field waitid_result_fields[] = {
1861 {"si_pid", },
1862 {"si_uid", },
1863 {"si_signo", },
1864 {"si_status", },
1865 {"si_code", },
1866 {0}
1867};
1868
1869static PyStructSequence_Desc waitid_result_desc = {
1870 "waitid_result", /* name */
1871 waitid_result__doc__, /* doc */
1872 waitid_result_fields,
1873 5
1874};
1875static PyTypeObject WaitidResultType;
1876#endif
1877
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001878static int initialized;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001879static PyTypeObject StatResultType;
1880static PyTypeObject StatVFSResultType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05001881#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001882static PyTypeObject SchedParamType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05001883#endif
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001884static newfunc structseq_new;
1885
1886static PyObject *
1887statresult_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1888{
Victor Stinner8c62be82010-05-06 00:08:46 +00001889 PyStructSequence *result;
1890 int i;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001891
Victor Stinner8c62be82010-05-06 00:08:46 +00001892 result = (PyStructSequence*)structseq_new(type, args, kwds);
1893 if (!result)
1894 return NULL;
1895 /* If we have been initialized from a tuple,
1896 st_?time might be set to None. Initialize it
1897 from the int slots. */
1898 for (i = 7; i <= 9; i++) {
1899 if (result->ob_item[i+3] == Py_None) {
1900 Py_DECREF(Py_None);
1901 Py_INCREF(result->ob_item[i]);
1902 result->ob_item[i+3] = result->ob_item[i];
1903 }
1904 }
1905 return (PyObject*)result;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001906}
1907
1908
1909
1910/* If true, st_?time is float. */
Martin v. Löwisfe33d0b2005-01-16 08:57:39 +00001911static int _stat_float_times = 1;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001912
1913PyDoc_STRVAR(stat_float_times__doc__,
1914"stat_float_times([newval]) -> oldval\n\n\
1915Determine whether os.[lf]stat represents time stamps as float objects.\n\
Larry Hastings2f936352014-08-05 14:04:04 +10001916\n\
1917If value is True, future calls to stat() return floats; if it is False,\n\
1918future calls return ints.\n\
1919If value is omitted, return the current setting.\n");
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001920
Larry Hastings2f936352014-08-05 14:04:04 +10001921/* AC 3.5: the public default value should be None, not ready for that yet */
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001922static PyObject*
1923stat_float_times(PyObject* self, PyObject *args)
1924{
Victor Stinner8c62be82010-05-06 00:08:46 +00001925 int newval = -1;
1926 if (!PyArg_ParseTuple(args, "|i:stat_float_times", &newval))
1927 return NULL;
Victor Stinner034d0aa2012-06-05 01:22:15 +02001928 if (PyErr_WarnEx(PyExc_DeprecationWarning,
1929 "stat_float_times() is deprecated",
1930 1))
1931 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00001932 if (newval == -1)
1933 /* Return old value */
1934 return PyBool_FromLong(_stat_float_times);
1935 _stat_float_times = newval;
1936 Py_INCREF(Py_None);
1937 return Py_None;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001938}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001939
Larry Hastings6fe20b32012-04-19 15:07:49 -07001940static PyObject *billion = NULL;
1941
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001942static void
Victor Stinner4195b5c2012-02-08 23:03:19 +01001943fill_time(PyObject *v, int index, time_t sec, unsigned long nsec)
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001944{
Larry Hastings6fe20b32012-04-19 15:07:49 -07001945 PyObject *s = _PyLong_FromTime_t(sec);
1946 PyObject *ns_fractional = PyLong_FromUnsignedLong(nsec);
1947 PyObject *s_in_ns = NULL;
1948 PyObject *ns_total = NULL;
1949 PyObject *float_s = NULL;
1950
1951 if (!(s && ns_fractional))
1952 goto exit;
1953
1954 s_in_ns = PyNumber_Multiply(s, billion);
1955 if (!s_in_ns)
1956 goto exit;
1957
1958 ns_total = PyNumber_Add(s_in_ns, ns_fractional);
1959 if (!ns_total)
1960 goto exit;
1961
Victor Stinner4195b5c2012-02-08 23:03:19 +01001962 if (_stat_float_times) {
Larry Hastings6fe20b32012-04-19 15:07:49 -07001963 float_s = PyFloat_FromDouble(sec + 1e-9*nsec);
1964 if (!float_s)
1965 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00001966 }
Larry Hastings6fe20b32012-04-19 15:07:49 -07001967 else {
1968 float_s = s;
1969 Py_INCREF(float_s);
1970 }
1971
1972 PyStructSequence_SET_ITEM(v, index, s);
1973 PyStructSequence_SET_ITEM(v, index+3, float_s);
1974 PyStructSequence_SET_ITEM(v, index+6, ns_total);
1975 s = NULL;
1976 float_s = NULL;
1977 ns_total = NULL;
1978exit:
1979 Py_XDECREF(s);
1980 Py_XDECREF(ns_fractional);
1981 Py_XDECREF(s_in_ns);
1982 Py_XDECREF(ns_total);
1983 Py_XDECREF(float_s);
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001984}
1985
Tim Peters5aa91602002-01-30 05:46:57 +00001986/* pack a system stat C structure into the Python stat tuple
Fred Drake699f3522000-06-29 21:12:41 +00001987 (used by posix_stat() and posix_fstat()) */
1988static PyObject*
Victor Stinner4195b5c2012-02-08 23:03:19 +01001989_pystat_fromstructstat(STRUCT_STAT *st)
Fred Drake699f3522000-06-29 21:12:41 +00001990{
Victor Stinner8c62be82010-05-06 00:08:46 +00001991 unsigned long ansec, mnsec, cnsec;
1992 PyObject *v = PyStructSequence_New(&StatResultType);
1993 if (v == NULL)
1994 return NULL;
Fred Drake699f3522000-06-29 21:12:41 +00001995
Victor Stinner8c62be82010-05-06 00:08:46 +00001996 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long)st->st_mode));
Fred Drake699f3522000-06-29 21:12:41 +00001997#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00001998 PyStructSequence_SET_ITEM(v, 1,
1999 PyLong_FromLongLong((PY_LONG_LONG)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002000#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002001 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002002#endif
Serhiy Storchaka404fa922013-01-02 18:22:23 +02002003#ifdef MS_WINDOWS
2004 PyStructSequence_SET_ITEM(v, 2, PyLong_FromUnsignedLong(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002005#else
Serhiy Storchakab2653b32015-01-18 11:12:11 +02002006 PyStructSequence_SET_ITEM(v, 2, _PyLong_FromDev(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002007#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002008 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long)st->st_nlink));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02002009#if defined(MS_WINDOWS)
2010 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong(0));
2011 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong(0));
2012#else
2013 PyStructSequence_SET_ITEM(v, 4, _PyLong_FromUid(st->st_uid));
2014 PyStructSequence_SET_ITEM(v, 5, _PyLong_FromGid(st->st_gid));
2015#endif
Fred Drake699f3522000-06-29 21:12:41 +00002016#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002017 PyStructSequence_SET_ITEM(v, 6,
2018 PyLong_FromLongLong((PY_LONG_LONG)st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002019#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002020 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong(st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002021#endif
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002022
Martin v. Löwis14694662006-02-03 12:54:16 +00002023#if defined(HAVE_STAT_TV_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002024 ansec = st->st_atim.tv_nsec;
2025 mnsec = st->st_mtim.tv_nsec;
2026 cnsec = st->st_ctim.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002027#elif defined(HAVE_STAT_TV_NSEC2)
Victor Stinner8c62be82010-05-06 00:08:46 +00002028 ansec = st->st_atimespec.tv_nsec;
2029 mnsec = st->st_mtimespec.tv_nsec;
2030 cnsec = st->st_ctimespec.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002031#elif defined(HAVE_STAT_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002032 ansec = st->st_atime_nsec;
2033 mnsec = st->st_mtime_nsec;
2034 cnsec = st->st_ctime_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002035#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002036 ansec = mnsec = cnsec = 0;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002037#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002038 fill_time(v, 7, st->st_atime, ansec);
2039 fill_time(v, 8, st->st_mtime, mnsec);
2040 fill_time(v, 9, st->st_ctime, cnsec);
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002041
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002042#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00002043 PyStructSequence_SET_ITEM(v, ST_BLKSIZE_IDX,
2044 PyLong_FromLong((long)st->st_blksize));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002045#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002046#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00002047 PyStructSequence_SET_ITEM(v, ST_BLOCKS_IDX,
2048 PyLong_FromLong((long)st->st_blocks));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002049#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002050#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00002051 PyStructSequence_SET_ITEM(v, ST_RDEV_IDX,
2052 PyLong_FromLong((long)st->st_rdev));
Fred Drake699f3522000-06-29 21:12:41 +00002053#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002054#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00002055 PyStructSequence_SET_ITEM(v, ST_GEN_IDX,
2056 PyLong_FromLong((long)st->st_gen));
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002057#endif
2058#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00002059 {
Victor Stinner4195b5c2012-02-08 23:03:19 +01002060 PyObject *val;
2061 unsigned long bsec,bnsec;
2062 bsec = (long)st->st_birthtime;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002063#ifdef HAVE_STAT_TV_NSEC2
Victor Stinner4195b5c2012-02-08 23:03:19 +01002064 bnsec = st->st_birthtimespec.tv_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002065#else
Victor Stinner4195b5c2012-02-08 23:03:19 +01002066 bnsec = 0;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002067#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002068 if (_stat_float_times) {
2069 val = PyFloat_FromDouble(bsec + 1e-9*bnsec);
2070 } else {
2071 val = PyLong_FromLong((long)bsec);
2072 }
2073 PyStructSequence_SET_ITEM(v, ST_BIRTHTIME_IDX,
2074 val);
Victor Stinner8c62be82010-05-06 00:08:46 +00002075 }
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002076#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002077#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00002078 PyStructSequence_SET_ITEM(v, ST_FLAGS_IDX,
2079 PyLong_FromLong((long)st->st_flags));
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002080#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05002081#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2082 PyStructSequence_SET_ITEM(v, ST_FILE_ATTRIBUTES_IDX,
2083 PyLong_FromUnsignedLong(st->st_file_attributes));
2084#endif
Fred Drake699f3522000-06-29 21:12:41 +00002085
Victor Stinner8c62be82010-05-06 00:08:46 +00002086 if (PyErr_Occurred()) {
2087 Py_DECREF(v);
2088 return NULL;
2089 }
Fred Drake699f3522000-06-29 21:12:41 +00002090
Victor Stinner8c62be82010-05-06 00:08:46 +00002091 return v;
Fred Drake699f3522000-06-29 21:12:41 +00002092}
2093
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002094/* POSIX methods */
2095
Guido van Rossum94f6f721999-01-06 18:42:14 +00002096
2097static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07002098posix_do_stat(char *function_name, path_t *path,
2099 int dir_fd, int follow_symlinks)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002100{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002101 STRUCT_STAT st;
2102 int result;
2103
2104#if !defined(MS_WINDOWS) && !defined(HAVE_FSTATAT) && !defined(HAVE_LSTAT)
2105 if (follow_symlinks_specified(function_name, follow_symlinks))
2106 return NULL;
2107#endif
2108
2109 if (path_and_dir_fd_invalid("stat", path, dir_fd) ||
2110 dir_fd_and_fd_invalid("stat", dir_fd, path->fd) ||
2111 fd_and_follow_symlinks_invalid("stat", path->fd, follow_symlinks))
2112 return NULL;
2113
2114 Py_BEGIN_ALLOW_THREADS
2115 if (path->fd != -1)
2116 result = FSTAT(path->fd, &st);
2117 else
2118#ifdef MS_WINDOWS
2119 if (path->wide) {
2120 if (follow_symlinks)
2121 result = win32_stat_w(path->wide, &st);
2122 else
2123 result = win32_lstat_w(path->wide, &st);
2124 }
2125 else
2126#endif
2127#if defined(HAVE_LSTAT) || defined(MS_WINDOWS)
2128 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
2129 result = LSTAT(path->narrow, &st);
2130 else
2131#endif
2132#ifdef HAVE_FSTATAT
2133 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks)
2134 result = fstatat(dir_fd, path->narrow, &st,
2135 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2136 else
2137#endif
2138 result = STAT(path->narrow, &st);
2139 Py_END_ALLOW_THREADS
2140
Victor Stinner292c8352012-10-30 02:17:38 +01002141 if (result != 0) {
2142 return path_error(path);
2143 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07002144
2145 return _pystat_fromstructstat(&st);
2146}
2147
Larry Hastings2f936352014-08-05 14:04:04 +10002148/*[python input]
2149
2150for s in """
2151
2152FACCESSAT
2153FCHMODAT
2154FCHOWNAT
2155FSTATAT
2156LINKAT
2157MKDIRAT
2158MKFIFOAT
2159MKNODAT
2160OPENAT
2161READLINKAT
2162SYMLINKAT
2163UNLINKAT
2164
2165""".strip().split():
2166 s = s.strip()
2167 print("""
2168#ifdef HAVE_{s}
2169 #define {s}_DIR_FD_CONVERTER dir_fd_converter
Larry Hastings31826802013-10-19 00:09:25 -07002170#else
Larry Hastings2f936352014-08-05 14:04:04 +10002171 #define {s}_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings31826802013-10-19 00:09:25 -07002172#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002173""".rstrip().format(s=s))
2174
2175for s in """
2176
2177FCHDIR
2178FCHMOD
2179FCHOWN
2180FDOPENDIR
2181FEXECVE
2182FPATHCONF
2183FSTATVFS
2184FTRUNCATE
2185
2186""".strip().split():
2187 s = s.strip()
2188 print("""
2189#ifdef HAVE_{s}
2190 #define PATH_HAVE_{s} 1
2191#else
2192 #define PATH_HAVE_{s} 0
2193#endif
2194
2195""".rstrip().format(s=s))
2196[python start generated code]*/
2197
2198#ifdef HAVE_FACCESSAT
2199 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_converter
2200#else
2201 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_unavailable
2202#endif
2203
2204#ifdef HAVE_FCHMODAT
2205 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_converter
2206#else
2207 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_unavailable
2208#endif
2209
2210#ifdef HAVE_FCHOWNAT
2211 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_converter
2212#else
2213 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_unavailable
2214#endif
2215
2216#ifdef HAVE_FSTATAT
2217 #define FSTATAT_DIR_FD_CONVERTER dir_fd_converter
2218#else
2219 #define FSTATAT_DIR_FD_CONVERTER dir_fd_unavailable
2220#endif
2221
2222#ifdef HAVE_LINKAT
2223 #define LINKAT_DIR_FD_CONVERTER dir_fd_converter
2224#else
2225 #define LINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2226#endif
2227
2228#ifdef HAVE_MKDIRAT
2229 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_converter
2230#else
2231 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_unavailable
2232#endif
2233
2234#ifdef HAVE_MKFIFOAT
2235 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_converter
2236#else
2237 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_unavailable
2238#endif
2239
2240#ifdef HAVE_MKNODAT
2241 #define MKNODAT_DIR_FD_CONVERTER dir_fd_converter
2242#else
2243 #define MKNODAT_DIR_FD_CONVERTER dir_fd_unavailable
2244#endif
2245
2246#ifdef HAVE_OPENAT
2247 #define OPENAT_DIR_FD_CONVERTER dir_fd_converter
2248#else
2249 #define OPENAT_DIR_FD_CONVERTER dir_fd_unavailable
2250#endif
2251
2252#ifdef HAVE_READLINKAT
2253 #define READLINKAT_DIR_FD_CONVERTER dir_fd_converter
2254#else
2255 #define READLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2256#endif
2257
2258#ifdef HAVE_SYMLINKAT
2259 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_converter
2260#else
2261 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2262#endif
2263
2264#ifdef HAVE_UNLINKAT
2265 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_converter
2266#else
2267 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2268#endif
2269
2270#ifdef HAVE_FCHDIR
2271 #define PATH_HAVE_FCHDIR 1
2272#else
2273 #define PATH_HAVE_FCHDIR 0
2274#endif
2275
2276#ifdef HAVE_FCHMOD
2277 #define PATH_HAVE_FCHMOD 1
2278#else
2279 #define PATH_HAVE_FCHMOD 0
2280#endif
2281
2282#ifdef HAVE_FCHOWN
2283 #define PATH_HAVE_FCHOWN 1
2284#else
2285 #define PATH_HAVE_FCHOWN 0
2286#endif
2287
2288#ifdef HAVE_FDOPENDIR
2289 #define PATH_HAVE_FDOPENDIR 1
2290#else
2291 #define PATH_HAVE_FDOPENDIR 0
2292#endif
2293
2294#ifdef HAVE_FEXECVE
2295 #define PATH_HAVE_FEXECVE 1
2296#else
2297 #define PATH_HAVE_FEXECVE 0
2298#endif
2299
2300#ifdef HAVE_FPATHCONF
2301 #define PATH_HAVE_FPATHCONF 1
2302#else
2303 #define PATH_HAVE_FPATHCONF 0
2304#endif
2305
2306#ifdef HAVE_FSTATVFS
2307 #define PATH_HAVE_FSTATVFS 1
2308#else
2309 #define PATH_HAVE_FSTATVFS 0
2310#endif
2311
2312#ifdef HAVE_FTRUNCATE
2313 #define PATH_HAVE_FTRUNCATE 1
2314#else
2315 #define PATH_HAVE_FTRUNCATE 0
2316#endif
2317/*[python end generated code: output=4bd4f6f7d41267f1 input=80b4c890b6774ea5]*/
Larry Hastings31826802013-10-19 00:09:25 -07002318
Steve Dowerfe0a41a2015-03-20 19:50:46 -07002319#ifdef MS_WINDOWS
2320 #undef PATH_HAVE_FTRUNCATE
2321 #define PATH_HAVE_FTRUNCATE 1
2322#endif
Larry Hastings31826802013-10-19 00:09:25 -07002323
Larry Hastings61272b72014-01-07 12:41:53 -08002324/*[python input]
Larry Hastings31826802013-10-19 00:09:25 -07002325
2326class path_t_converter(CConverter):
2327
2328 type = "path_t"
2329 impl_by_reference = True
2330 parse_by_reference = True
2331
2332 converter = 'path_converter'
2333
2334 def converter_init(self, *, allow_fd=False, nullable=False):
Larry Hastings31826802013-10-19 00:09:25 -07002335 # right now path_t doesn't support default values.
2336 # to support a default value, you'll need to override initialize().
Larry Hastings2f936352014-08-05 14:04:04 +10002337 if self.default not in (unspecified, None):
Larry Hastings7726ac92014-01-31 22:03:12 -08002338 fail("Can't specify a default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002339
Larry Hastings2f936352014-08-05 14:04:04 +10002340 if self.c_default not in (None, 'Py_None'):
2341 raise RuntimeError("Can't specify a c_default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002342
2343 self.nullable = nullable
2344 self.allow_fd = allow_fd
2345
Larry Hastings7726ac92014-01-31 22:03:12 -08002346 def pre_render(self):
2347 def strify(value):
Larry Hastings2f936352014-08-05 14:04:04 +10002348 if isinstance(value, str):
2349 return value
Larry Hastings7726ac92014-01-31 22:03:12 -08002350 return str(int(bool(value)))
2351
2352 # add self.py_name here when merging with posixmodule conversion
Larry Hastings2f936352014-08-05 14:04:04 +10002353 self.c_default = 'PATH_T_INITIALIZE("{}", "{}", {}, {})'.format(
Larry Hastings31826802013-10-19 00:09:25 -07002354 self.function.name,
Larry Hastings2f936352014-08-05 14:04:04 +10002355 self.name,
Larry Hastings7726ac92014-01-31 22:03:12 -08002356 strify(self.nullable),
2357 strify(self.allow_fd),
Larry Hastings31826802013-10-19 00:09:25 -07002358 )
2359
2360 def cleanup(self):
2361 return "path_cleanup(&" + self.name + ");\n"
2362
2363
2364class dir_fd_converter(CConverter):
2365 type = 'int'
Larry Hastings31826802013-10-19 00:09:25 -07002366
Larry Hastings2f936352014-08-05 14:04:04 +10002367 def converter_init(self, requires=None):
Larry Hastings31826802013-10-19 00:09:25 -07002368 if self.default in (unspecified, None):
2369 self.c_default = 'DEFAULT_DIR_FD'
Larry Hastings2f936352014-08-05 14:04:04 +10002370 if isinstance(requires, str):
2371 self.converter = requires.upper() + '_DIR_FD_CONVERTER'
2372 else:
2373 self.converter = 'dir_fd_converter'
Larry Hastings31826802013-10-19 00:09:25 -07002374
Larry Hastings2f936352014-08-05 14:04:04 +10002375class fildes_converter(CConverter):
2376 type = 'int'
2377 converter = 'fildes_converter'
2378
2379class uid_t_converter(CConverter):
2380 type = "uid_t"
2381 converter = '_Py_Uid_Converter'
2382
2383class gid_t_converter(CConverter):
2384 type = "gid_t"
2385 converter = '_Py_Gid_Converter'
2386
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002387class dev_t_converter(CConverter):
2388 type = 'dev_t'
2389 converter = '_Py_Dev_Converter'
2390
2391class dev_t_return_converter(unsigned_long_return_converter):
2392 type = 'dev_t'
2393 conversion_fn = '_PyLong_FromDev'
2394 unsigned_cast = '(dev_t)'
2395
Larry Hastings2f936352014-08-05 14:04:04 +10002396class FSConverter_converter(CConverter):
2397 type = 'PyObject *'
2398 converter = 'PyUnicode_FSConverter'
2399 def converter_init(self):
2400 if self.default is not unspecified:
2401 fail("FSConverter_converter does not support default values")
2402 self.c_default = 'NULL'
2403
2404 def cleanup(self):
2405 return "Py_XDECREF(" + self.name + ");\n"
2406
2407class pid_t_converter(CConverter):
2408 type = 'pid_t'
2409 format_unit = '" _Py_PARSE_PID "'
2410
2411class idtype_t_converter(int_converter):
2412 type = 'idtype_t'
2413
2414class id_t_converter(CConverter):
2415 type = 'id_t'
2416 format_unit = '" _Py_PARSE_PID "'
2417
2418class Py_intptr_t_converter(CConverter):
2419 type = 'Py_intptr_t'
2420 format_unit = '" _Py_PARSE_INTPTR "'
2421
2422class Py_off_t_converter(CConverter):
2423 type = 'Py_off_t'
2424 converter = 'Py_off_t_converter'
2425
2426class Py_off_t_return_converter(long_return_converter):
2427 type = 'Py_off_t'
2428 conversion_fn = 'PyLong_FromPy_off_t'
2429
2430class path_confname_converter(CConverter):
2431 type="int"
2432 converter="conv_path_confname"
2433
2434class confstr_confname_converter(path_confname_converter):
2435 converter='conv_confstr_confname'
2436
2437class sysconf_confname_converter(path_confname_converter):
2438 converter="conv_sysconf_confname"
2439
2440class sched_param_converter(CConverter):
2441 type = 'struct sched_param'
2442 converter = 'convert_sched_param'
2443 impl_by_reference = True;
Larry Hastings31826802013-10-19 00:09:25 -07002444
Larry Hastings61272b72014-01-07 12:41:53 -08002445[python start generated code]*/
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002446/*[python end generated code: output=da39a3ee5e6b4b0d input=affe68316f160401]*/
Larry Hastings31826802013-10-19 00:09:25 -07002447
Larry Hastings61272b72014-01-07 12:41:53 -08002448/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002449
Larry Hastings2a727912014-01-16 11:32:01 -08002450os.stat
Larry Hastings31826802013-10-19 00:09:25 -07002451
2452 path : path_t(allow_fd=True)
2453 Path to be examined; can be string, bytes, or open-file-descriptor int.
2454
2455 *
2456
Larry Hastings2f936352014-08-05 14:04:04 +10002457 dir_fd : dir_fd(requires='fstatat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002458 If not None, it should be a file descriptor open to a directory,
2459 and path should be a relative string; path will then be relative to
2460 that directory.
2461
2462 follow_symlinks: bool = True
2463 If False, and the last element of the path is a symbolic link,
2464 stat will examine the symbolic link itself instead of the file
2465 the link points to.
2466
2467Perform a stat system call on the given path.
2468
2469dir_fd and follow_symlinks may not be implemented
2470 on your platform. If they are unavailable, using them will raise a
2471 NotImplementedError.
2472
2473It's an error to use dir_fd or follow_symlinks when specifying path as
2474 an open file descriptor.
2475
Larry Hastings61272b72014-01-07 12:41:53 -08002476[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002477
Larry Hastings31826802013-10-19 00:09:25 -07002478static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002479os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd,
2480 int follow_symlinks)
2481/*[clinic end generated code: output=e4f7569f95d523ca input=099d356c306fa24a]*/
Larry Hastings31826802013-10-19 00:09:25 -07002482{
2483 return posix_do_stat("stat", path, dir_fd, follow_symlinks);
2484}
2485
Larry Hastings2f936352014-08-05 14:04:04 +10002486
2487/*[clinic input]
2488os.lstat
2489
2490 path : path_t
2491
2492 *
2493
2494 dir_fd : dir_fd(requires='fstatat') = None
2495
2496Perform a stat system call on the given path, without following symbolic links.
2497
2498Like stat(), but do not follow symbolic links.
2499Equivalent to stat(path, follow_symlinks=False).
2500[clinic start generated code]*/
2501
Larry Hastings2f936352014-08-05 14:04:04 +10002502static PyObject *
2503os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002504/*[clinic end generated code: output=7a748e333fcb39bd input=0b7474765927b925]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002505{
2506 int follow_symlinks = 0;
2507 return posix_do_stat("lstat", path, dir_fd, follow_symlinks);
2508}
Larry Hastings31826802013-10-19 00:09:25 -07002509
Larry Hastings2f936352014-08-05 14:04:04 +10002510
Larry Hastings61272b72014-01-07 12:41:53 -08002511/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +10002512os.access -> bool
Larry Hastings31826802013-10-19 00:09:25 -07002513
2514 path: path_t(allow_fd=True)
2515 Path to be tested; can be string, bytes, or open-file-descriptor int.
2516
2517 mode: int
2518 Operating-system mode bitfield. Can be F_OK to test existence,
2519 or the inclusive-OR of R_OK, W_OK, and X_OK.
2520
2521 *
2522
Larry Hastings2f936352014-08-05 14:04:04 +10002523 dir_fd : dir_fd(requires='faccessat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002524 If not None, it should be a file descriptor open to a directory,
2525 and path should be relative; path will then be relative to that
2526 directory.
2527
2528 effective_ids: bool = False
2529 If True, access will use the effective uid/gid instead of
2530 the real uid/gid.
2531
2532 follow_symlinks: bool = True
2533 If False, and the last element of the path is a symbolic link,
2534 access will examine the symbolic link itself instead of the file
2535 the link points to.
2536
2537Use the real uid/gid to test for access to a path.
2538
2539{parameters}
2540dir_fd, effective_ids, and follow_symlinks may not be implemented
2541 on your platform. If they are unavailable, using them will raise a
2542 NotImplementedError.
2543
2544Note that most operations will use the effective uid/gid, therefore this
2545 routine can be used in a suid/sgid environment to test if the invoking user
2546 has the specified access to the path.
2547
Larry Hastings61272b72014-01-07 12:41:53 -08002548[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002549
Larry Hastings2f936352014-08-05 14:04:04 +10002550static int
Larry Hastings89964c42015-04-14 18:07:59 -04002551os_access_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd,
2552 int effective_ids, int follow_symlinks)
2553/*[clinic end generated code: output=abaa53340210088d input=b75a756797af45ec]*/
Larry Hastings31826802013-10-19 00:09:25 -07002554{
Larry Hastings2f936352014-08-05 14:04:04 +10002555 int return_value;
Victor Stinner8c62be82010-05-06 00:08:46 +00002556
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002557#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002558 DWORD attr;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002559#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07002560 int result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002561#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07002562
Larry Hastings9cf065c2012-06-22 16:30:09 -07002563#ifndef HAVE_FACCESSAT
2564 if (follow_symlinks_specified("access", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002565 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002566
2567 if (effective_ids) {
2568 argument_unavailable_error("access", "effective_ids");
Larry Hastings2f936352014-08-05 14:04:04 +10002569 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002570 }
2571#endif
2572
2573#ifdef MS_WINDOWS
2574 Py_BEGIN_ALLOW_THREADS
Christian Heimesebe83f92013-10-19 22:36:17 +02002575 if (path->wide != NULL)
2576 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002577 else
Christian Heimesebe83f92013-10-19 22:36:17 +02002578 attr = GetFileAttributesA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002579 Py_END_ALLOW_THREADS
2580
2581 /*
Georg Brandlf7875592012-06-24 13:58:31 +02002582 * Access is possible if
Larry Hastings9cf065c2012-06-22 16:30:09 -07002583 * * we didn't get a -1, and
2584 * * write access wasn't requested,
2585 * * or the file isn't read-only,
2586 * * or it's a directory.
2587 * (Directories cannot be read-only on Windows.)
2588 */
Larry Hastings2f936352014-08-05 14:04:04 +10002589 return_value = (attr != INVALID_FILE_ATTRIBUTES) &&
Georg Brandl5bb7aa92012-06-23 12:48:40 +02002590 (!(mode & 2) ||
Larry Hastings9cf065c2012-06-22 16:30:09 -07002591 !(attr & FILE_ATTRIBUTE_READONLY) ||
Larry Hastings2f936352014-08-05 14:04:04 +10002592 (attr & FILE_ATTRIBUTE_DIRECTORY));
Larry Hastings9cf065c2012-06-22 16:30:09 -07002593#else
2594
2595 Py_BEGIN_ALLOW_THREADS
2596#ifdef HAVE_FACCESSAT
2597 if ((dir_fd != DEFAULT_DIR_FD) ||
2598 effective_ids ||
2599 !follow_symlinks) {
2600 int flags = 0;
2601 if (!follow_symlinks)
2602 flags |= AT_SYMLINK_NOFOLLOW;
2603 if (effective_ids)
2604 flags |= AT_EACCESS;
Larry Hastings31826802013-10-19 00:09:25 -07002605 result = faccessat(dir_fd, path->narrow, mode, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002606 }
2607 else
2608#endif
Larry Hastings31826802013-10-19 00:09:25 -07002609 result = access(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002610 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002611 return_value = !result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002612#endif
2613
Larry Hastings9cf065c2012-06-22 16:30:09 -07002614 return return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002615}
2616
Guido van Rossumd371ff11999-01-25 16:12:23 +00002617#ifndef F_OK
2618#define F_OK 0
2619#endif
2620#ifndef R_OK
2621#define R_OK 4
2622#endif
2623#ifndef W_OK
2624#define W_OK 2
2625#endif
2626#ifndef X_OK
2627#define X_OK 1
2628#endif
2629
Larry Hastings31826802013-10-19 00:09:25 -07002630
Guido van Rossumd371ff11999-01-25 16:12:23 +00002631#ifdef HAVE_TTYNAME
Larry Hastings61272b72014-01-07 12:41:53 -08002632/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002633os.ttyname -> DecodeFSDefault
2634
2635 fd: int
2636 Integer file descriptor handle.
2637
2638 /
2639
2640Return the name of the terminal device connected to 'fd'.
Larry Hastings61272b72014-01-07 12:41:53 -08002641[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002642
Larry Hastings31826802013-10-19 00:09:25 -07002643static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002644os_ttyname_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002645/*[clinic end generated code: output=03ad3d5ccaef75c3 input=5f72ca83e76b3b45]*/
Larry Hastings31826802013-10-19 00:09:25 -07002646{
2647 char *ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002648
Larry Hastings31826802013-10-19 00:09:25 -07002649 ret = ttyname(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00002650 if (ret == NULL)
Larry Hastings31826802013-10-19 00:09:25 -07002651 posix_error();
2652 return ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002653}
Guido van Rossumd371ff11999-01-25 16:12:23 +00002654#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00002655
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002656#ifdef HAVE_CTERMID
Larry Hastings2f936352014-08-05 14:04:04 +10002657/*[clinic input]
2658os.ctermid
2659
2660Return the name of the controlling terminal for this process.
2661[clinic start generated code]*/
2662
Larry Hastings2f936352014-08-05 14:04:04 +10002663static PyObject *
2664os_ctermid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002665/*[clinic end generated code: output=1b73788201e0aebd input=3b87fdd52556382d]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002666{
Victor Stinner8c62be82010-05-06 00:08:46 +00002667 char *ret;
2668 char buffer[L_ctermid];
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002669
Greg Wardb48bc172000-03-01 21:51:56 +00002670#ifdef USE_CTERMID_R
Victor Stinner8c62be82010-05-06 00:08:46 +00002671 ret = ctermid_r(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002672#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002673 ret = ctermid(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002674#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002675 if (ret == NULL)
2676 return posix_error();
Victor Stinner5fe6de82010-08-15 09:12:51 +00002677 return PyUnicode_DecodeFSDefault(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002678}
Larry Hastings2f936352014-08-05 14:04:04 +10002679#endif /* HAVE_CTERMID */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002680
Larry Hastings2f936352014-08-05 14:04:04 +10002681
2682/*[clinic input]
2683os.chdir
2684
2685 path: path_t(allow_fd='PATH_HAVE_FCHDIR')
2686
2687Change the current working directory to the specified path.
2688
2689path may always be specified as a string.
2690On some platforms, path may also be specified as an open file descriptor.
2691 If this functionality is unavailable, using it raises an exception.
2692[clinic start generated code]*/
2693
Larry Hastings2f936352014-08-05 14:04:04 +10002694static PyObject *
2695os_chdir_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002696/*[clinic end generated code: output=7358e3a20fb5aa93 input=1a4a15b4d12cb15d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002697{
2698 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002699
2700 Py_BEGIN_ALLOW_THREADS
2701#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10002702 if (path->wide)
2703 result = win32_wchdir(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002704 else
Larry Hastings2f936352014-08-05 14:04:04 +10002705 result = win32_chdir(path->narrow);
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03002706 result = !result; /* on unix, success = 0, on windows, success = !0 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002707#else
2708#ifdef HAVE_FCHDIR
Larry Hastings2f936352014-08-05 14:04:04 +10002709 if (path->fd != -1)
2710 result = fchdir(path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002711 else
2712#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002713 result = chdir(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002714#endif
2715 Py_END_ALLOW_THREADS
2716
2717 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10002718 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002719 }
2720
Larry Hastings2f936352014-08-05 14:04:04 +10002721 Py_RETURN_NONE;
2722}
2723
2724
2725#ifdef HAVE_FCHDIR
2726/*[clinic input]
2727os.fchdir
2728
2729 fd: fildes
2730
2731Change to the directory of the given file descriptor.
2732
2733fd must be opened on a directory, not a file.
2734Equivalent to os.chdir(fd).
2735
2736[clinic start generated code]*/
2737
Fred Drake4d1e64b2002-04-15 19:40:07 +00002738static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10002739os_fchdir_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002740/*[clinic end generated code: output=361d30df6b2d3418 input=18e816479a2fa985]*/
Fred Drake4d1e64b2002-04-15 19:40:07 +00002741{
Larry Hastings2f936352014-08-05 14:04:04 +10002742 return posix_fildes_fd(fd, fchdir);
Fred Drake4d1e64b2002-04-15 19:40:07 +00002743}
2744#endif /* HAVE_FCHDIR */
2745
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002746
Larry Hastings2f936352014-08-05 14:04:04 +10002747/*[clinic input]
2748os.chmod
2749
2750 path: path_t(allow_fd='PATH_HAVE_FCHMOD')
2751 Path to be modified. May always be specified as a str or bytes.
2752 On some platforms, path may also be specified as an open file descriptor.
2753 If this functionality is unavailable, using it raises an exception.
2754
2755 mode: int
2756 Operating-system mode bitfield.
2757
2758 *
2759
2760 dir_fd : dir_fd(requires='fchmodat') = None
2761 If not None, it should be a file descriptor open to a directory,
2762 and path should be relative; path will then be relative to that
2763 directory.
2764
2765 follow_symlinks: bool = True
2766 If False, and the last element of the path is a symbolic link,
2767 chmod will modify the symbolic link itself instead of the file
2768 the link points to.
2769
2770Change the access permissions of a file.
2771
2772It is an error to use dir_fd or follow_symlinks when specifying path as
2773 an open file descriptor.
2774dir_fd and follow_symlinks may not be implemented on your platform.
2775 If they are unavailable, using them will raise a NotImplementedError.
2776
2777[clinic start generated code]*/
2778
Larry Hastings2f936352014-08-05 14:04:04 +10002779static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002780os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd,
2781 int follow_symlinks)
2782/*[clinic end generated code: output=05e7f73b1a843ba2 input=7f1618e5e15cc196]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002783{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002784 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002785
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002786#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002787 DWORD attr;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002788#endif
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00002789
Larry Hastings9cf065c2012-06-22 16:30:09 -07002790#ifdef HAVE_FCHMODAT
2791 int fchmodat_nofollow_unsupported = 0;
2792#endif
2793
Larry Hastings9cf065c2012-06-22 16:30:09 -07002794#if !(defined(HAVE_FCHMODAT) || defined(HAVE_LCHMOD))
2795 if (follow_symlinks_specified("chmod", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002796 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002797#endif
2798
2799#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002800 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002801 if (path->wide)
2802 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002803 else
Larry Hastings2f936352014-08-05 14:04:04 +10002804 attr = GetFileAttributesA(path->narrow);
Tim Golden23005082013-10-25 11:22:37 +01002805 if (attr == INVALID_FILE_ATTRIBUTES)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002806 result = 0;
2807 else {
2808 if (mode & _S_IWRITE)
Victor Stinner8c62be82010-05-06 00:08:46 +00002809 attr &= ~FILE_ATTRIBUTE_READONLY;
2810 else
2811 attr |= FILE_ATTRIBUTE_READONLY;
Larry Hastings2f936352014-08-05 14:04:04 +10002812 if (path->wide)
2813 result = SetFileAttributesW(path->wide, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002814 else
Larry Hastings2f936352014-08-05 14:04:04 +10002815 result = SetFileAttributesA(path->narrow, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002816 }
2817 Py_END_ALLOW_THREADS
2818
2819 if (!result) {
Larry Hastings2f936352014-08-05 14:04:04 +10002820 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002821 }
2822#else /* MS_WINDOWS */
2823 Py_BEGIN_ALLOW_THREADS
2824#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002825 if (path->fd != -1)
2826 result = fchmod(path->fd, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002827 else
2828#endif
2829#ifdef HAVE_LCHMOD
2830 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10002831 result = lchmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002832 else
2833#endif
2834#ifdef HAVE_FCHMODAT
2835 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks) {
2836 /*
2837 * fchmodat() doesn't currently support AT_SYMLINK_NOFOLLOW!
2838 * The documentation specifically shows how to use it,
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07002839 * and then says it isn't implemented yet.
2840 * (true on linux with glibc 2.15, and openindiana 3.x)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002841 *
2842 * Once it is supported, os.chmod will automatically
2843 * support dir_fd and follow_symlinks=False. (Hopefully.)
2844 * Until then, we need to be careful what exception we raise.
2845 */
Larry Hastings2f936352014-08-05 14:04:04 +10002846 result = fchmodat(dir_fd, path->narrow, mode,
Larry Hastings9cf065c2012-06-22 16:30:09 -07002847 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2848 /*
2849 * But wait! We can't throw the exception without allowing threads,
2850 * and we can't do that in this nested scope. (Macro trickery, sigh.)
2851 */
2852 fchmodat_nofollow_unsupported =
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07002853 result &&
2854 ((errno == ENOTSUP) || (errno == EOPNOTSUPP)) &&
2855 !follow_symlinks;
Victor Stinner8c62be82010-05-06 00:08:46 +00002856 }
2857 else
Thomas Wouters477c8d52006-05-27 19:21:47 +00002858#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002859 result = chmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002860 Py_END_ALLOW_THREADS
2861
2862 if (result) {
2863#ifdef HAVE_FCHMODAT
2864 if (fchmodat_nofollow_unsupported) {
2865 if (dir_fd != DEFAULT_DIR_FD)
2866 dir_fd_and_follow_symlinks_invalid("chmod",
2867 dir_fd, follow_symlinks);
2868 else
2869 follow_symlinks_specified("chmod", follow_symlinks);
2870 }
2871 else
2872#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002873 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002874 }
2875#endif
2876
Larry Hastings2f936352014-08-05 14:04:04 +10002877 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002878}
2879
Larry Hastings9cf065c2012-06-22 16:30:09 -07002880
Christian Heimes4e30a842007-11-30 22:12:06 +00002881#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002882/*[clinic input]
2883os.fchmod
2884
2885 fd: int
2886 mode: int
2887
2888Change the access permissions of the file given by file descriptor fd.
2889
2890Equivalent to os.chmod(fd, mode).
2891[clinic start generated code]*/
2892
Larry Hastings2f936352014-08-05 14:04:04 +10002893static PyObject *
2894os_fchmod_impl(PyModuleDef *module, int fd, int mode)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002895/*[clinic end generated code: output=2ee31ca226d1ed33 input=8ab11975ca01ee5b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002896{
2897 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00002898 int async_err = 0;
2899
2900 do {
2901 Py_BEGIN_ALLOW_THREADS
2902 res = fchmod(fd, mode);
2903 Py_END_ALLOW_THREADS
2904 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
2905 if (res != 0)
2906 return (!async_err) ? posix_error() : NULL;
2907
Victor Stinner8c62be82010-05-06 00:08:46 +00002908 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00002909}
2910#endif /* HAVE_FCHMOD */
2911
Larry Hastings2f936352014-08-05 14:04:04 +10002912
Christian Heimes4e30a842007-11-30 22:12:06 +00002913#ifdef HAVE_LCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002914/*[clinic input]
2915os.lchmod
2916
2917 path: path_t
2918 mode: int
2919
2920Change the access permissions of a file, without following symbolic links.
2921
2922If path is a symlink, this affects the link itself rather than the target.
2923Equivalent to chmod(path, mode, follow_symlinks=False)."
2924[clinic start generated code]*/
2925
Larry Hastings2f936352014-08-05 14:04:04 +10002926static PyObject *
2927os_lchmod_impl(PyModuleDef *module, path_t *path, int mode)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002928/*[clinic end generated code: output=7c0cc46588d89e46 input=90c5663c7465d24f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002929{
Victor Stinner8c62be82010-05-06 00:08:46 +00002930 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00002931 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10002932 res = lchmod(path->narrow, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +00002933 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01002934 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10002935 path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01002936 return NULL;
2937 }
Victor Stinner8c62be82010-05-06 00:08:46 +00002938 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00002939}
2940#endif /* HAVE_LCHMOD */
2941
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002942
Thomas Wouterscf297e42007-02-23 15:07:44 +00002943#ifdef HAVE_CHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10002944/*[clinic input]
2945os.chflags
2946
2947 path: path_t
2948 flags: unsigned_long(bitwise=True)
2949 follow_symlinks: bool=True
2950
2951Set file flags.
2952
2953If follow_symlinks is False, and the last element of the path is a symbolic
2954 link, chflags will change flags on the symbolic link itself instead of the
2955 file the link points to.
2956follow_symlinks may not be implemented on your platform. If it is
2957unavailable, using it will raise a NotImplementedError.
2958
2959[clinic start generated code]*/
2960
Larry Hastings2f936352014-08-05 14:04:04 +10002961static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002962os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags,
2963 int follow_symlinks)
2964/*[clinic end generated code: output=ff2d6e73534a95b9 input=0327e29feb876236]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002965{
2966 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002967
2968#ifndef HAVE_LCHFLAGS
2969 if (follow_symlinks_specified("chflags", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002970 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002971#endif
2972
Victor Stinner8c62be82010-05-06 00:08:46 +00002973 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07002974#ifdef HAVE_LCHFLAGS
2975 if (!follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002976 result = lchflags(path->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002977 else
2978#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002979 result = chflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00002980 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07002981
Larry Hastings2f936352014-08-05 14:04:04 +10002982 if (result)
2983 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002984
Larry Hastings2f936352014-08-05 14:04:04 +10002985 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00002986}
2987#endif /* HAVE_CHFLAGS */
2988
Larry Hastings2f936352014-08-05 14:04:04 +10002989
Thomas Wouterscf297e42007-02-23 15:07:44 +00002990#ifdef HAVE_LCHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10002991/*[clinic input]
2992os.lchflags
2993
2994 path: path_t
2995 flags: unsigned_long(bitwise=True)
2996
2997Set file flags.
2998
2999This function will not follow symbolic links.
3000Equivalent to chflags(path, flags, follow_symlinks=False).
3001[clinic start generated code]*/
3002
Larry Hastings2f936352014-08-05 14:04:04 +10003003static PyObject *
3004os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003005/*[clinic end generated code: output=6741322fb949661b input=f9f82ea8b585ca9d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003006{
Victor Stinner8c62be82010-05-06 00:08:46 +00003007 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003008 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003009 res = lchflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003010 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003011 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003012 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003013 }
Victor Stinner292c8352012-10-30 02:17:38 +01003014 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003015}
3016#endif /* HAVE_LCHFLAGS */
3017
Larry Hastings2f936352014-08-05 14:04:04 +10003018
Martin v. Löwis244edc82001-10-04 22:44:26 +00003019#ifdef HAVE_CHROOT
Larry Hastings2f936352014-08-05 14:04:04 +10003020/*[clinic input]
3021os.chroot
3022 path: path_t
3023
3024Change root directory to path.
3025
3026[clinic start generated code]*/
3027
Larry Hastings2f936352014-08-05 14:04:04 +10003028static PyObject *
3029os_chroot_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003030/*[clinic end generated code: output=b6dbfabe74ecaa9d input=14822965652c3dc3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003031{
3032 int res;
3033 Py_BEGIN_ALLOW_THREADS
3034 res = chroot(path->narrow);
3035 Py_END_ALLOW_THREADS
3036 if (res < 0)
3037 return path_error(path);
3038 Py_RETURN_NONE;
3039}
3040#endif /* HAVE_CHROOT */
3041
Martin v. Löwis244edc82001-10-04 22:44:26 +00003042
Guido van Rossum21142a01999-01-08 21:05:37 +00003043#ifdef HAVE_FSYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003044/*[clinic input]
3045os.fsync
3046
3047 fd: fildes
3048
3049Force write of fd to disk.
3050[clinic start generated code]*/
3051
Larry Hastings2f936352014-08-05 14:04:04 +10003052static PyObject *
3053os_fsync_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003054/*[clinic end generated code: output=83a350851064aea7 input=21c3645c056967f2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003055{
3056 return posix_fildes_fd(fd, fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003057}
3058#endif /* HAVE_FSYNC */
3059
Larry Hastings2f936352014-08-05 14:04:04 +10003060
Ross Lagerwall7807c352011-03-17 20:20:30 +02003061#ifdef HAVE_SYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003062/*[clinic input]
3063os.sync
3064
3065Force write of everything to disk.
3066[clinic start generated code]*/
3067
Larry Hastings2f936352014-08-05 14:04:04 +10003068static PyObject *
3069os_sync_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003070/*[clinic end generated code: output=ba524f656c201c40 input=84749fe5e9b404ff]*/
Ross Lagerwall7807c352011-03-17 20:20:30 +02003071{
3072 Py_BEGIN_ALLOW_THREADS
3073 sync();
3074 Py_END_ALLOW_THREADS
3075 Py_RETURN_NONE;
3076}
Larry Hastings2f936352014-08-05 14:04:04 +10003077#endif /* HAVE_SYNC */
3078
Ross Lagerwall7807c352011-03-17 20:20:30 +02003079
Guido van Rossum21142a01999-01-08 21:05:37 +00003080#ifdef HAVE_FDATASYNC
Guido van Rossum7f58e2e2000-09-22 17:26:14 +00003081#ifdef __hpux
Guido van Rossumecc23b02000-09-22 16:01:05 +00003082extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
3083#endif
3084
Larry Hastings2f936352014-08-05 14:04:04 +10003085/*[clinic input]
3086os.fdatasync
3087
3088 fd: fildes
3089
3090Force write of fd to disk without forcing update of metadata.
3091[clinic start generated code]*/
3092
Larry Hastings2f936352014-08-05 14:04:04 +10003093static PyObject *
3094os_fdatasync_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003095/*[clinic end generated code: output=e0f04a3aff515b75 input=bc74791ee54dd291]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003096{
3097 return posix_fildes_fd(fd, fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003098}
3099#endif /* HAVE_FDATASYNC */
3100
3101
Fredrik Lundh10723342000-07-10 16:38:09 +00003102#ifdef HAVE_CHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003103/*[clinic input]
3104os.chown
3105
3106 path : path_t(allow_fd='PATH_HAVE_FCHOWN')
3107 Path to be examined; can be string, bytes, or open-file-descriptor int.
3108
3109 uid: uid_t
3110
3111 gid: gid_t
3112
3113 *
3114
3115 dir_fd : dir_fd(requires='fchownat') = None
3116 If not None, it should be a file descriptor open to a directory,
3117 and path should be relative; path will then be relative to that
3118 directory.
3119
3120 follow_symlinks: bool = True
3121 If False, and the last element of the path is a symbolic link,
3122 stat will examine the symbolic link itself instead of the file
3123 the link points to.
3124
3125Change the owner and group id of path to the numeric uid and gid.\
3126
3127path may always be specified as a string.
3128On some platforms, path may also be specified as an open file descriptor.
3129 If this functionality is unavailable, using it raises an exception.
3130If dir_fd is not None, it should be a file descriptor open to a directory,
3131 and path should be relative; path will then be relative to that directory.
3132If follow_symlinks is False, and the last element of the path is a symbolic
3133 link, chown will modify the symbolic link itself instead of the file the
3134 link points to.
3135It is an error to use dir_fd or follow_symlinks when specifying path as
3136 an open file descriptor.
3137dir_fd and follow_symlinks may not be implemented on your platform.
3138 If they are unavailable, using them will raise a NotImplementedError.
3139
3140[clinic start generated code]*/
3141
Larry Hastings2f936352014-08-05 14:04:04 +10003142static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04003143os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid,
3144 int dir_fd, int follow_symlinks)
3145/*[clinic end generated code: output=e0a4559f394dbd91 input=a61cc35574814d5d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003146{
3147 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003148
3149#if !(defined(HAVE_LCHOWN) || defined(HAVE_FCHOWNAT))
3150 if (follow_symlinks_specified("chown", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003151 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003152#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003153 if (dir_fd_and_fd_invalid("chown", dir_fd, path->fd) ||
3154 fd_and_follow_symlinks_invalid("chown", path->fd, follow_symlinks))
3155 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003156
3157#ifdef __APPLE__
3158 /*
3159 * This is for Mac OS X 10.3, which doesn't have lchown.
3160 * (But we still have an lchown symbol because of weak-linking.)
3161 * It doesn't have fchownat either. So there's no possibility
3162 * of a graceful failover.
Georg Brandlf7875592012-06-24 13:58:31 +02003163 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003164 if ((!follow_symlinks) && (lchown == NULL)) {
3165 follow_symlinks_specified("chown", follow_symlinks);
Larry Hastings2f936352014-08-05 14:04:04 +10003166 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003167 }
3168#endif
3169
Victor Stinner8c62be82010-05-06 00:08:46 +00003170 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003171#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003172 if (path->fd != -1)
3173 result = fchown(path->fd, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003174 else
3175#endif
3176#ifdef HAVE_LCHOWN
3177 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003178 result = lchown(path->narrow, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003179 else
3180#endif
3181#ifdef HAVE_FCHOWNAT
3182 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003183 result = fchownat(dir_fd, path->narrow, uid, gid,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003184 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3185 else
3186#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003187 result = chown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00003188 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003189
Larry Hastings2f936352014-08-05 14:04:04 +10003190 if (result)
3191 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003192
Larry Hastings2f936352014-08-05 14:04:04 +10003193 Py_RETURN_NONE;
Guido van Rossumb6775db1994-08-01 11:34:53 +00003194}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00003195#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00003196
Larry Hastings2f936352014-08-05 14:04:04 +10003197
Christian Heimes4e30a842007-11-30 22:12:06 +00003198#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003199/*[clinic input]
3200os.fchown
3201
3202 fd: int
3203 uid: uid_t
3204 gid: gid_t
3205
3206Change the owner and group id of the file specified by file descriptor.
3207
3208Equivalent to os.chown(fd, uid, gid).
3209
3210[clinic start generated code]*/
3211
Larry Hastings2f936352014-08-05 14:04:04 +10003212static PyObject *
3213os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003214/*[clinic end generated code: output=7545abf8f6086d76 input=3af544ba1b13a0d7]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003215{
Victor Stinner8c62be82010-05-06 00:08:46 +00003216 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00003217 int async_err = 0;
3218
3219 do {
3220 Py_BEGIN_ALLOW_THREADS
3221 res = fchown(fd, uid, gid);
3222 Py_END_ALLOW_THREADS
3223 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
3224 if (res != 0)
3225 return (!async_err) ? posix_error() : NULL;
3226
Victor Stinner8c62be82010-05-06 00:08:46 +00003227 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003228}
3229#endif /* HAVE_FCHOWN */
3230
Larry Hastings2f936352014-08-05 14:04:04 +10003231
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00003232#ifdef HAVE_LCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003233/*[clinic input]
3234os.lchown
3235
3236 path : path_t
3237 uid: uid_t
3238 gid: gid_t
3239
3240Change the owner and group id of path to the numeric uid and gid.
3241
3242This function will not follow symbolic links.
3243Equivalent to os.chown(path, uid, gid, follow_symlinks=False).
3244[clinic start generated code]*/
3245
Larry Hastings2f936352014-08-05 14:04:04 +10003246static PyObject *
3247os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003248/*[clinic end generated code: output=bb0d2da1579ac275 input=b1c6014d563a7161]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003249{
Victor Stinner8c62be82010-05-06 00:08:46 +00003250 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003251 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003252 res = lchown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00003253 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003254 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003255 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003256 }
Larry Hastings2f936352014-08-05 14:04:04 +10003257 Py_RETURN_NONE;
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00003258}
3259#endif /* HAVE_LCHOWN */
3260
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003261
Barry Warsaw53699e91996-12-10 23:23:01 +00003262static PyObject *
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003263posix_getcwd(int use_bytes)
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003264{
Victor Stinner8c62be82010-05-06 00:08:46 +00003265 char buf[1026];
3266 char *res;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003267
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003268#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003269 if (!use_bytes) {
3270 wchar_t wbuf[1026];
3271 wchar_t *wbuf2 = wbuf;
3272 PyObject *resobj;
3273 DWORD len;
3274 Py_BEGIN_ALLOW_THREADS
Victor Stinner75875072013-11-24 19:23:25 +01003275 len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00003276 /* If the buffer is large enough, len does not include the
3277 terminating \0. If the buffer is too small, len includes
3278 the space needed for the terminator. */
Victor Stinner75875072013-11-24 19:23:25 +01003279 if (len >= Py_ARRAY_LENGTH(wbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02003280 wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00003281 if (wbuf2)
3282 len = GetCurrentDirectoryW(len, wbuf2);
3283 }
3284 Py_END_ALLOW_THREADS
3285 if (!wbuf2) {
3286 PyErr_NoMemory();
3287 return NULL;
3288 }
3289 if (!len) {
Victor Stinnerb024e842012-10-31 22:24:06 +01003290 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003291 PyMem_RawFree(wbuf2);
Victor Stinnerb024e842012-10-31 22:24:06 +01003292 return PyErr_SetFromWindowsErr(0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003293 }
3294 resobj = PyUnicode_FromWideChar(wbuf2, len);
Victor Stinnerb024e842012-10-31 22:24:06 +01003295 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003296 PyMem_RawFree(wbuf2);
Victor Stinner8c62be82010-05-06 00:08:46 +00003297 return resobj;
3298 }
Victor Stinnerf7c5ae22011-11-16 23:43:07 +01003299
3300 if (win32_warn_bytes_api())
3301 return NULL;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003302#endif
3303
Victor Stinner8c62be82010-05-06 00:08:46 +00003304 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003305 res = getcwd(buf, sizeof buf);
Victor Stinner8c62be82010-05-06 00:08:46 +00003306 Py_END_ALLOW_THREADS
3307 if (res == NULL)
3308 return posix_error();
3309 if (use_bytes)
3310 return PyBytes_FromStringAndSize(buf, strlen(buf));
Victor Stinner97c18ab2010-05-07 16:34:53 +00003311 return PyUnicode_DecodeFSDefault(buf);
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003312}
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003313
Larry Hastings2f936352014-08-05 14:04:04 +10003314
3315/*[clinic input]
3316os.getcwd
3317
3318Return a unicode string representing the current working directory.
3319[clinic start generated code]*/
3320
Larry Hastings2f936352014-08-05 14:04:04 +10003321static PyObject *
3322os_getcwd_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003323/*[clinic end generated code: output=efe3a8c0121525ea input=f069211bb70e3d39]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003324{
3325 return posix_getcwd(0);
3326}
3327
Larry Hastings2f936352014-08-05 14:04:04 +10003328
3329/*[clinic input]
3330os.getcwdb
3331
3332Return a bytes string representing the current working directory.
3333[clinic start generated code]*/
3334
Larry Hastings2f936352014-08-05 14:04:04 +10003335static PyObject *
3336os_getcwdb_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003337/*[clinic end generated code: output=7fce42ee4b2a296a input=f6f6a378dad3d9cb]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003338{
3339 return posix_getcwd(1);
3340}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003341
Larry Hastings2f936352014-08-05 14:04:04 +10003342
Larry Hastings9cf065c2012-06-22 16:30:09 -07003343#if ((!defined(HAVE_LINK)) && defined(MS_WINDOWS))
3344#define HAVE_LINK 1
3345#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003346
Guido van Rossumb6775db1994-08-01 11:34:53 +00003347#ifdef HAVE_LINK
Larry Hastings2f936352014-08-05 14:04:04 +10003348/*[clinic input]
3349
3350os.link
3351
3352 src : path_t
3353 dst : path_t
3354 *
3355 src_dir_fd : dir_fd = None
3356 dst_dir_fd : dir_fd = None
3357 follow_symlinks: bool = True
3358
3359Create a hard link to a file.
3360
3361If either src_dir_fd or dst_dir_fd is not None, it should be a file
3362 descriptor open to a directory, and the respective path string (src or dst)
3363 should be relative; the path will then be relative to that directory.
3364If follow_symlinks is False, and the last element of src is a symbolic
3365 link, link will create a link to the symbolic link itself instead of the
3366 file the link points to.
3367src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your
3368 platform. If they are unavailable, using them will raise a
3369 NotImplementedError.
3370[clinic start generated code]*/
3371
Larry Hastings2f936352014-08-05 14:04:04 +10003372static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04003373os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd,
3374 int dst_dir_fd, int follow_symlinks)
3375/*[clinic end generated code: output=f47a7e88f7b391b6 input=b0095ebbcbaa7e04]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003376{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003377#ifdef MS_WINDOWS
3378 BOOL result;
3379#else
3380 int result;
3381#endif
3382
Larry Hastings9cf065c2012-06-22 16:30:09 -07003383#ifndef HAVE_LINKAT
3384 if ((src_dir_fd != DEFAULT_DIR_FD) || (dst_dir_fd != DEFAULT_DIR_FD)) {
3385 argument_unavailable_error("link", "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10003386 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003387 }
3388#endif
3389
Larry Hastings2f936352014-08-05 14:04:04 +10003390 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003391 PyErr_SetString(PyExc_NotImplementedError,
3392 "link: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10003393 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003394 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003395
Brian Curtin1b9df392010-11-24 20:24:31 +00003396#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003397 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003398 if (src->wide)
3399 result = CreateHardLinkW(dst->wide, src->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003400 else
Larry Hastings2f936352014-08-05 14:04:04 +10003401 result = CreateHardLinkA(dst->narrow, src->narrow, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003402 Py_END_ALLOW_THREADS
Brian Curtin1b9df392010-11-24 20:24:31 +00003403
Larry Hastings2f936352014-08-05 14:04:04 +10003404 if (!result)
3405 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003406#else
3407 Py_BEGIN_ALLOW_THREADS
Larry Hastings67cbf7b2012-06-22 17:06:48 -07003408#ifdef HAVE_LINKAT
Larry Hastings9cf065c2012-06-22 16:30:09 -07003409 if ((src_dir_fd != DEFAULT_DIR_FD) ||
3410 (dst_dir_fd != DEFAULT_DIR_FD) ||
3411 (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003412 result = linkat(src_dir_fd, src->narrow,
3413 dst_dir_fd, dst->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003414 follow_symlinks ? AT_SYMLINK_FOLLOW : 0);
3415 else
3416#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003417 result = link(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003418 Py_END_ALLOW_THREADS
Brian Curtinfc889c42010-11-28 23:59:46 +00003419
Larry Hastings2f936352014-08-05 14:04:04 +10003420 if (result)
3421 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003422#endif
3423
Larry Hastings2f936352014-08-05 14:04:04 +10003424 Py_RETURN_NONE;
Brian Curtin1b9df392010-11-24 20:24:31 +00003425}
Larry Hastings9cf065c2012-06-22 16:30:09 -07003426#endif
3427
Brian Curtin1b9df392010-11-24 20:24:31 +00003428
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003429#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
Barry Warsaw53699e91996-12-10 23:23:01 +00003430static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07003431_listdir_windows_no_opendir(path_t *path, PyObject *list)
Guido van Rossumb6775db1994-08-01 11:34:53 +00003432{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003433 PyObject *v;
3434 HANDLE hFindFile = INVALID_HANDLE_VALUE;
3435 BOOL result;
3436 WIN32_FIND_DATA FileData;
Victor Stinner75875072013-11-24 19:23:25 +01003437 char namebuf[MAX_PATH+4]; /* Overallocate for "\*.*" */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003438 char *bufptr = namebuf;
3439 /* only claim to have space for MAX_PATH */
Victor Stinner75875072013-11-24 19:23:25 +01003440 Py_ssize_t len = Py_ARRAY_LENGTH(namebuf)-4;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003441 PyObject *po = NULL;
3442 wchar_t *wnamebuf = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003443
Gregory P. Smith40a21602013-03-20 20:52:50 -07003444 if (!path->narrow) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003445 WIN32_FIND_DATAW wFileData;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003446 wchar_t *po_wchars;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003447
Gregory P. Smith40a21602013-03-20 20:52:50 -07003448 if (!path->wide) { /* Default arg: "." */
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003449 po_wchars = L".";
3450 len = 1;
3451 } else {
Gregory P. Smith40a21602013-03-20 20:52:50 -07003452 po_wchars = path->wide;
3453 len = wcslen(path->wide);
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003454 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003455 /* The +5 is so we can append "\\*.*\0" */
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003456 wnamebuf = PyMem_New(wchar_t, len + 5);
Victor Stinner8c62be82010-05-06 00:08:46 +00003457 if (!wnamebuf) {
3458 PyErr_NoMemory();
Larry Hastings9cf065c2012-06-22 16:30:09 -07003459 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003460 }
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003461 wcscpy(wnamebuf, po_wchars);
Victor Stinner8c62be82010-05-06 00:08:46 +00003462 if (len > 0) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02003463 wchar_t wch = wnamebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01003464 if (wch != SEP && wch != ALTSEP && wch != L':')
3465 wnamebuf[len++] = SEP;
Victor Stinner8c62be82010-05-06 00:08:46 +00003466 wcscpy(wnamebuf + len, L"*.*");
3467 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003468 if ((list = PyList_New(0)) == NULL) {
3469 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003470 }
Antoine Pitroub73caab2010-08-09 23:39:31 +00003471 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003472 hFindFile = FindFirstFileW(wnamebuf, &wFileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00003473 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003474 if (hFindFile == INVALID_HANDLE_VALUE) {
3475 int error = GetLastError();
Larry Hastings9cf065c2012-06-22 16:30:09 -07003476 if (error == ERROR_FILE_NOT_FOUND)
3477 goto exit;
3478 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003479 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003480 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003481 }
3482 do {
3483 /* Skip over . and .. */
3484 if (wcscmp(wFileData.cFileName, L".") != 0 &&
3485 wcscmp(wFileData.cFileName, L"..") != 0) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003486 v = PyUnicode_FromWideChar(wFileData.cFileName,
3487 wcslen(wFileData.cFileName));
Victor Stinner8c62be82010-05-06 00:08:46 +00003488 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003489 Py_DECREF(list);
3490 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003491 break;
3492 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003493 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003494 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003495 Py_DECREF(list);
3496 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003497 break;
3498 }
3499 Py_DECREF(v);
3500 }
3501 Py_BEGIN_ALLOW_THREADS
3502 result = FindNextFileW(hFindFile, &wFileData);
3503 Py_END_ALLOW_THREADS
3504 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
3505 it got to the end of the directory. */
3506 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003507 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003508 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003509 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003510 }
3511 } while (result == TRUE);
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00003512
Larry Hastings9cf065c2012-06-22 16:30:09 -07003513 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003514 }
Gregory P. Smith40a21602013-03-20 20:52:50 -07003515 strcpy(namebuf, path->narrow);
3516 len = path->length;
Victor Stinner8c62be82010-05-06 00:08:46 +00003517 if (len > 0) {
3518 char ch = namebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01003519 if (ch != '\\' && ch != '/' && ch != ':')
3520 namebuf[len++] = '\\';
Victor Stinner8c62be82010-05-06 00:08:46 +00003521 strcpy(namebuf + len, "*.*");
3522 }
Guido van Rossumb6775db1994-08-01 11:34:53 +00003523
Larry Hastings9cf065c2012-06-22 16:30:09 -07003524 if ((list = PyList_New(0)) == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +00003525 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00003526
Antoine Pitroub73caab2010-08-09 23:39:31 +00003527 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003528 hFindFile = FindFirstFile(namebuf, &FileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00003529 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003530 if (hFindFile == INVALID_HANDLE_VALUE) {
3531 int error = GetLastError();
3532 if (error == ERROR_FILE_NOT_FOUND)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003533 goto exit;
3534 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003535 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003536 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003537 }
3538 do {
3539 /* Skip over . and .. */
3540 if (strcmp(FileData.cFileName, ".") != 0 &&
3541 strcmp(FileData.cFileName, "..") != 0) {
3542 v = PyBytes_FromString(FileData.cFileName);
3543 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003544 Py_DECREF(list);
3545 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003546 break;
3547 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003548 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003549 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003550 Py_DECREF(list);
3551 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003552 break;
3553 }
3554 Py_DECREF(v);
3555 }
3556 Py_BEGIN_ALLOW_THREADS
3557 result = FindNextFile(hFindFile, &FileData);
3558 Py_END_ALLOW_THREADS
3559 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
3560 it got to the end of the directory. */
3561 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003562 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003563 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003564 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003565 }
3566 } while (result == TRUE);
Guido van Rossumb6775db1994-08-01 11:34:53 +00003567
Larry Hastings9cf065c2012-06-22 16:30:09 -07003568exit:
3569 if (hFindFile != INVALID_HANDLE_VALUE) {
3570 if (FindClose(hFindFile) == FALSE) {
3571 if (list != NULL) {
3572 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003573 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003574 }
3575 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003576 }
Victor Stinnerb6404912013-07-07 16:21:41 +02003577 PyMem_Free(wnamebuf);
Guido van Rossumb6775db1994-08-01 11:34:53 +00003578
Larry Hastings9cf065c2012-06-22 16:30:09 -07003579 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003580} /* end of _listdir_windows_no_opendir */
3581
3582#else /* thus POSIX, ie: not (MS_WINDOWS and not HAVE_OPENDIR) */
3583
3584static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07003585_posix_listdir(path_t *path, PyObject *list)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003586{
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003587 PyObject *v;
3588 DIR *dirp = NULL;
3589 struct dirent *ep;
3590 int return_str; /* if false, return bytes */
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003591#ifdef HAVE_FDOPENDIR
3592 int fd = -1;
3593#endif
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003594
Victor Stinner8c62be82010-05-06 00:08:46 +00003595 errno = 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003596#ifdef HAVE_FDOPENDIR
Gregory P. Smith40a21602013-03-20 20:52:50 -07003597 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003598 /* closedir() closes the FD, so we duplicate it */
Victor Stinnerdaf45552013-08-28 00:53:59 +02003599 fd = _Py_dup(path->fd);
Victor Stinnerf3266652013-12-19 13:24:49 +01003600 if (fd == -1)
3601 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003602
Larry Hastingsfdaea062012-06-25 04:42:23 -07003603 return_str = 1;
3604
Larry Hastings9cf065c2012-06-22 16:30:09 -07003605 Py_BEGIN_ALLOW_THREADS
3606 dirp = fdopendir(fd);
3607 Py_END_ALLOW_THREADS
3608 }
3609 else
3610#endif
3611 {
Larry Hastingsfdaea062012-06-25 04:42:23 -07003612 char *name;
Gregory P. Smith40a21602013-03-20 20:52:50 -07003613 if (path->narrow) {
3614 name = path->narrow;
Larry Hastingsfdaea062012-06-25 04:42:23 -07003615 /* only return bytes if they specified a bytes object */
Gregory P. Smith40a21602013-03-20 20:52:50 -07003616 return_str = !(PyBytes_Check(path->object));
Larry Hastingsfdaea062012-06-25 04:42:23 -07003617 }
3618 else {
3619 name = ".";
3620 return_str = 1;
3621 }
3622
Larry Hastings9cf065c2012-06-22 16:30:09 -07003623 Py_BEGIN_ALLOW_THREADS
3624 dirp = opendir(name);
3625 Py_END_ALLOW_THREADS
3626 }
3627
3628 if (dirp == NULL) {
Gregory P. Smith40a21602013-03-20 20:52:50 -07003629 list = path_error(path);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003630#ifdef HAVE_FDOPENDIR
3631 if (fd != -1) {
3632 Py_BEGIN_ALLOW_THREADS
3633 close(fd);
3634 Py_END_ALLOW_THREADS
3635 }
3636#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07003637 goto exit;
3638 }
3639 if ((list = PyList_New(0)) == NULL) {
3640 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003641 }
3642 for (;;) {
3643 errno = 0;
3644 Py_BEGIN_ALLOW_THREADS
3645 ep = readdir(dirp);
3646 Py_END_ALLOW_THREADS
3647 if (ep == NULL) {
3648 if (errno == 0) {
3649 break;
3650 } else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003651 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003652 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003653 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003654 }
3655 }
3656 if (ep->d_name[0] == '.' &&
3657 (NAMLEN(ep) == 1 ||
3658 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
3659 continue;
Larry Hastingsfdaea062012-06-25 04:42:23 -07003660 if (return_str)
Victor Stinnera45598a2010-05-14 16:35:39 +00003661 v = PyUnicode_DecodeFSDefaultAndSize(ep->d_name, NAMLEN(ep));
3662 else
3663 v = PyBytes_FromStringAndSize(ep->d_name, NAMLEN(ep));
Victor Stinner8c62be82010-05-06 00:08:46 +00003664 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003665 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00003666 break;
3667 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003668 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003669 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003670 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00003671 break;
3672 }
3673 Py_DECREF(v);
3674 }
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00003675
Larry Hastings9cf065c2012-06-22 16:30:09 -07003676exit:
3677 if (dirp != NULL) {
3678 Py_BEGIN_ALLOW_THREADS
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003679#ifdef HAVE_FDOPENDIR
Larry Hastings9cf065c2012-06-22 16:30:09 -07003680 if (fd > -1)
3681 rewinddir(dirp);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003682#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07003683 closedir(dirp);
3684 Py_END_ALLOW_THREADS
3685 }
3686
Larry Hastings9cf065c2012-06-22 16:30:09 -07003687 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003688} /* end of _posix_listdir */
3689#endif /* which OS */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00003690
Larry Hastings2f936352014-08-05 14:04:04 +10003691
3692/*[clinic input]
3693os.listdir
3694
3695 path : path_t(nullable=True, allow_fd='PATH_HAVE_FDOPENDIR') = None
3696
3697Return a list containing the names of the files in the directory.
3698
3699path can be specified as either str or bytes. If path is bytes,
3700 the filenames returned will also be bytes; in all other circumstances
3701 the filenames returned will be str.
3702If path is None, uses the path='.'.
3703On some platforms, path may also be specified as an open file descriptor;\
3704 the file descriptor must refer to a directory.
3705 If this functionality is unavailable, using it raises NotImplementedError.
3706
3707The list is in arbitrary order. It does not include the special
3708entries '.' and '..' even if they are present in the directory.
3709
3710
3711[clinic start generated code]*/
3712
Larry Hastings2f936352014-08-05 14:04:04 +10003713static PyObject *
3714os_listdir_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003715/*[clinic end generated code: output=1fbe67c1f780c8b7 input=09e300416e3cd729]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003716{
3717#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
3718 return _listdir_windows_no_opendir(path, NULL);
3719#else
3720 return _posix_listdir(path, NULL);
3721#endif
3722}
3723
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00003724#ifdef MS_WINDOWS
Mark Hammondef8b6542001-05-13 08:04:26 +00003725/* A helper function for abspath on win32 */
Larry Hastings2f936352014-08-05 14:04:04 +10003726/* AC 3.5: probably just convert to using path converter */
Mark Hammondef8b6542001-05-13 08:04:26 +00003727static PyObject *
3728posix__getfullpathname(PyObject *self, PyObject *args)
3729{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003730 const char *path;
Victor Stinner75875072013-11-24 19:23:25 +01003731 char outbuf[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00003732 char *temp;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003733 PyObject *po;
3734
3735 if (PyArg_ParseTuple(args, "U|:_getfullpathname", &po))
3736 {
3737 wchar_t *wpath;
Victor Stinner75875072013-11-24 19:23:25 +01003738 wchar_t woutbuf[MAX_PATH], *woutbufp = woutbuf;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003739 wchar_t *wtemp;
Victor Stinner8c62be82010-05-06 00:08:46 +00003740 DWORD result;
3741 PyObject *v;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003742
3743 wpath = PyUnicode_AsUnicode(po);
3744 if (wpath == NULL)
3745 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003746 result = GetFullPathNameW(wpath,
Victor Stinner63941882011-09-29 00:42:28 +02003747 Py_ARRAY_LENGTH(woutbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00003748 woutbuf, &wtemp);
Victor Stinner63941882011-09-29 00:42:28 +02003749 if (result > Py_ARRAY_LENGTH(woutbuf)) {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003750 woutbufp = PyMem_New(wchar_t, result);
Victor Stinner8c62be82010-05-06 00:08:46 +00003751 if (!woutbufp)
3752 return PyErr_NoMemory();
3753 result = GetFullPathNameW(wpath, result, woutbufp, &wtemp);
3754 }
3755 if (result)
Victor Stinner9d3b93b2011-11-22 02:27:30 +01003756 v = PyUnicode_FromWideChar(woutbufp, wcslen(woutbufp));
Victor Stinner8c62be82010-05-06 00:08:46 +00003757 else
Victor Stinnereb5657a2011-09-30 01:44:27 +02003758 v = win32_error_object("GetFullPathNameW", po);
Victor Stinner8c62be82010-05-06 00:08:46 +00003759 if (woutbufp != woutbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003760 PyMem_Free(woutbufp);
Victor Stinner8c62be82010-05-06 00:08:46 +00003761 return v;
3762 }
3763 /* Drop the argument parsing error as narrow strings
3764 are also valid. */
3765 PyErr_Clear();
Victor Stinnereb5657a2011-09-30 01:44:27 +02003766
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003767 if (!PyArg_ParseTuple (args, "y:_getfullpathname",
3768 &path))
Victor Stinner8c62be82010-05-06 00:08:46 +00003769 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003770 if (win32_warn_bytes_api())
3771 return NULL;
Victor Stinner63941882011-09-29 00:42:28 +02003772 if (!GetFullPathName(path, Py_ARRAY_LENGTH(outbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00003773 outbuf, &temp)) {
3774 win32_error("GetFullPathName", path);
Victor Stinner8c62be82010-05-06 00:08:46 +00003775 return NULL;
3776 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003777 if (PyUnicode_Check(PyTuple_GetItem(args, 0))) {
3778 return PyUnicode_Decode(outbuf, strlen(outbuf),
3779 Py_FileSystemDefaultEncoding, NULL);
3780 }
3781 return PyBytes_FromString(outbuf);
Larry Hastings2f936352014-08-05 14:04:04 +10003782}
Brian Curtind40e6f72010-07-08 21:39:08 +00003783
Brian Curtind25aef52011-06-13 15:16:04 -05003784
Larry Hastings2f936352014-08-05 14:04:04 +10003785/*[clinic input]
3786os._getfinalpathname
Brian Curtinf5e76d02010-11-24 13:14:05 +00003787
Larry Hastings2f936352014-08-05 14:04:04 +10003788 path: unicode
3789 /
3790
3791A helper function for samepath on windows.
3792[clinic start generated code]*/
3793
Larry Hastings2f936352014-08-05 14:04:04 +10003794static PyObject *
3795os__getfinalpathname_impl(PyModuleDef *module, PyObject *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003796/*[clinic end generated code: output=8be81a5f51a34bcf input=71d5e89334891bf4]*/
Brian Curtind40e6f72010-07-08 21:39:08 +00003797{
3798 HANDLE hFile;
3799 int buf_size;
3800 wchar_t *target_path;
3801 int result_length;
Larry Hastings2f936352014-08-05 14:04:04 +10003802 PyObject *result;
3803 wchar_t *path_wchar;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003804
Larry Hastings2f936352014-08-05 14:04:04 +10003805 path_wchar = PyUnicode_AsUnicode(path);
3806 if (path_wchar == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02003807 return NULL;
Brian Curtind40e6f72010-07-08 21:39:08 +00003808
Brian Curtind40e6f72010-07-08 21:39:08 +00003809 hFile = CreateFileW(
Larry Hastings2f936352014-08-05 14:04:04 +10003810 path_wchar,
Brian Curtind40e6f72010-07-08 21:39:08 +00003811 0, /* desired access */
3812 0, /* share mode */
3813 NULL, /* security attributes */
3814 OPEN_EXISTING,
3815 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
3816 FILE_FLAG_BACKUP_SEMANTICS,
3817 NULL);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003818
Victor Stinnereb5657a2011-09-30 01:44:27 +02003819 if(hFile == INVALID_HANDLE_VALUE)
Larry Hastings2f936352014-08-05 14:04:04 +10003820 return win32_error_object("CreateFileW", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003821
3822 /* We have a good handle to the target, use it to determine the
3823 target path name. */
Steve Dower2ea51c92015-03-20 21:49:12 -07003824 buf_size = GetFinalPathNameByHandleW(hFile, 0, 0, VOLUME_NAME_NT);
Brian Curtind40e6f72010-07-08 21:39:08 +00003825
3826 if(!buf_size)
Larry Hastings2f936352014-08-05 14:04:04 +10003827 return win32_error_object("GetFinalPathNameByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003828
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003829 target_path = PyMem_New(wchar_t, buf_size+1);
Brian Curtind40e6f72010-07-08 21:39:08 +00003830 if(!target_path)
3831 return PyErr_NoMemory();
3832
Steve Dower2ea51c92015-03-20 21:49:12 -07003833 result_length = GetFinalPathNameByHandleW(hFile, target_path,
3834 buf_size, VOLUME_NAME_DOS);
Brian Curtind40e6f72010-07-08 21:39:08 +00003835 if(!result_length)
Larry Hastings2f936352014-08-05 14:04:04 +10003836 return win32_error_object("GetFinalPathNamyByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003837
3838 if(!CloseHandle(hFile))
Larry Hastings2f936352014-08-05 14:04:04 +10003839 return win32_error_object("CloseHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003840
3841 target_path[result_length] = 0;
Victor Stinner9d3b93b2011-11-22 02:27:30 +01003842 result = PyUnicode_FromWideChar(target_path, result_length);
Victor Stinnerb6404912013-07-07 16:21:41 +02003843 PyMem_Free(target_path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003844 return result;
Larry Hastings2f936352014-08-05 14:04:04 +10003845}
Brian Curtin62857742010-09-06 17:07:27 +00003846
Brian Curtin95d028f2011-06-09 09:10:38 -05003847PyDoc_STRVAR(posix__isdir__doc__,
3848"Return true if the pathname refers to an existing directory.");
3849
Larry Hastings2f936352014-08-05 14:04:04 +10003850/* AC 3.5: convert using path converter */
Brian Curtin9c669cc2011-06-08 18:17:18 -05003851static PyObject *
3852posix__isdir(PyObject *self, PyObject *args)
3853{
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003854 const char *path;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003855 PyObject *po;
Brian Curtin9c669cc2011-06-08 18:17:18 -05003856 DWORD attributes;
3857
3858 if (PyArg_ParseTuple(args, "U|:_isdir", &po)) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02003859 wchar_t *wpath = PyUnicode_AsUnicode(po);
3860 if (wpath == NULL)
3861 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05003862
3863 attributes = GetFileAttributesW(wpath);
3864 if (attributes == INVALID_FILE_ATTRIBUTES)
3865 Py_RETURN_FALSE;
3866 goto check;
3867 }
3868 /* Drop the argument parsing error as narrow strings
3869 are also valid. */
3870 PyErr_Clear();
3871
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003872 if (!PyArg_ParseTuple(args, "y:_isdir", &path))
Brian Curtin9c669cc2011-06-08 18:17:18 -05003873 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01003874 if (win32_warn_bytes_api())
3875 return NULL;
Brian Curtin9c669cc2011-06-08 18:17:18 -05003876 attributes = GetFileAttributesA(path);
3877 if (attributes == INVALID_FILE_ATTRIBUTES)
3878 Py_RETURN_FALSE;
3879
3880check:
3881 if (attributes & FILE_ATTRIBUTE_DIRECTORY)
3882 Py_RETURN_TRUE;
3883 else
3884 Py_RETURN_FALSE;
3885}
Tim Golden6b528062013-08-01 12:44:00 +01003886
Tim Golden6b528062013-08-01 12:44:00 +01003887
Larry Hastings2f936352014-08-05 14:04:04 +10003888/*[clinic input]
3889os._getvolumepathname
3890
3891 path: unicode
3892
3893A helper function for ismount on Win32.
3894[clinic start generated code]*/
3895
Larry Hastings2f936352014-08-05 14:04:04 +10003896static PyObject *
3897os__getvolumepathname_impl(PyModuleDef *module, PyObject *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003898/*[clinic end generated code: output=79a0ba729f956dbe input=7eacadc40acbda6b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003899{
3900 PyObject *result;
3901 wchar_t *path_wchar, *mountpath=NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01003902 size_t buflen;
Tim Golden6b528062013-08-01 12:44:00 +01003903 BOOL ret;
3904
Larry Hastings2f936352014-08-05 14:04:04 +10003905 path_wchar = PyUnicode_AsUnicodeAndSize(path, &buflen);
3906 if (path_wchar == NULL)
Tim Golden6b528062013-08-01 12:44:00 +01003907 return NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01003908 buflen += 1;
Tim Golden6b528062013-08-01 12:44:00 +01003909
3910 /* Volume path should be shorter than entire path */
Victor Stinner6edddfa2013-11-24 19:22:57 +01003911 buflen = Py_MAX(buflen, MAX_PATH);
3912
3913 if (buflen > DWORD_MAX) {
3914 PyErr_SetString(PyExc_OverflowError, "path too long");
3915 return NULL;
3916 }
3917
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003918 mountpath = PyMem_New(wchar_t, buflen);
Tim Golden6b528062013-08-01 12:44:00 +01003919 if (mountpath == NULL)
3920 return PyErr_NoMemory();
3921
3922 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003923 ret = GetVolumePathNameW(path_wchar, mountpath,
Victor Stinner6edddfa2013-11-24 19:22:57 +01003924 Py_SAFE_DOWNCAST(buflen, size_t, DWORD));
Tim Golden6b528062013-08-01 12:44:00 +01003925 Py_END_ALLOW_THREADS
3926
3927 if (!ret) {
Larry Hastings2f936352014-08-05 14:04:04 +10003928 result = win32_error_object("_getvolumepathname", path);
Tim Golden6b528062013-08-01 12:44:00 +01003929 goto exit;
3930 }
3931 result = PyUnicode_FromWideChar(mountpath, wcslen(mountpath));
3932
3933exit:
3934 PyMem_Free(mountpath);
3935 return result;
3936}
Tim Golden6b528062013-08-01 12:44:00 +01003937
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00003938#endif /* MS_WINDOWS */
Mark Hammondef8b6542001-05-13 08:04:26 +00003939
Larry Hastings2f936352014-08-05 14:04:04 +10003940
3941/*[clinic input]
3942os.mkdir
3943
3944 path : path_t
3945
3946 mode: int = 0o777
3947
3948 *
3949
3950 dir_fd : dir_fd(requires='mkdirat') = None
3951
3952# "mkdir(path, mode=0o777, *, dir_fd=None)\n\n\
3953
3954Create a directory.
3955
3956If dir_fd is not None, it should be a file descriptor open to a directory,
3957 and path should be relative; path will then be relative to that directory.
3958dir_fd may not be implemented on your platform.
3959 If it is unavailable, using it will raise a NotImplementedError.
3960
3961The mode argument is ignored on Windows.
3962[clinic start generated code]*/
3963
Larry Hastings2f936352014-08-05 14:04:04 +10003964static PyObject *
3965os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003966/*[clinic end generated code: output=8bf1f738873ef2c5 input=e965f68377e9b1ce]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003967{
3968 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003969
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003970#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003971 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003972 if (path->wide)
3973 result = CreateDirectoryW(path->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003974 else
Larry Hastings2f936352014-08-05 14:04:04 +10003975 result = CreateDirectoryA(path->narrow, NULL);
Victor Stinner8c62be82010-05-06 00:08:46 +00003976 Py_END_ALLOW_THREADS
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003977
Larry Hastings2f936352014-08-05 14:04:04 +10003978 if (!result)
3979 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003980#else
Victor Stinner8c62be82010-05-06 00:08:46 +00003981 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003982#if HAVE_MKDIRAT
3983 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10003984 result = mkdirat(dir_fd, path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003985 else
3986#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00003987#if ( defined(__WATCOMC__) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Larry Hastings2f936352014-08-05 14:04:04 +10003988 result = mkdir(path->narrow);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00003989#else
Larry Hastings2f936352014-08-05 14:04:04 +10003990 result = mkdir(path->narrow, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00003991#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00003992 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003993 if (result < 0)
3994 return path_error(path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00003995#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003996 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003997}
3998
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003999
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00004000/* sys/resource.h is needed for at least: wait3(), wait4(), broken nice. */
4001#if defined(HAVE_SYS_RESOURCE_H)
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004002#include <sys/resource.h>
4003#endif
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004004
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00004005
4006#ifdef HAVE_NICE
Larry Hastings2f936352014-08-05 14:04:04 +10004007/*[clinic input]
4008os.nice
4009
4010 increment: int
4011 /
4012
4013Add increment to the priority of process and return the new priority.
4014[clinic start generated code]*/
4015
Larry Hastings2f936352014-08-05 14:04:04 +10004016static PyObject *
4017os_nice_impl(PyModuleDef *module, int increment)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004018/*[clinic end generated code: output=8870418a3fc07b51 input=864be2d402a21da2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004019{
4020 int value;
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004021
Victor Stinner8c62be82010-05-06 00:08:46 +00004022 /* There are two flavours of 'nice': one that returns the new
4023 priority (as required by almost all standards out there) and the
4024 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
4025 the use of getpriority() to get the new priority.
Tim Peters5aa91602002-01-30 05:46:57 +00004026
Victor Stinner8c62be82010-05-06 00:08:46 +00004027 If we are of the nice family that returns the new priority, we
4028 need to clear errno before the call, and check if errno is filled
4029 before calling posix_error() on a returnvalue of -1, because the
4030 -1 may be the actual new priority! */
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004031
Victor Stinner8c62be82010-05-06 00:08:46 +00004032 errno = 0;
4033 value = nice(increment);
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004034#if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
Victor Stinner8c62be82010-05-06 00:08:46 +00004035 if (value == 0)
4036 value = getpriority(PRIO_PROCESS, 0);
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004037#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00004038 if (value == -1 && errno != 0)
4039 /* either nice() or getpriority() returned an error */
4040 return posix_error();
4041 return PyLong_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00004042}
Guido van Rossumb6775db1994-08-01 11:34:53 +00004043#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004044
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004045
4046#ifdef HAVE_GETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10004047/*[clinic input]
4048os.getpriority
4049
4050 which: int
4051 who: int
4052
4053Return program scheduling priority.
4054[clinic start generated code]*/
4055
Larry Hastings2f936352014-08-05 14:04:04 +10004056static PyObject *
4057os_getpriority_impl(PyModuleDef *module, int which, int who)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004058/*[clinic end generated code: output=4759937aa5b67ed6 input=9be615d40e2544ef]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004059{
4060 int retval;
4061
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004062 errno = 0;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004063 retval = getpriority(which, who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004064 if (errno != 0)
4065 return posix_error();
4066 return PyLong_FromLong((long)retval);
4067}
4068#endif /* HAVE_GETPRIORITY */
4069
4070
4071#ifdef HAVE_SETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10004072/*[clinic input]
4073os.setpriority
4074
4075 which: int
4076 who: int
4077 priority: int
4078
4079Set program scheduling priority.
4080[clinic start generated code]*/
4081
Larry Hastings2f936352014-08-05 14:04:04 +10004082static PyObject *
4083os_setpriority_impl(PyModuleDef *module, int which, int who, int priority)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004084/*[clinic end generated code: output=6497d3301547e7d5 input=710ccbf65b9dc513]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004085{
4086 int retval;
4087
4088 retval = setpriority(which, who, priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004089 if (retval == -1)
4090 return posix_error();
4091 Py_RETURN_NONE;
4092}
4093#endif /* HAVE_SETPRIORITY */
4094
4095
Barry Warsaw53699e91996-12-10 23:23:01 +00004096static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004097internal_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 +00004098{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004099 char *function_name = is_replace ? "replace" : "rename";
Larry Hastings9cf065c2012-06-22 16:30:09 -07004100 int dir_fd_specified;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004101
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004102#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00004103 BOOL result;
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004104 int flags = is_replace ? MOVEFILE_REPLACE_EXISTING : 0;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004105#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07004106 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004107#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004108
Larry Hastings9cf065c2012-06-22 16:30:09 -07004109 dir_fd_specified = (src_dir_fd != DEFAULT_DIR_FD) ||
4110 (dst_dir_fd != DEFAULT_DIR_FD);
4111#ifndef HAVE_RENAMEAT
4112 if (dir_fd_specified) {
4113 argument_unavailable_error(function_name, "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10004114 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004115 }
4116#endif
4117
Larry Hastings2f936352014-08-05 14:04:04 +10004118 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004119 PyErr_Format(PyExc_ValueError,
4120 "%s: src and dst must be the same type", function_name);
Larry Hastings2f936352014-08-05 14:04:04 +10004121 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004122 }
4123
4124#ifdef MS_WINDOWS
4125 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004126 if (src->wide)
4127 result = MoveFileExW(src->wide, dst->wide, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004128 else
Larry Hastings2f936352014-08-05 14:04:04 +10004129 result = MoveFileExA(src->narrow, dst->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004130 Py_END_ALLOW_THREADS
4131
Larry Hastings2f936352014-08-05 14:04:04 +10004132 if (!result)
4133 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004134
4135#else
4136 Py_BEGIN_ALLOW_THREADS
4137#ifdef HAVE_RENAMEAT
4138 if (dir_fd_specified)
Larry Hastings2f936352014-08-05 14:04:04 +10004139 result = renameat(src_dir_fd, src->narrow, dst_dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004140 else
4141#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004142 result = rename(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004143 Py_END_ALLOW_THREADS
4144
Larry Hastings2f936352014-08-05 14:04:04 +10004145 if (result)
4146 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004147#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004148 Py_RETURN_NONE;
4149}
Larry Hastings9cf065c2012-06-22 16:30:09 -07004150
Larry Hastings2f936352014-08-05 14:04:04 +10004151
4152/*[clinic input]
4153os.rename
4154
4155 src : path_t
4156 dst : path_t
4157 *
4158 src_dir_fd : dir_fd = None
4159 dst_dir_fd : dir_fd = None
4160
4161Rename a file or directory.
4162
4163If either src_dir_fd or dst_dir_fd is not None, it should be a file
4164 descriptor open to a directory, and the respective path string (src or dst)
4165 should be relative; the path will then be relative to that directory.
4166src_dir_fd and dst_dir_fd, may not be implemented on your platform.
4167 If they are unavailable, using them will raise a NotImplementedError.
4168[clinic start generated code]*/
4169
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004170static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004171os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd,
4172 int dst_dir_fd)
4173/*[clinic end generated code: output=08033bb2ec27fb5f input=faa61c847912c850]*/
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004174{
Larry Hastings2f936352014-08-05 14:04:04 +10004175 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 0);
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004176}
4177
Larry Hastings2f936352014-08-05 14:04:04 +10004178
4179/*[clinic input]
4180os.replace = os.rename
4181
4182Rename a file or directory, overwriting the destination.
4183
4184If either src_dir_fd or dst_dir_fd is not None, it should be a file
4185 descriptor open to a directory, and the respective path string (src or dst)
4186 should be relative; the path will then be relative to that directory.
4187src_dir_fd and dst_dir_fd, may not be implemented on your platform.
4188 If they are unavailable, using them will raise a NotImplementedError."
4189[clinic start generated code]*/
4190
Larry Hastings2f936352014-08-05 14:04:04 +10004191static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004192os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst,
4193 int src_dir_fd, int dst_dir_fd)
4194/*[clinic end generated code: output=131d012eed8d3b8b input=25515dfb107c8421]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004195{
4196 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 1);
4197}
4198
4199
4200/*[clinic input]
4201os.rmdir
4202
4203 path: path_t
4204 *
4205 dir_fd: dir_fd(requires='unlinkat') = None
4206
4207Remove a directory.
4208
4209If dir_fd is not None, it should be a file descriptor open to a directory,
4210 and path should be relative; path will then be relative to that directory.
4211dir_fd may not be implemented on your platform.
4212 If it is unavailable, using it will raise a NotImplementedError.
4213[clinic start generated code]*/
4214
Larry Hastings2f936352014-08-05 14:04:04 +10004215static PyObject *
4216os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004217/*[clinic end generated code: output=cabadec80d5a77c7 input=38c8b375ca34a7e2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004218{
4219 int result;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004220
4221 Py_BEGIN_ALLOW_THREADS
4222#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10004223 if (path->wide)
4224 result = RemoveDirectoryW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004225 else
Larry Hastings2f936352014-08-05 14:04:04 +10004226 result = RemoveDirectoryA(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004227 result = !result; /* Windows, success=1, UNIX, success=0 */
4228#else
4229#ifdef HAVE_UNLINKAT
4230 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10004231 result = unlinkat(dir_fd, path->narrow, AT_REMOVEDIR);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004232 else
4233#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004234 result = rmdir(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004235#endif
4236 Py_END_ALLOW_THREADS
4237
Larry Hastings2f936352014-08-05 14:04:04 +10004238 if (result)
4239 return path_error(path);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004240
Larry Hastings2f936352014-08-05 14:04:04 +10004241 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004242}
4243
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004244
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004245#ifdef HAVE_SYSTEM
Larry Hastings2f936352014-08-05 14:04:04 +10004246#ifdef MS_WINDOWS
4247/*[clinic input]
4248os.system -> long
4249
4250 command: Py_UNICODE
4251
4252Execute the command in a subshell.
4253[clinic start generated code]*/
4254
Larry Hastings2f936352014-08-05 14:04:04 +10004255static long
4256os_system_impl(PyModuleDef *module, Py_UNICODE *command)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004257/*[clinic end generated code: output=4c3bd5abcd9c29e7 input=303f5ce97df606b0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004258{
4259 long result;
Victor Stinner8c62be82010-05-06 00:08:46 +00004260 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004261 result = _wsystem(command);
Victor Stinner8c62be82010-05-06 00:08:46 +00004262 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004263 return result;
4264}
4265#else /* MS_WINDOWS */
4266/*[clinic input]
4267os.system -> long
4268
4269 command: FSConverter
4270
4271Execute the command in a subshell.
4272[clinic start generated code]*/
4273
Larry Hastings2f936352014-08-05 14:04:04 +10004274static long
4275os_system_impl(PyModuleDef *module, PyObject *command)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004276/*[clinic end generated code: output=800f775e10b7be55 input=86a58554ba6094af]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004277{
4278 long result;
4279 char *bytes = PyBytes_AsString(command);
4280 Py_BEGIN_ALLOW_THREADS
4281 result = system(bytes);
4282 Py_END_ALLOW_THREADS
4283 return result;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004284}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004285#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004286#endif /* HAVE_SYSTEM */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004287
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004288
Larry Hastings2f936352014-08-05 14:04:04 +10004289/*[clinic input]
4290os.umask
4291
4292 mask: int
4293 /
4294
4295Set the current numeric umask and return the previous umask.
4296[clinic start generated code]*/
4297
Larry Hastings2f936352014-08-05 14:04:04 +10004298static PyObject *
4299os_umask_impl(PyModuleDef *module, int mask)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004300/*[clinic end generated code: output=9e1fe3c9f14d6a05 input=ab6bfd9b24d8a7e8]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004301{
4302 int i = (int)umask(mask);
Victor Stinner8c62be82010-05-06 00:08:46 +00004303 if (i < 0)
4304 return posix_error();
4305 return PyLong_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004306}
4307
Brian Curtind40e6f72010-07-08 21:39:08 +00004308#ifdef MS_WINDOWS
4309
4310/* override the default DeleteFileW behavior so that directory
4311symlinks can be removed with this function, the same as with
4312Unix symlinks */
4313BOOL WINAPI Py_DeleteFileW(LPCWSTR lpFileName)
4314{
4315 WIN32_FILE_ATTRIBUTE_DATA info;
4316 WIN32_FIND_DATAW find_data;
4317 HANDLE find_data_handle;
4318 int is_directory = 0;
4319 int is_link = 0;
4320
4321 if (GetFileAttributesExW(lpFileName, GetFileExInfoStandard, &info)) {
4322 is_directory = info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004323
Brian Curtind40e6f72010-07-08 21:39:08 +00004324 /* Get WIN32_FIND_DATA structure for the path to determine if
4325 it is a symlink */
4326 if(is_directory &&
4327 info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
4328 find_data_handle = FindFirstFileW(lpFileName, &find_data);
4329
4330 if(find_data_handle != INVALID_HANDLE_VALUE) {
Tim Golden0321cf22014-05-05 19:46:17 +01004331 /* IO_REPARSE_TAG_SYMLINK if it is a symlink and
4332 IO_REPARSE_TAG_MOUNT_POINT if it is a junction point. */
4333 is_link = find_data.dwReserved0 == IO_REPARSE_TAG_SYMLINK ||
4334 find_data.dwReserved0 == IO_REPARSE_TAG_MOUNT_POINT;
Brian Curtind40e6f72010-07-08 21:39:08 +00004335 FindClose(find_data_handle);
4336 }
4337 }
4338 }
4339
4340 if (is_directory && is_link)
4341 return RemoveDirectoryW(lpFileName);
4342
4343 return DeleteFileW(lpFileName);
4344}
4345#endif /* MS_WINDOWS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004346
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004347
Larry Hastings2f936352014-08-05 14:04:04 +10004348/*[clinic input]
4349os.unlink
4350
4351 path: path_t
4352 *
4353 dir_fd: dir_fd(requires='unlinkat')=None
4354
4355Remove a file (same as remove()).
4356
4357If dir_fd is not None, it should be a file descriptor open to a directory,
4358 and path should be relative; path will then be relative to that directory.
4359dir_fd may not be implemented on your platform.
4360 If it is unavailable, using it will raise a NotImplementedError.
4361
4362[clinic start generated code]*/
4363
Larry Hastings2f936352014-08-05 14:04:04 +10004364static PyObject *
4365os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004366/*[clinic end generated code: output=474afd5cd09b237e input=d7bcde2b1b2a2552]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004367{
4368 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004369
4370 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04004371 _Py_BEGIN_SUPPRESS_IPH
Larry Hastings9cf065c2012-06-22 16:30:09 -07004372#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10004373 if (path->wide)
4374 result = Py_DeleteFileW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004375 else
Larry Hastings2f936352014-08-05 14:04:04 +10004376 result = DeleteFileA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004377 result = !result; /* Windows, success=1, UNIX, success=0 */
4378#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07004379#ifdef HAVE_UNLINKAT
4380 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10004381 result = unlinkat(dir_fd, path->narrow, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004382 else
4383#endif /* HAVE_UNLINKAT */
Larry Hastings2f936352014-08-05 14:04:04 +10004384 result = unlink(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004385#endif
Steve Dower8fc89802015-04-12 00:26:27 -04004386 _Py_END_SUPPRESS_IPH
Larry Hastings9cf065c2012-06-22 16:30:09 -07004387 Py_END_ALLOW_THREADS
4388
Larry Hastings2f936352014-08-05 14:04:04 +10004389 if (result)
4390 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004391
Larry Hastings2f936352014-08-05 14:04:04 +10004392 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004393}
4394
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004395
Larry Hastings2f936352014-08-05 14:04:04 +10004396/*[clinic input]
4397os.remove = os.unlink
4398
4399Remove a file (same as unlink()).
4400
4401If dir_fd is not None, it should be a file descriptor open to a directory,
4402 and path should be relative; path will then be relative to that directory.
4403dir_fd may not be implemented on your platform.
4404 If it is unavailable, using it will raise a NotImplementedError.
4405[clinic start generated code]*/
4406
Larry Hastings2f936352014-08-05 14:04:04 +10004407static PyObject *
4408os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004409/*[clinic end generated code: output=d0d5149e64832b9e input=e05c5ab55cd30983]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004410{
4411 return os_unlink_impl(module, path, dir_fd);
4412}
4413
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004414
Larry Hastings605a62d2012-06-24 04:33:36 -07004415static PyStructSequence_Field uname_result_fields[] = {
4416 {"sysname", "operating system name"},
4417 {"nodename", "name of machine on network (implementation-defined)"},
4418 {"release", "operating system release"},
4419 {"version", "operating system version"},
4420 {"machine", "hardware identifier"},
4421 {NULL}
4422};
4423
4424PyDoc_STRVAR(uname_result__doc__,
4425"uname_result: Result from os.uname().\n\n\
4426This object may be accessed either as a tuple of\n\
4427 (sysname, nodename, release, version, machine),\n\
4428or via the attributes sysname, nodename, release, version, and machine.\n\
4429\n\
4430See os.uname for more information.");
4431
4432static PyStructSequence_Desc uname_result_desc = {
4433 "uname_result", /* name */
4434 uname_result__doc__, /* doc */
4435 uname_result_fields,
4436 5
4437};
4438
4439static PyTypeObject UnameResultType;
4440
4441
4442#ifdef HAVE_UNAME
Larry Hastings2f936352014-08-05 14:04:04 +10004443/*[clinic input]
4444os.uname
4445
4446Return an object identifying the current operating system.
4447
4448The object behaves like a named tuple with the following fields:
4449 (sysname, nodename, release, version, machine)
4450
4451[clinic start generated code]*/
4452
Larry Hastings2f936352014-08-05 14:04:04 +10004453static PyObject *
4454os_uname_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004455/*[clinic end generated code: output=01e1421b757e753f input=e68bd246db3043ed]*/
Guido van Rossumc39de5f1992-02-05 11:15:54 +00004456{
Victor Stinner8c62be82010-05-06 00:08:46 +00004457 struct utsname u;
4458 int res;
Larry Hastings605a62d2012-06-24 04:33:36 -07004459 PyObject *value;
Neal Norwitze241ce82003-02-17 18:17:05 +00004460
Victor Stinner8c62be82010-05-06 00:08:46 +00004461 Py_BEGIN_ALLOW_THREADS
4462 res = uname(&u);
4463 Py_END_ALLOW_THREADS
4464 if (res < 0)
4465 return posix_error();
Larry Hastings605a62d2012-06-24 04:33:36 -07004466
4467 value = PyStructSequence_New(&UnameResultType);
4468 if (value == NULL)
4469 return NULL;
4470
4471#define SET(i, field) \
4472 { \
Victor Stinnera534fc42013-06-03 22:07:27 +02004473 PyObject *o = PyUnicode_DecodeFSDefault(field); \
Larry Hastings605a62d2012-06-24 04:33:36 -07004474 if (!o) { \
4475 Py_DECREF(value); \
4476 return NULL; \
4477 } \
4478 PyStructSequence_SET_ITEM(value, i, o); \
4479 } \
4480
4481 SET(0, u.sysname);
4482 SET(1, u.nodename);
4483 SET(2, u.release);
4484 SET(3, u.version);
4485 SET(4, u.machine);
4486
4487#undef SET
4488
4489 return value;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00004490}
Guido van Rossumb6775db1994-08-01 11:34:53 +00004491#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004492
Larry Hastings9e3e70b2011-09-08 19:29:07 -07004493
Larry Hastings9cf065c2012-06-22 16:30:09 -07004494
4495typedef struct {
4496 int now;
4497 time_t atime_s;
4498 long atime_ns;
4499 time_t mtime_s;
4500 long mtime_ns;
4501} utime_t;
4502
4503/*
Victor Stinner484df002014-10-09 13:52:31 +02004504 * these macros assume that "ut" is a pointer to a utime_t
Larry Hastings9cf065c2012-06-22 16:30:09 -07004505 * they also intentionally leak the declaration of a pointer named "time"
4506 */
4507#define UTIME_TO_TIMESPEC \
4508 struct timespec ts[2]; \
4509 struct timespec *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004510 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004511 time = NULL; \
4512 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004513 ts[0].tv_sec = ut->atime_s; \
4514 ts[0].tv_nsec = ut->atime_ns; \
4515 ts[1].tv_sec = ut->mtime_s; \
4516 ts[1].tv_nsec = ut->mtime_ns; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004517 time = ts; \
4518 } \
4519
4520#define UTIME_TO_TIMEVAL \
4521 struct timeval tv[2]; \
4522 struct timeval *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004523 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004524 time = NULL; \
4525 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004526 tv[0].tv_sec = ut->atime_s; \
4527 tv[0].tv_usec = ut->atime_ns / 1000; \
4528 tv[1].tv_sec = ut->mtime_s; \
4529 tv[1].tv_usec = ut->mtime_ns / 1000; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004530 time = tv; \
4531 } \
4532
4533#define UTIME_TO_UTIMBUF \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004534 struct utimbuf u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004535 struct utimbuf *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004536 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004537 time = NULL; \
4538 else { \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004539 u.actime = ut->atime_s; \
4540 u.modtime = ut->mtime_s; \
4541 time = &u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004542 }
4543
4544#define UTIME_TO_TIME_T \
4545 time_t timet[2]; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004546 time_t *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004547 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004548 time = NULL; \
4549 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004550 timet[0] = ut->atime_s; \
4551 timet[1] = ut->mtime_s; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004552 time = timet; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004553 } \
4554
4555
4556#define UTIME_HAVE_DIR_FD (defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT))
4557
4558#if UTIME_HAVE_DIR_FD
4559
4560static int
Victor Stinner484df002014-10-09 13:52:31 +02004561utime_dir_fd(utime_t *ut, int dir_fd, char *path, int follow_symlinks)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004562{
4563#ifdef HAVE_UTIMENSAT
4564 int flags = follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW;
4565 UTIME_TO_TIMESPEC;
4566 return utimensat(dir_fd, path, time, flags);
4567#elif defined(HAVE_FUTIMESAT)
4568 UTIME_TO_TIMEVAL;
4569 /*
4570 * follow_symlinks will never be false here;
4571 * we only allow !follow_symlinks and dir_fd together
4572 * if we have utimensat()
4573 */
4574 assert(follow_symlinks);
4575 return futimesat(dir_fd, path, time);
4576#endif
4577}
4578
Larry Hastings2f936352014-08-05 14:04:04 +10004579 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_converter
4580#else
4581 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings9cf065c2012-06-22 16:30:09 -07004582#endif
4583
4584#define UTIME_HAVE_FD (defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS))
4585
4586#if UTIME_HAVE_FD
4587
4588static int
Victor Stinner484df002014-10-09 13:52:31 +02004589utime_fd(utime_t *ut, int fd)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004590{
4591#ifdef HAVE_FUTIMENS
4592 UTIME_TO_TIMESPEC;
4593 return futimens(fd, time);
4594#else
4595 UTIME_TO_TIMEVAL;
4596 return futimes(fd, time);
4597#endif
4598}
4599
Larry Hastings2f936352014-08-05 14:04:04 +10004600 #define PATH_UTIME_HAVE_FD 1
4601#else
4602 #define PATH_UTIME_HAVE_FD 0
Larry Hastings9cf065c2012-06-22 16:30:09 -07004603#endif
4604
4605
4606#define UTIME_HAVE_NOFOLLOW_SYMLINKS \
4607 (defined(HAVE_UTIMENSAT) || defined(HAVE_LUTIMES))
4608
4609#if UTIME_HAVE_NOFOLLOW_SYMLINKS
4610
4611static int
Victor Stinner484df002014-10-09 13:52:31 +02004612utime_nofollow_symlinks(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004613{
4614#ifdef HAVE_UTIMENSAT
4615 UTIME_TO_TIMESPEC;
4616 return utimensat(DEFAULT_DIR_FD, path, time, AT_SYMLINK_NOFOLLOW);
4617#else
4618 UTIME_TO_TIMEVAL;
4619 return lutimes(path, time);
4620#endif
4621}
4622
4623#endif
4624
4625#ifndef MS_WINDOWS
4626
4627static int
Victor Stinner484df002014-10-09 13:52:31 +02004628utime_default(utime_t *ut, char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004629{
4630#ifdef HAVE_UTIMENSAT
4631 UTIME_TO_TIMESPEC;
4632 return utimensat(DEFAULT_DIR_FD, path, time, 0);
4633#elif defined(HAVE_UTIMES)
4634 UTIME_TO_TIMEVAL;
4635 return utimes(path, time);
4636#elif defined(HAVE_UTIME_H)
4637 UTIME_TO_UTIMBUF;
4638 return utime(path, time);
4639#else
4640 UTIME_TO_TIME_T;
4641 return utime(path, time);
4642#endif
4643}
4644
4645#endif
4646
Larry Hastings76ad59b2012-05-03 00:30:07 -07004647static int
4648split_py_long_to_s_and_ns(PyObject *py_long, time_t *s, long *ns)
4649{
4650 int result = 0;
Benjamin Petersonfbd85a02012-05-04 11:06:09 -04004651 PyObject *divmod;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004652 divmod = PyNumber_Divmod(py_long, billion);
4653 if (!divmod)
4654 goto exit;
4655 *s = _PyLong_AsTime_t(PyTuple_GET_ITEM(divmod, 0));
4656 if ((*s == -1) && PyErr_Occurred())
4657 goto exit;
4658 *ns = PyLong_AsLong(PyTuple_GET_ITEM(divmod, 1));
Benjamin Peterson35a8f0d2012-05-04 01:10:59 -04004659 if ((*ns == -1) && PyErr_Occurred())
Larry Hastings76ad59b2012-05-03 00:30:07 -07004660 goto exit;
4661
4662 result = 1;
4663exit:
4664 Py_XDECREF(divmod);
4665 return result;
4666}
4667
Larry Hastings2f936352014-08-05 14:04:04 +10004668
4669/*[clinic input]
4670os.utime
4671
4672 path: path_t(allow_fd='PATH_UTIME_HAVE_FD')
4673 times: object = NULL
4674 *
4675 ns: object = NULL
4676 dir_fd: dir_fd(requires='futimensat') = None
4677 follow_symlinks: bool=True
4678
4679# "utime(path, times=None, *, ns=None, dir_fd=None, follow_symlinks=True)\n\
4680
4681Set the access and modified time of path.
4682
4683path may always be specified as a string.
4684On some platforms, path may also be specified as an open file descriptor.
4685 If this functionality is unavailable, using it raises an exception.
4686
4687If times is not None, it must be a tuple (atime, mtime);
4688 atime and mtime should be expressed as float seconds since the epoch.
4689If ns is not None, it must be a tuple (atime_ns, mtime_ns);
4690 atime_ns and mtime_ns should be expressed as integer nanoseconds
4691 since the epoch.
4692If both times and ns are None, utime uses the current time.
4693Specifying tuples for both times and ns is an error.
4694
4695If dir_fd is not None, it should be a file descriptor open to a directory,
4696 and path should be relative; path will then be relative to that directory.
4697If follow_symlinks is False, and the last element of the path is a symbolic
4698 link, utime will modify the symbolic link itself instead of the file the
4699 link points to.
4700It is an error to use dir_fd or follow_symlinks when specifying path
4701 as an open file descriptor.
4702dir_fd and follow_symlinks may not be available on your platform.
4703 If they are unavailable, using them will raise a NotImplementedError.
4704
4705[clinic start generated code]*/
4706
Larry Hastings2f936352014-08-05 14:04:04 +10004707static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004708os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times,
4709 PyObject *ns, int dir_fd, int follow_symlinks)
4710/*[clinic end generated code: output=31f3434e560ba2f0 input=1f18c17d5941aa82]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004711{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004712#ifdef MS_WINDOWS
4713 HANDLE hFile;
4714 FILETIME atime, mtime;
4715#else
4716 int result;
4717#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07004718
Larry Hastings9cf065c2012-06-22 16:30:09 -07004719 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10004720 utime_t utime;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004721
Christian Heimesb3c87242013-08-01 00:08:16 +02004722 memset(&utime, 0, sizeof(utime_t));
Larry Hastings76ad59b2012-05-03 00:30:07 -07004723
Larry Hastings9cf065c2012-06-22 16:30:09 -07004724 if (times && (times != Py_None) && ns) {
4725 PyErr_SetString(PyExc_ValueError,
4726 "utime: you may specify either 'times'"
4727 " or 'ns' but not both");
4728 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004729 }
4730
4731 if (times && (times != Py_None)) {
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02004732 time_t a_sec, m_sec;
4733 long a_nsec, m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004734 if (!PyTuple_CheckExact(times) || (PyTuple_Size(times) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004735 PyErr_SetString(PyExc_TypeError,
4736 "utime: 'times' must be either"
4737 " a tuple of two ints or None");
4738 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004739 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004740 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004741 if (_PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 0),
Victor Stinnerdca028b2015-03-30 01:02:57 +02004742 &a_sec, &a_nsec, _PyTime_ROUND_FLOOR) == -1 ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004743 _PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 1),
Victor Stinnerdca028b2015-03-30 01:02:57 +02004744 &m_sec, &m_nsec, _PyTime_ROUND_FLOOR) == -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004745 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004746 }
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02004747 utime.atime_s = a_sec;
4748 utime.atime_ns = a_nsec;
4749 utime.mtime_s = m_sec;
4750 utime.mtime_ns = m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004751 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004752 else if (ns) {
Larry Hastings76ad59b2012-05-03 00:30:07 -07004753 if (!PyTuple_CheckExact(ns) || (PyTuple_Size(ns) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004754 PyErr_SetString(PyExc_TypeError,
4755 "utime: 'ns' must be a tuple of two ints");
4756 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004757 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004758 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004759 if (!split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 0),
Larry Hastings9cf065c2012-06-22 16:30:09 -07004760 &utime.atime_s, &utime.atime_ns) ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004761 !split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 1),
Larry Hastings9cf065c2012-06-22 16:30:09 -07004762 &utime.mtime_s, &utime.mtime_ns)) {
4763 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004764 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004765 }
4766 else {
4767 /* times and ns are both None/unspecified. use "now". */
4768 utime.now = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004769 }
4770
Larry Hastings9cf065c2012-06-22 16:30:09 -07004771#if !UTIME_HAVE_NOFOLLOW_SYMLINKS
4772 if (follow_symlinks_specified("utime", follow_symlinks))
4773 goto exit;
4774#endif
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004775
Larry Hastings2f936352014-08-05 14:04:04 +10004776 if (path_and_dir_fd_invalid("utime", path, dir_fd) ||
4777 dir_fd_and_fd_invalid("utime", dir_fd, path->fd) ||
4778 fd_and_follow_symlinks_invalid("utime", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -07004779 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004780
Larry Hastings9cf065c2012-06-22 16:30:09 -07004781#if !defined(HAVE_UTIMENSAT)
4782 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
Georg Brandl969288e2012-06-26 09:25:44 +02004783 PyErr_SetString(PyExc_ValueError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004784 "utime: cannot use dir_fd and follow_symlinks "
4785 "together on this platform");
4786 goto exit;
4787 }
4788#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07004789
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004790#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004791 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004792 if (path->wide)
4793 hFile = CreateFileW(path->wide, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00004794 NULL, OPEN_EXISTING,
4795 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004796 else
Larry Hastings2f936352014-08-05 14:04:04 +10004797 hFile = CreateFileA(path->narrow, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00004798 NULL, OPEN_EXISTING,
4799 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004800 Py_END_ALLOW_THREADS
4801 if (hFile == INVALID_HANDLE_VALUE) {
Larry Hastings2f936352014-08-05 14:04:04 +10004802 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004803 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004804 }
4805
Larry Hastings9cf065c2012-06-22 16:30:09 -07004806 if (utime.now) {
Antoine Pitrou91a7af32013-11-23 15:23:26 +01004807 GetSystemTimeAsFileTime(&mtime);
4808 atime = mtime;
Victor Stinner8c62be82010-05-06 00:08:46 +00004809 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004810 else {
Steve Dowerbf1f3762015-02-21 15:26:02 -08004811 _Py_time_t_to_FILE_TIME(utime.atime_s, utime.atime_ns, &atime);
4812 _Py_time_t_to_FILE_TIME(utime.mtime_s, utime.mtime_ns, &mtime);
Victor Stinner8c62be82010-05-06 00:08:46 +00004813 }
4814 if (!SetFileTime(hFile, NULL, &atime, &mtime)) {
4815 /* Avoid putting the file name into the error here,
4816 as that may confuse the user into believing that
4817 something is wrong with the file, when it also
4818 could be the time stamp that gives a problem. */
Victor Stinnerb024e842012-10-31 22:24:06 +01004819 PyErr_SetFromWindowsErr(0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004820 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004821 }
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004822#else /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004823 Py_BEGIN_ALLOW_THREADS
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004824
Larry Hastings9cf065c2012-06-22 16:30:09 -07004825#if UTIME_HAVE_NOFOLLOW_SYMLINKS
4826 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10004827 result = utime_nofollow_symlinks(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004828 else
Larry Hastings9e3e70b2011-09-08 19:29:07 -07004829#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004830
4831#if UTIME_HAVE_DIR_FD
4832 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004833 result = utime_dir_fd(&utime, dir_fd, path->narrow, follow_symlinks);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004834 else
4835#endif
4836
4837#if UTIME_HAVE_FD
Larry Hastings2f936352014-08-05 14:04:04 +10004838 if (path->fd != -1)
4839 result = utime_fd(&utime, path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004840 else
4841#endif
4842
Larry Hastings2f936352014-08-05 14:04:04 +10004843 result = utime_default(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004844
4845 Py_END_ALLOW_THREADS
4846
4847 if (result < 0) {
4848 /* see previous comment about not putting filename in error here */
4849 return_value = posix_error();
4850 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004851 }
Larry Hastings76ad59b2012-05-03 00:30:07 -07004852
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004853#endif /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004854
4855 Py_INCREF(Py_None);
4856 return_value = Py_None;
4857
4858exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07004859#ifdef MS_WINDOWS
4860 if (hFile != INVALID_HANDLE_VALUE)
4861 CloseHandle(hFile);
4862#endif
4863 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004864}
4865
Guido van Rossum3b066191991-06-04 19:40:25 +00004866/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00004867
Larry Hastings2f936352014-08-05 14:04:04 +10004868
4869/*[clinic input]
4870os._exit
4871
4872 status: int
4873
4874Exit to the system with specified status, without normal exit processing.
4875[clinic start generated code]*/
4876
Larry Hastings2f936352014-08-05 14:04:04 +10004877static PyObject *
4878os__exit_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004879/*[clinic end generated code: output=472a3cbaf68f3621 input=5e6d57556b0c4a62]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004880{
4881 _exit(status);
Victor Stinner8c62be82010-05-06 00:08:46 +00004882 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00004883}
4884
Martin v. Löwis114619e2002-10-07 06:44:21 +00004885#if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
4886static void
Martin v. Löwis725507b2006-03-07 12:08:51 +00004887free_string_array(char **array, Py_ssize_t count)
Martin v. Löwis114619e2002-10-07 06:44:21 +00004888{
Victor Stinner8c62be82010-05-06 00:08:46 +00004889 Py_ssize_t i;
4890 for (i = 0; i < count; i++)
4891 PyMem_Free(array[i]);
4892 PyMem_DEL(array);
Martin v. Löwis114619e2002-10-07 06:44:21 +00004893}
Martin v. Löwis011e8422009-05-05 04:43:17 +00004894
Antoine Pitrou69f71142009-05-24 21:25:49 +00004895static
Martin v. Löwis011e8422009-05-05 04:43:17 +00004896int fsconvert_strdup(PyObject *o, char**out)
4897{
Victor Stinner8c62be82010-05-06 00:08:46 +00004898 PyObject *bytes;
4899 Py_ssize_t size;
4900 if (!PyUnicode_FSConverter(o, &bytes))
4901 return 0;
4902 size = PyBytes_GET_SIZE(bytes);
4903 *out = PyMem_Malloc(size+1);
Victor Stinner50abf222013-11-07 23:56:10 +01004904 if (!*out) {
4905 PyErr_NoMemory();
Victor Stinner8c62be82010-05-06 00:08:46 +00004906 return 0;
Victor Stinner50abf222013-11-07 23:56:10 +01004907 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004908 memcpy(*out, PyBytes_AsString(bytes), size+1);
4909 Py_DECREF(bytes);
4910 return 1;
Martin v. Löwis011e8422009-05-05 04:43:17 +00004911}
Martin v. Löwis114619e2002-10-07 06:44:21 +00004912#endif
4913
Ross Lagerwall7807c352011-03-17 20:20:30 +02004914#if defined(HAVE_EXECV) || defined (HAVE_FEXECVE)
Victor Stinner13bb71c2010-04-23 21:41:56 +00004915static char**
4916parse_envlist(PyObject* env, Py_ssize_t *envc_ptr)
4917{
Victor Stinner8c62be82010-05-06 00:08:46 +00004918 char **envlist;
4919 Py_ssize_t i, pos, envc;
4920 PyObject *keys=NULL, *vals=NULL;
4921 PyObject *key, *val, *key2, *val2;
4922 char *p, *k, *v;
4923 size_t len;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004924
Victor Stinner8c62be82010-05-06 00:08:46 +00004925 i = PyMapping_Size(env);
4926 if (i < 0)
4927 return NULL;
4928 envlist = PyMem_NEW(char *, i + 1);
4929 if (envlist == NULL) {
4930 PyErr_NoMemory();
4931 return NULL;
4932 }
4933 envc = 0;
4934 keys = PyMapping_Keys(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01004935 if (!keys)
4936 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00004937 vals = PyMapping_Values(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01004938 if (!vals)
Victor Stinner8c62be82010-05-06 00:08:46 +00004939 goto error;
4940 if (!PyList_Check(keys) || !PyList_Check(vals)) {
4941 PyErr_Format(PyExc_TypeError,
4942 "env.keys() or env.values() is not a list");
4943 goto error;
4944 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00004945
Victor Stinner8c62be82010-05-06 00:08:46 +00004946 for (pos = 0; pos < i; pos++) {
4947 key = PyList_GetItem(keys, pos);
4948 val = PyList_GetItem(vals, pos);
4949 if (!key || !val)
4950 goto error;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004951
Victor Stinner8c62be82010-05-06 00:08:46 +00004952 if (PyUnicode_FSConverter(key, &key2) == 0)
4953 goto error;
4954 if (PyUnicode_FSConverter(val, &val2) == 0) {
4955 Py_DECREF(key2);
4956 goto error;
4957 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00004958
Victor Stinner8c62be82010-05-06 00:08:46 +00004959 k = PyBytes_AsString(key2);
4960 v = PyBytes_AsString(val2);
4961 len = PyBytes_GET_SIZE(key2) + PyBytes_GET_SIZE(val2) + 2;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004962
Victor Stinner8c62be82010-05-06 00:08:46 +00004963 p = PyMem_NEW(char, len);
4964 if (p == NULL) {
4965 PyErr_NoMemory();
4966 Py_DECREF(key2);
4967 Py_DECREF(val2);
4968 goto error;
4969 }
4970 PyOS_snprintf(p, len, "%s=%s", k, v);
4971 envlist[envc++] = p;
4972 Py_DECREF(key2);
4973 Py_DECREF(val2);
Victor Stinner8c62be82010-05-06 00:08:46 +00004974 }
4975 Py_DECREF(vals);
4976 Py_DECREF(keys);
Victor Stinner13bb71c2010-04-23 21:41:56 +00004977
Victor Stinner8c62be82010-05-06 00:08:46 +00004978 envlist[envc] = 0;
4979 *envc_ptr = envc;
4980 return envlist;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004981
4982error:
Victor Stinner8c62be82010-05-06 00:08:46 +00004983 Py_XDECREF(keys);
4984 Py_XDECREF(vals);
4985 while (--envc >= 0)
4986 PyMem_DEL(envlist[envc]);
4987 PyMem_DEL(envlist);
4988 return NULL;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004989}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004990
Ross Lagerwall7807c352011-03-17 20:20:30 +02004991static char**
4992parse_arglist(PyObject* argv, Py_ssize_t *argc)
4993{
4994 int i;
4995 char **argvlist = PyMem_NEW(char *, *argc+1);
4996 if (argvlist == NULL) {
4997 PyErr_NoMemory();
4998 return NULL;
4999 }
5000 for (i = 0; i < *argc; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005001 PyObject* item = PySequence_ITEM(argv, i);
5002 if (item == NULL)
5003 goto fail;
5004 if (!fsconvert_strdup(item, &argvlist[i])) {
5005 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005006 goto fail;
5007 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005008 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005009 }
5010 argvlist[*argc] = NULL;
5011 return argvlist;
5012fail:
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005013 *argc = i;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005014 free_string_array(argvlist, *argc);
5015 return NULL;
5016}
5017#endif
5018
Larry Hastings2f936352014-08-05 14:04:04 +10005019
Ross Lagerwall7807c352011-03-17 20:20:30 +02005020#ifdef HAVE_EXECV
Larry Hastings2f936352014-08-05 14:04:04 +10005021/*[clinic input]
5022os.execv
5023
5024 path: FSConverter
5025 Path of executable file.
5026 argv: object
5027 Tuple or list of strings.
5028 /
5029
5030Execute an executable path with arguments, replacing current process.
5031[clinic start generated code]*/
5032
Larry Hastings2f936352014-08-05 14:04:04 +10005033static PyObject *
5034os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005035/*[clinic end generated code: output=9221f08143146fff input=96041559925e5229]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005036{
5037 char *path_char;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005038 char **argvlist;
5039 Py_ssize_t argc;
5040
5041 /* execv has two arguments: (path, argv), where
5042 argv is a list or tuple of strings. */
5043
Larry Hastings2f936352014-08-05 14:04:04 +10005044 path_char = PyBytes_AsString(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005045 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
5046 PyErr_SetString(PyExc_TypeError,
5047 "execv() arg 2 must be a tuple or list");
Ross Lagerwall7807c352011-03-17 20:20:30 +02005048 return NULL;
5049 }
5050 argc = PySequence_Size(argv);
5051 if (argc < 1) {
5052 PyErr_SetString(PyExc_ValueError, "execv() arg 2 must not be empty");
Ross Lagerwall7807c352011-03-17 20:20:30 +02005053 return NULL;
5054 }
5055
5056 argvlist = parse_arglist(argv, &argc);
5057 if (argvlist == NULL) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02005058 return NULL;
5059 }
5060
Larry Hastings2f936352014-08-05 14:04:04 +10005061 execv(path_char, argvlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005062
5063 /* If we get here it's definitely an error */
5064
5065 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005066 return posix_error();
5067}
5068
Larry Hastings2f936352014-08-05 14:04:04 +10005069
5070/*[clinic input]
5071os.execve
5072
5073 path: path_t(allow_fd='PATH_HAVE_FEXECVE')
5074 Path of executable file.
5075 argv: object
5076 Tuple or list of strings.
5077 env: object
5078 Dictionary of strings mapping to strings.
5079
5080Execute an executable path with arguments, replacing current process.
5081[clinic start generated code]*/
5082
Larry Hastings2f936352014-08-05 14:04:04 +10005083static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005084os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv,
5085 PyObject *env)
5086/*[clinic end generated code: output=181884fcdb21508e input=626804fa092606d9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005087{
Larry Hastings9cf065c2012-06-22 16:30:09 -07005088 char **argvlist = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00005089 char **envlist;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005090 Py_ssize_t argc, envc;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005091
Victor Stinner8c62be82010-05-06 00:08:46 +00005092 /* execve has three arguments: (path, argv, env), where
5093 argv is a list or tuple of strings and env is a dictionary
5094 like posix.environ. */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005095
Ross Lagerwall7807c352011-03-17 20:20:30 +02005096 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00005097 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07005098 "execve: argv must be a tuple or list");
5099 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005100 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02005101 argc = PySequence_Size(argv);
Victor Stinner8c62be82010-05-06 00:08:46 +00005102 if (!PyMapping_Check(env)) {
5103 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07005104 "execve: environment must be a mapping object");
5105 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005106 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005107
Ross Lagerwall7807c352011-03-17 20:20:30 +02005108 argvlist = parse_arglist(argv, &argc);
Victor Stinner8c62be82010-05-06 00:08:46 +00005109 if (argvlist == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07005110 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005111 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005112
Victor Stinner8c62be82010-05-06 00:08:46 +00005113 envlist = parse_envlist(env, &envc);
5114 if (envlist == NULL)
Ross Lagerwall7807c352011-03-17 20:20:30 +02005115 goto fail;
5116
Larry Hastings9cf065c2012-06-22 16:30:09 -07005117#ifdef HAVE_FEXECVE
Larry Hastings2f936352014-08-05 14:04:04 +10005118 if (path->fd > -1)
5119 fexecve(path->fd, argvlist, envlist);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005120 else
5121#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005122 execve(path->narrow, argvlist, envlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005123
5124 /* If we get here it's definitely an error */
5125
Larry Hastings2f936352014-08-05 14:04:04 +10005126 path_error(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005127
5128 while (--envc >= 0)
5129 PyMem_DEL(envlist[envc]);
5130 PyMem_DEL(envlist);
5131 fail:
Larry Hastings9cf065c2012-06-22 16:30:09 -07005132 if (argvlist)
5133 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005134 return NULL;
5135}
Larry Hastings9cf065c2012-06-22 16:30:09 -07005136#endif /* HAVE_EXECV */
5137
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005138
Guido van Rossuma1065681999-01-25 23:20:23 +00005139#ifdef HAVE_SPAWNV
Larry Hastings2f936352014-08-05 14:04:04 +10005140/*[clinic input]
5141os.spawnv
5142
5143 mode: int
5144 Mode of process creation.
5145 path: FSConverter
5146 Path of executable file.
5147 argv: object
5148 Tuple or list of strings.
5149 /
5150
5151Execute the program specified by path in a new process.
5152[clinic start generated code]*/
5153
Larry Hastings2f936352014-08-05 14:04:04 +10005154static PyObject *
5155os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005156/*[clinic end generated code: output=140a7945484c8cc5 input=042c91dfc1e6debc]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005157{
5158 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00005159 char **argvlist;
Larry Hastings2f936352014-08-05 14:04:04 +10005160 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00005161 Py_ssize_t argc;
5162 Py_intptr_t spawnval;
5163 PyObject *(*getitem)(PyObject *, Py_ssize_t);
Guido van Rossuma1065681999-01-25 23:20:23 +00005164
Victor Stinner8c62be82010-05-06 00:08:46 +00005165 /* spawnv has three arguments: (mode, path, argv), where
5166 argv is a list or tuple of strings. */
Guido van Rossuma1065681999-01-25 23:20:23 +00005167
Larry Hastings2f936352014-08-05 14:04:04 +10005168 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00005169 if (PyList_Check(argv)) {
5170 argc = PyList_Size(argv);
5171 getitem = PyList_GetItem;
5172 }
5173 else if (PyTuple_Check(argv)) {
5174 argc = PyTuple_Size(argv);
5175 getitem = PyTuple_GetItem;
5176 }
5177 else {
5178 PyErr_SetString(PyExc_TypeError,
5179 "spawnv() arg 2 must be a tuple or list");
Victor Stinner8c62be82010-05-06 00:08:46 +00005180 return NULL;
5181 }
Guido van Rossuma1065681999-01-25 23:20:23 +00005182
Victor Stinner8c62be82010-05-06 00:08:46 +00005183 argvlist = PyMem_NEW(char *, argc+1);
5184 if (argvlist == NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00005185 return PyErr_NoMemory();
5186 }
5187 for (i = 0; i < argc; i++) {
5188 if (!fsconvert_strdup((*getitem)(argv, i),
5189 &argvlist[i])) {
5190 free_string_array(argvlist, i);
5191 PyErr_SetString(
5192 PyExc_TypeError,
5193 "spawnv() arg 2 must contain only strings");
Victor Stinner8c62be82010-05-06 00:08:46 +00005194 return NULL;
5195 }
5196 }
5197 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00005198
Victor Stinner8c62be82010-05-06 00:08:46 +00005199 if (mode == _OLD_P_OVERLAY)
5200 mode = _P_OVERLAY;
Tim Peters5aa91602002-01-30 05:46:57 +00005201
Victor Stinner8c62be82010-05-06 00:08:46 +00005202 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005203 spawnval = _spawnv(mode, path_char, argvlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00005204 Py_END_ALLOW_THREADS
Tim Peters5aa91602002-01-30 05:46:57 +00005205
Victor Stinner8c62be82010-05-06 00:08:46 +00005206 free_string_array(argvlist, argc);
Guido van Rossuma1065681999-01-25 23:20:23 +00005207
Victor Stinner8c62be82010-05-06 00:08:46 +00005208 if (spawnval == -1)
5209 return posix_error();
5210 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01005211 return Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00005212}
5213
5214
Larry Hastings2f936352014-08-05 14:04:04 +10005215/*[clinic input]
5216os.spawnve
5217
5218 mode: int
5219 Mode of process creation.
5220 path: FSConverter
5221 Path of executable file.
5222 argv: object
5223 Tuple or list of strings.
5224 env: object
5225 Dictionary of strings mapping to strings.
5226 /
5227
5228Execute the program specified by path in a new process.
5229[clinic start generated code]*/
5230
Larry Hastings2f936352014-08-05 14:04:04 +10005231static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005232os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path,
5233 PyObject *argv, PyObject *env)
5234/*[clinic end generated code: output=e7f5f0703610531f input=02362fd937963f8f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005235{
5236 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00005237 char **argvlist;
5238 char **envlist;
5239 PyObject *res = NULL;
Antoine Pitrou22e41552010-08-15 18:07:50 +00005240 Py_ssize_t argc, i, envc;
Victor Stinner8c62be82010-05-06 00:08:46 +00005241 Py_intptr_t spawnval;
5242 PyObject *(*getitem)(PyObject *, Py_ssize_t);
5243 Py_ssize_t lastarg = 0;
Guido van Rossuma1065681999-01-25 23:20:23 +00005244
Victor Stinner8c62be82010-05-06 00:08:46 +00005245 /* spawnve has four arguments: (mode, path, argv, env), where
5246 argv is a list or tuple of strings and env is a dictionary
5247 like posix.environ. */
Guido van Rossuma1065681999-01-25 23:20:23 +00005248
Larry Hastings2f936352014-08-05 14:04:04 +10005249 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00005250 if (PyList_Check(argv)) {
5251 argc = PyList_Size(argv);
5252 getitem = PyList_GetItem;
5253 }
5254 else if (PyTuple_Check(argv)) {
5255 argc = PyTuple_Size(argv);
5256 getitem = PyTuple_GetItem;
5257 }
5258 else {
5259 PyErr_SetString(PyExc_TypeError,
5260 "spawnve() arg 2 must be a tuple or list");
5261 goto fail_0;
5262 }
5263 if (!PyMapping_Check(env)) {
5264 PyErr_SetString(PyExc_TypeError,
5265 "spawnve() arg 3 must be a mapping object");
5266 goto fail_0;
5267 }
Guido van Rossuma1065681999-01-25 23:20:23 +00005268
Victor Stinner8c62be82010-05-06 00:08:46 +00005269 argvlist = PyMem_NEW(char *, argc+1);
5270 if (argvlist == NULL) {
5271 PyErr_NoMemory();
5272 goto fail_0;
5273 }
5274 for (i = 0; i < argc; i++) {
5275 if (!fsconvert_strdup((*getitem)(argv, i),
5276 &argvlist[i]))
5277 {
5278 lastarg = i;
5279 goto fail_1;
5280 }
5281 }
5282 lastarg = argc;
5283 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00005284
Victor Stinner8c62be82010-05-06 00:08:46 +00005285 envlist = parse_envlist(env, &envc);
5286 if (envlist == NULL)
5287 goto fail_1;
Guido van Rossuma1065681999-01-25 23:20:23 +00005288
Victor Stinner8c62be82010-05-06 00:08:46 +00005289 if (mode == _OLD_P_OVERLAY)
5290 mode = _P_OVERLAY;
Tim Peters25059d32001-12-07 20:35:43 +00005291
Victor Stinner8c62be82010-05-06 00:08:46 +00005292 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005293 spawnval = _spawnve(mode, path_char, argvlist, envlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00005294 Py_END_ALLOW_THREADS
Tim Peters25059d32001-12-07 20:35:43 +00005295
Victor Stinner8c62be82010-05-06 00:08:46 +00005296 if (spawnval == -1)
5297 (void) posix_error();
5298 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01005299 res = Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00005300
Victor Stinner8c62be82010-05-06 00:08:46 +00005301 while (--envc >= 0)
5302 PyMem_DEL(envlist[envc]);
5303 PyMem_DEL(envlist);
Guido van Rossum0847c5c2002-12-13 18:36:22 +00005304 fail_1:
Victor Stinner8c62be82010-05-06 00:08:46 +00005305 free_string_array(argvlist, lastarg);
Martin v. Löwis114619e2002-10-07 06:44:21 +00005306 fail_0:
Victor Stinner8c62be82010-05-06 00:08:46 +00005307 return res;
Guido van Rossuma1065681999-01-25 23:20:23 +00005308}
Andrew MacIntyre69e18c92004-04-04 07:11:43 +00005309
Guido van Rossuma1065681999-01-25 23:20:23 +00005310#endif /* HAVE_SPAWNV */
5311
5312
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005313#ifdef HAVE_FORK1
Larry Hastings2f936352014-08-05 14:04:04 +10005314/*[clinic input]
5315os.fork1
5316
5317Fork a child process with a single multiplexed (i.e., not bound) thread.
5318
5319Return 0 to child process and PID of child to parent process.
5320[clinic start generated code]*/
5321
Larry Hastings2f936352014-08-05 14:04:04 +10005322static PyObject *
5323os_fork1_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005324/*[clinic end generated code: output=e27b4f66419c9dcf input=12db02167893926e]*/
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005325{
Victor Stinner8c62be82010-05-06 00:08:46 +00005326 pid_t pid;
5327 int result = 0;
5328 _PyImport_AcquireLock();
5329 pid = fork1();
5330 if (pid == 0) {
5331 /* child: this clobbers and resets the import lock. */
5332 PyOS_AfterFork();
5333 } else {
5334 /* parent: release the import lock. */
5335 result = _PyImport_ReleaseLock();
5336 }
5337 if (pid == -1)
5338 return posix_error();
5339 if (result < 0) {
5340 /* Don't clobber the OSError if the fork failed. */
5341 PyErr_SetString(PyExc_RuntimeError,
5342 "not holding the import lock");
5343 return NULL;
5344 }
5345 return PyLong_FromPid(pid);
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005346}
Larry Hastings2f936352014-08-05 14:04:04 +10005347#endif /* HAVE_FORK1 */
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005348
5349
Guido van Rossumad0ee831995-03-01 10:34:45 +00005350#ifdef HAVE_FORK
Larry Hastings2f936352014-08-05 14:04:04 +10005351/*[clinic input]
5352os.fork
5353
5354Fork a child process.
5355
5356Return 0 to child process and PID of child to parent process.
5357[clinic start generated code]*/
5358
Larry Hastings2f936352014-08-05 14:04:04 +10005359static PyObject *
5360os_fork_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005361/*[clinic end generated code: output=898b1ecd3498ba12 input=13c956413110eeaa]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00005362{
Victor Stinner8c62be82010-05-06 00:08:46 +00005363 pid_t pid;
5364 int result = 0;
5365 _PyImport_AcquireLock();
5366 pid = fork();
5367 if (pid == 0) {
5368 /* child: this clobbers and resets the import lock. */
5369 PyOS_AfterFork();
5370 } else {
5371 /* parent: release the import lock. */
5372 result = _PyImport_ReleaseLock();
5373 }
5374 if (pid == -1)
5375 return posix_error();
5376 if (result < 0) {
5377 /* Don't clobber the OSError if the fork failed. */
5378 PyErr_SetString(PyExc_RuntimeError,
5379 "not holding the import lock");
5380 return NULL;
5381 }
5382 return PyLong_FromPid(pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00005383}
Larry Hastings2f936352014-08-05 14:04:04 +10005384#endif /* HAVE_FORK */
5385
Guido van Rossum85e3b011991-06-03 12:42:10 +00005386
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005387#ifdef HAVE_SCHED_H
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005388#ifdef HAVE_SCHED_GET_PRIORITY_MAX
Larry Hastings2f936352014-08-05 14:04:04 +10005389/*[clinic input]
5390os.sched_get_priority_max
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005391
Larry Hastings2f936352014-08-05 14:04:04 +10005392 policy: int
5393
5394Get the maximum scheduling priority for policy.
5395[clinic start generated code]*/
5396
Larry Hastings2f936352014-08-05 14:04:04 +10005397static PyObject *
5398os_sched_get_priority_max_impl(PyModuleDef *module, int policy)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005399/*[clinic end generated code: output=a6a30fa5071f2d81 input=2097b7998eca6874]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005400{
5401 int max;
5402
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005403 max = sched_get_priority_max(policy);
5404 if (max < 0)
5405 return posix_error();
5406 return PyLong_FromLong(max);
5407}
5408
Larry Hastings2f936352014-08-05 14:04:04 +10005409
5410/*[clinic input]
5411os.sched_get_priority_min
5412
5413 policy: int
5414
5415Get the minimum scheduling priority for policy.
5416[clinic start generated code]*/
5417
Larry Hastings2f936352014-08-05 14:04:04 +10005418static PyObject *
5419os_sched_get_priority_min_impl(PyModuleDef *module, int policy)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005420/*[clinic end generated code: output=5ca3ed6bc43e9b20 input=21bc8fa0d70983bf]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005421{
5422 int min = sched_get_priority_min(policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005423 if (min < 0)
5424 return posix_error();
5425 return PyLong_FromLong(min);
5426}
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005427#endif /* HAVE_SCHED_GET_PRIORITY_MAX */
5428
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005429
Larry Hastings2f936352014-08-05 14:04:04 +10005430#ifdef HAVE_SCHED_SETSCHEDULER
5431/*[clinic input]
5432os.sched_getscheduler
5433 pid: pid_t
5434 /
5435
5436Get the scheduling policy for the process identifiedy by pid.
5437
5438Passing 0 for pid returns the scheduling policy for the calling process.
5439[clinic start generated code]*/
5440
Larry Hastings2f936352014-08-05 14:04:04 +10005441static PyObject *
5442os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005443/*[clinic end generated code: output=8cd63c15caf54fa9 input=5f14cfd1f189e1a0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005444{
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005445 int policy;
5446
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005447 policy = sched_getscheduler(pid);
5448 if (policy < 0)
5449 return posix_error();
5450 return PyLong_FromLong(policy);
5451}
Larry Hastings2f936352014-08-05 14:04:04 +10005452#endif /* HAVE_SCHED_SETSCHEDULER */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005453
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005454
5455#if defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM)
Larry Hastings2f936352014-08-05 14:04:04 +10005456/*[clinic input]
5457class os.sched_param "PyObject *" "&SchedParamType"
5458
5459@classmethod
5460os.sched_param.__new__
5461
5462 sched_priority: object
5463 A scheduling parameter.
5464
5465Current has only one field: sched_priority");
5466[clinic start generated code]*/
5467
Larry Hastings2f936352014-08-05 14:04:04 +10005468static PyObject *
5469os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005470/*[clinic end generated code: output=48f4067d60f48c13 input=73a4c22f7071fc62]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005471{
5472 PyObject *res;
5473
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005474 res = PyStructSequence_New(type);
5475 if (!res)
5476 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10005477 Py_INCREF(sched_priority);
5478 PyStructSequence_SET_ITEM(res, 0, sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005479 return res;
5480}
5481
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005482
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005483PyDoc_VAR(os_sched_param__doc__);
5484
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005485static PyStructSequence_Field sched_param_fields[] = {
5486 {"sched_priority", "the scheduling priority"},
5487 {0}
5488};
5489
5490static PyStructSequence_Desc sched_param_desc = {
5491 "sched_param", /* name */
Larry Hastings2f936352014-08-05 14:04:04 +10005492 os_sched_param__doc__, /* doc */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005493 sched_param_fields,
5494 1
5495};
5496
5497static int
5498convert_sched_param(PyObject *param, struct sched_param *res)
5499{
5500 long priority;
5501
5502 if (Py_TYPE(param) != &SchedParamType) {
5503 PyErr_SetString(PyExc_TypeError, "must have a sched_param object");
5504 return 0;
5505 }
5506 priority = PyLong_AsLong(PyStructSequence_GET_ITEM(param, 0));
5507 if (priority == -1 && PyErr_Occurred())
5508 return 0;
5509 if (priority > INT_MAX || priority < INT_MIN) {
5510 PyErr_SetString(PyExc_OverflowError, "sched_priority out of range");
5511 return 0;
5512 }
5513 res->sched_priority = Py_SAFE_DOWNCAST(priority, long, int);
5514 return 1;
5515}
Larry Hastings2f936352014-08-05 14:04:04 +10005516#endif /* defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM) */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005517
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005518
5519#ifdef HAVE_SCHED_SETSCHEDULER
Larry Hastings2f936352014-08-05 14:04:04 +10005520/*[clinic input]
5521os.sched_setscheduler
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005522
Larry Hastings2f936352014-08-05 14:04:04 +10005523 pid: pid_t
5524 policy: int
5525 param: sched_param
5526 /
5527
5528Set the scheduling policy for the process identified by pid.
5529
5530If pid is 0, the calling process is changed.
5531param is an instance of sched_param.
5532[clinic start generated code]*/
5533
Larry Hastings2f936352014-08-05 14:04:04 +10005534static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005535os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy,
5536 struct sched_param *param)
5537/*[clinic end generated code: output=37053e5c528c35c9 input=c581f9469a5327dd]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005538{
Jesus Cea9c822272011-09-10 01:40:52 +02005539 /*
Jesus Cea54b01492011-09-10 01:53:19 +02005540 ** sched_setscheduler() returns 0 in Linux, but the previous
5541 ** scheduling policy under Solaris/Illumos, and others.
5542 ** On error, -1 is returned in all Operating Systems.
Jesus Cea9c822272011-09-10 01:40:52 +02005543 */
Larry Hastings2f936352014-08-05 14:04:04 +10005544 if (sched_setscheduler(pid, policy, param) == -1)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005545 return posix_error();
5546 Py_RETURN_NONE;
5547}
Larry Hastings2f936352014-08-05 14:04:04 +10005548#endif /* HAVE_SCHED_SETSCHEDULER*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005549
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005550
5551#ifdef HAVE_SCHED_SETPARAM
Larry Hastings2f936352014-08-05 14:04:04 +10005552/*[clinic input]
5553os.sched_getparam
5554 pid: pid_t
5555 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005556
Larry Hastings2f936352014-08-05 14:04:04 +10005557Returns scheduling parameters for the process identified by pid.
5558
5559If pid is 0, returns parameters for the calling process.
5560Return value is an instance of sched_param.
5561[clinic start generated code]*/
5562
Larry Hastings2f936352014-08-05 14:04:04 +10005563static PyObject *
5564os_sched_getparam_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005565/*[clinic end generated code: output=f42c5bd2604ecd08 input=18a1ef9c2efae296]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005566{
5567 struct sched_param param;
5568 PyObject *result;
5569 PyObject *priority;
5570
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005571 if (sched_getparam(pid, &param))
5572 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10005573 result = PyStructSequence_New(&SchedParamType);
5574 if (!result)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005575 return NULL;
5576 priority = PyLong_FromLong(param.sched_priority);
5577 if (!priority) {
Larry Hastings2f936352014-08-05 14:04:04 +10005578 Py_DECREF(result);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005579 return NULL;
5580 }
Larry Hastings2f936352014-08-05 14:04:04 +10005581 PyStructSequence_SET_ITEM(result, 0, priority);
5582 return result;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005583}
5584
Larry Hastings2f936352014-08-05 14:04:04 +10005585
5586/*[clinic input]
5587os.sched_setparam
5588 pid: pid_t
5589 param: sched_param
5590 /
5591
5592Set scheduling parameters for the process identified by pid.
5593
5594If pid is 0, sets parameters for the calling process.
5595param should be an instance of sched_param.
5596[clinic start generated code]*/
5597
Larry Hastings2f936352014-08-05 14:04:04 +10005598static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005599os_sched_setparam_impl(PyModuleDef *module, pid_t pid,
5600 struct sched_param *param)
5601/*[clinic end generated code: output=b7a3c589436cec9b input=6b8d6dfcecdc21bd]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005602{
5603 if (sched_setparam(pid, param))
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005604 return posix_error();
5605 Py_RETURN_NONE;
5606}
Larry Hastings2f936352014-08-05 14:04:04 +10005607#endif /* HAVE_SCHED_SETPARAM */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005608
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005609
5610#ifdef HAVE_SCHED_RR_GET_INTERVAL
Larry Hastings2f936352014-08-05 14:04:04 +10005611/*[clinic input]
5612os.sched_rr_get_interval -> double
5613 pid: pid_t
5614 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005615
Larry Hastings2f936352014-08-05 14:04:04 +10005616Return the round-robin quantum for the process identified by pid, in seconds.
5617
5618Value returned is a float.
5619[clinic start generated code]*/
5620
Larry Hastings2f936352014-08-05 14:04:04 +10005621static double
5622os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005623/*[clinic end generated code: output=7adc137a86dea581 input=2a973da15cca6fae]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005624{
5625 struct timespec interval;
5626 if (sched_rr_get_interval(pid, &interval)) {
5627 posix_error();
5628 return -1.0;
5629 }
5630 return (double)interval.tv_sec + 1e-9*interval.tv_nsec;
5631}
5632#endif /* HAVE_SCHED_RR_GET_INTERVAL */
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005633
Larry Hastings2f936352014-08-05 14:04:04 +10005634
5635/*[clinic input]
5636os.sched_yield
5637
5638Voluntarily relinquish the CPU.
5639[clinic start generated code]*/
5640
Larry Hastings2f936352014-08-05 14:04:04 +10005641static PyObject *
5642os_sched_yield_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005643/*[clinic end generated code: output=d7bd51869c4cb6a8 input=e54d6f98189391d4]*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005644{
5645 if (sched_yield())
5646 return posix_error();
5647 Py_RETURN_NONE;
5648}
5649
Benjamin Peterson2740af82011-08-02 17:41:34 -05005650#ifdef HAVE_SCHED_SETAFFINITY
Antoine Pitrou84869872012-08-04 16:16:35 +02005651/* The minimum number of CPUs allocated in a cpu_set_t */
5652static const int NCPUS_START = sizeof(unsigned long) * CHAR_BIT;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005653
Larry Hastings2f936352014-08-05 14:04:04 +10005654/*[clinic input]
5655os.sched_setaffinity
5656 pid: pid_t
5657 mask : object
5658 /
5659
5660Set the CPU affinity of the process identified by pid to mask.
5661
5662mask should be an iterable of integers identifying CPUs.
5663[clinic start generated code]*/
5664
Larry Hastings2f936352014-08-05 14:04:04 +10005665static PyObject *
5666os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005667/*[clinic end generated code: output=582bcbf40d3253a9 input=a0791a597c7085ba]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005668{
Antoine Pitrou84869872012-08-04 16:16:35 +02005669 int ncpus;
5670 size_t setsize;
Larry Hastings2f936352014-08-05 14:04:04 +10005671 cpu_set_t *cpu_set = NULL;
5672 PyObject *iterator = NULL, *item;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005673
Larry Hastings2f936352014-08-05 14:04:04 +10005674 iterator = PyObject_GetIter(mask);
Antoine Pitrou84869872012-08-04 16:16:35 +02005675 if (iterator == NULL)
5676 return NULL;
5677
5678 ncpus = NCPUS_START;
5679 setsize = CPU_ALLOC_SIZE(ncpus);
Larry Hastings2f936352014-08-05 14:04:04 +10005680 cpu_set = CPU_ALLOC(ncpus);
5681 if (cpu_set == NULL) {
Antoine Pitrou84869872012-08-04 16:16:35 +02005682 PyErr_NoMemory();
5683 goto error;
5684 }
Larry Hastings2f936352014-08-05 14:04:04 +10005685 CPU_ZERO_S(setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005686
5687 while ((item = PyIter_Next(iterator))) {
5688 long cpu;
5689 if (!PyLong_Check(item)) {
5690 PyErr_Format(PyExc_TypeError,
5691 "expected an iterator of ints, "
5692 "but iterator yielded %R",
5693 Py_TYPE(item));
5694 Py_DECREF(item);
5695 goto error;
5696 }
5697 cpu = PyLong_AsLong(item);
5698 Py_DECREF(item);
5699 if (cpu < 0) {
5700 if (!PyErr_Occurred())
5701 PyErr_SetString(PyExc_ValueError, "negative CPU number");
5702 goto error;
5703 }
5704 if (cpu > INT_MAX - 1) {
5705 PyErr_SetString(PyExc_OverflowError, "CPU number too large");
5706 goto error;
5707 }
5708 if (cpu >= ncpus) {
5709 /* Grow CPU mask to fit the CPU number */
5710 int newncpus = ncpus;
5711 cpu_set_t *newmask;
5712 size_t newsetsize;
5713 while (newncpus <= cpu) {
5714 if (newncpus > INT_MAX / 2)
5715 newncpus = cpu + 1;
5716 else
5717 newncpus = newncpus * 2;
5718 }
5719 newmask = CPU_ALLOC(newncpus);
5720 if (newmask == NULL) {
5721 PyErr_NoMemory();
5722 goto error;
5723 }
5724 newsetsize = CPU_ALLOC_SIZE(newncpus);
5725 CPU_ZERO_S(newsetsize, newmask);
Larry Hastings2f936352014-08-05 14:04:04 +10005726 memcpy(newmask, cpu_set, setsize);
5727 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005728 setsize = newsetsize;
Larry Hastings2f936352014-08-05 14:04:04 +10005729 cpu_set = newmask;
Antoine Pitrou84869872012-08-04 16:16:35 +02005730 ncpus = newncpus;
5731 }
Larry Hastings2f936352014-08-05 14:04:04 +10005732 CPU_SET_S(cpu, setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005733 }
5734 Py_CLEAR(iterator);
5735
Larry Hastings2f936352014-08-05 14:04:04 +10005736 if (sched_setaffinity(pid, setsize, cpu_set)) {
Antoine Pitrou84869872012-08-04 16:16:35 +02005737 posix_error();
5738 goto error;
5739 }
Larry Hastings2f936352014-08-05 14:04:04 +10005740 CPU_FREE(cpu_set);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005741 Py_RETURN_NONE;
Antoine Pitrou84869872012-08-04 16:16:35 +02005742
5743error:
Larry Hastings2f936352014-08-05 14:04:04 +10005744 if (cpu_set)
5745 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005746 Py_XDECREF(iterator);
5747 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005748}
5749
Larry Hastings2f936352014-08-05 14:04:04 +10005750
5751/*[clinic input]
5752os.sched_getaffinity
5753 pid: pid_t
5754 /
5755
5756Return the affinity of the process identified by pid.
5757
5758The affinity is returned as a set of CPU identifiers.
5759[clinic start generated code]*/
5760
Larry Hastings2f936352014-08-05 14:04:04 +10005761static PyObject *
5762os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005763/*[clinic end generated code: output=b431a8f310e369e7 input=eaf161936874b8a1]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005764{
Antoine Pitrou84869872012-08-04 16:16:35 +02005765 int cpu, ncpus, count;
5766 size_t setsize;
5767 cpu_set_t *mask = NULL;
5768 PyObject *res = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005769
Antoine Pitrou84869872012-08-04 16:16:35 +02005770 ncpus = NCPUS_START;
5771 while (1) {
5772 setsize = CPU_ALLOC_SIZE(ncpus);
5773 mask = CPU_ALLOC(ncpus);
5774 if (mask == NULL)
5775 return PyErr_NoMemory();
5776 if (sched_getaffinity(pid, setsize, mask) == 0)
5777 break;
5778 CPU_FREE(mask);
5779 if (errno != EINVAL)
5780 return posix_error();
5781 if (ncpus > INT_MAX / 2) {
5782 PyErr_SetString(PyExc_OverflowError, "could not allocate "
5783 "a large enough CPU set");
5784 return NULL;
5785 }
5786 ncpus = ncpus * 2;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005787 }
Antoine Pitrou84869872012-08-04 16:16:35 +02005788
5789 res = PySet_New(NULL);
5790 if (res == NULL)
5791 goto error;
5792 for (cpu = 0, count = CPU_COUNT_S(setsize, mask); count; cpu++) {
5793 if (CPU_ISSET_S(cpu, setsize, mask)) {
5794 PyObject *cpu_num = PyLong_FromLong(cpu);
5795 --count;
5796 if (cpu_num == NULL)
5797 goto error;
5798 if (PySet_Add(res, cpu_num)) {
5799 Py_DECREF(cpu_num);
5800 goto error;
5801 }
5802 Py_DECREF(cpu_num);
5803 }
5804 }
5805 CPU_FREE(mask);
5806 return res;
5807
5808error:
5809 if (mask)
5810 CPU_FREE(mask);
5811 Py_XDECREF(res);
5812 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005813}
5814
Benjamin Peterson2740af82011-08-02 17:41:34 -05005815#endif /* HAVE_SCHED_SETAFFINITY */
5816
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005817#endif /* HAVE_SCHED_H */
5818
Larry Hastings2f936352014-08-05 14:04:04 +10005819
Neal Norwitzb59798b2003-03-21 01:43:31 +00005820/* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
Neal Norwitz2deaddb2003-03-21 03:08:31 +00005821/* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
5822#if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
Neal Norwitzb59798b2003-03-21 01:43:31 +00005823#define DEV_PTY_FILE "/dev/ptc"
5824#define HAVE_DEV_PTMX
5825#else
5826#define DEV_PTY_FILE "/dev/ptmx"
5827#endif
5828
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005829#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
Fred Drake8cef4cf2000-06-28 16:40:38 +00005830#ifdef HAVE_PTY_H
5831#include <pty.h>
5832#else
5833#ifdef HAVE_LIBUTIL_H
5834#include <libutil.h>
Ronald Oussoren755740f2010-02-07 19:56:39 +00005835#else
5836#ifdef HAVE_UTIL_H
5837#include <util.h>
5838#endif /* HAVE_UTIL_H */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005839#endif /* HAVE_LIBUTIL_H */
5840#endif /* HAVE_PTY_H */
Martin v. Löwis14e73b12003-01-01 09:51:12 +00005841#ifdef HAVE_STROPTS_H
5842#include <stropts.h>
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005843#endif
5844#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005845
Larry Hastings2f936352014-08-05 14:04:04 +10005846
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005847#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
Larry Hastings2f936352014-08-05 14:04:04 +10005848/*[clinic input]
5849os.openpty
5850
5851Open a pseudo-terminal.
5852
5853Return a tuple of (master_fd, slave_fd) containing open file descriptors
5854for both the master and slave ends.
5855[clinic start generated code]*/
5856
Larry Hastings2f936352014-08-05 14:04:04 +10005857static PyObject *
5858os_openpty_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005859/*[clinic end generated code: output=358e571c1ba135ee input=f3d99fd99e762907]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00005860{
Victor Stinnerdaf45552013-08-28 00:53:59 +02005861 int master_fd = -1, slave_fd = -1;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005862#ifndef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00005863 char * slave_name;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005864#endif
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005865#if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005866 PyOS_sighandler_t sig_saved;
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005867#ifdef sun
Victor Stinner8c62be82010-05-06 00:08:46 +00005868 extern char *ptsname(int fildes);
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005869#endif
5870#endif
Thomas Wouters70c21a12000-07-14 14:28:33 +00005871
Thomas Wouters70c21a12000-07-14 14:28:33 +00005872#ifdef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00005873 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005874 goto posix_error;
5875
5876 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5877 goto error;
5878 if (_Py_set_inheritable(slave_fd, 0, NULL) < 0)
5879 goto error;
5880
Neal Norwitzb59798b2003-03-21 01:43:31 +00005881#elif defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005882 slave_name = _getpty(&master_fd, O_RDWR, 0666, 0);
5883 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005884 goto posix_error;
5885 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5886 goto error;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005887
Victor Stinnerdaf45552013-08-28 00:53:59 +02005888 slave_fd = _Py_open(slave_name, O_RDWR);
Victor Stinner8c62be82010-05-06 00:08:46 +00005889 if (slave_fd < 0)
Victor Stinnera555cfc2015-03-18 00:22:14 +01005890 goto error;
Victor Stinnerdaf45552013-08-28 00:53:59 +02005891
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005892#else
Victor Stinner000de532013-11-25 23:19:58 +01005893 master_fd = open(DEV_PTY_FILE, O_RDWR | O_NOCTTY); /* open master */
Victor Stinner8c62be82010-05-06 00:08:46 +00005894 if (master_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005895 goto posix_error;
5896
Victor Stinner8c62be82010-05-06 00:08:46 +00005897 sig_saved = PyOS_setsig(SIGCHLD, SIG_DFL);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005898
Victor Stinner8c62be82010-05-06 00:08:46 +00005899 /* change permission of slave */
5900 if (grantpt(master_fd) < 0) {
5901 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005902 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00005903 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02005904
Victor Stinner8c62be82010-05-06 00:08:46 +00005905 /* unlock slave */
5906 if (unlockpt(master_fd) < 0) {
5907 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005908 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00005909 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02005910
Victor Stinner8c62be82010-05-06 00:08:46 +00005911 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005912
Victor Stinner8c62be82010-05-06 00:08:46 +00005913 slave_name = ptsname(master_fd); /* get name of slave */
5914 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005915 goto posix_error;
5916
5917 slave_fd = _Py_open(slave_name, O_RDWR | O_NOCTTY); /* open slave */
Victor Stinnera555cfc2015-03-18 00:22:14 +01005918 if (slave_fd == -1)
5919 goto error;
Victor Stinner000de532013-11-25 23:19:58 +01005920
5921 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5922 goto posix_error;
5923
Neal Norwitzb59798b2003-03-21 01:43:31 +00005924#if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
Victor Stinner8c62be82010-05-06 00:08:46 +00005925 ioctl(slave_fd, I_PUSH, "ptem"); /* push ptem */
5926 ioctl(slave_fd, I_PUSH, "ldterm"); /* push ldterm */
Neal Norwitz6700e472002-12-31 16:16:07 +00005927#ifndef __hpux
Victor Stinner8c62be82010-05-06 00:08:46 +00005928 ioctl(slave_fd, I_PUSH, "ttcompat"); /* push ttcompat */
Neal Norwitz6700e472002-12-31 16:16:07 +00005929#endif /* __hpux */
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005930#endif /* HAVE_CYGWIN */
Thomas Wouters1e0c2f42000-07-24 16:06:23 +00005931#endif /* HAVE_OPENPTY */
Thomas Wouters70c21a12000-07-14 14:28:33 +00005932
Victor Stinner8c62be82010-05-06 00:08:46 +00005933 return Py_BuildValue("(ii)", master_fd, slave_fd);
Thomas Wouters70c21a12000-07-14 14:28:33 +00005934
Victor Stinnerdaf45552013-08-28 00:53:59 +02005935posix_error:
5936 posix_error();
5937error:
5938 if (master_fd != -1)
5939 close(master_fd);
5940 if (slave_fd != -1)
5941 close(slave_fd);
5942 return NULL;
Fred Drake8cef4cf2000-06-28 16:40:38 +00005943}
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005944#endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005945
Larry Hastings2f936352014-08-05 14:04:04 +10005946
Fred Drake8cef4cf2000-06-28 16:40:38 +00005947#ifdef HAVE_FORKPTY
Larry Hastings2f936352014-08-05 14:04:04 +10005948/*[clinic input]
5949os.forkpty
5950
5951Fork a new process with a new pseudo-terminal as controlling tty.
5952
5953Returns a tuple of (pid, master_fd).
5954Like fork(), return pid of 0 to the child process,
5955and pid of child to the parent process.
5956To both, return fd of newly opened pseudo-terminal.
5957[clinic start generated code]*/
5958
Larry Hastings2f936352014-08-05 14:04:04 +10005959static PyObject *
5960os_forkpty_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005961/*[clinic end generated code: output=a11b8391dce3cb57 input=f1f7f4bae3966010]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00005962{
Victor Stinner8c62be82010-05-06 00:08:46 +00005963 int master_fd = -1, result = 0;
5964 pid_t pid;
Tim Peters5aa91602002-01-30 05:46:57 +00005965
Victor Stinner8c62be82010-05-06 00:08:46 +00005966 _PyImport_AcquireLock();
5967 pid = forkpty(&master_fd, NULL, NULL, NULL);
5968 if (pid == 0) {
5969 /* child: this clobbers and resets the import lock. */
5970 PyOS_AfterFork();
5971 } else {
5972 /* parent: release the import lock. */
5973 result = _PyImport_ReleaseLock();
5974 }
5975 if (pid == -1)
5976 return posix_error();
5977 if (result < 0) {
5978 /* Don't clobber the OSError if the fork failed. */
5979 PyErr_SetString(PyExc_RuntimeError,
5980 "not holding the import lock");
5981 return NULL;
5982 }
5983 return Py_BuildValue("(Ni)", PyLong_FromPid(pid), master_fd);
Fred Drake8cef4cf2000-06-28 16:40:38 +00005984}
Larry Hastings2f936352014-08-05 14:04:04 +10005985#endif /* HAVE_FORKPTY */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005986
Ross Lagerwall7807c352011-03-17 20:20:30 +02005987
Guido van Rossumad0ee831995-03-01 10:34:45 +00005988#ifdef HAVE_GETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10005989/*[clinic input]
5990os.getegid
5991
5992Return the current process's effective group id.
5993[clinic start generated code]*/
5994
Larry Hastings2f936352014-08-05 14:04:04 +10005995static PyObject *
5996os_getegid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005997/*[clinic end generated code: output=90f433a8c0b1d919 input=1596f79ad1107d5d]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00005998{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02005999 return _PyLong_FromGid(getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006000}
Larry Hastings2f936352014-08-05 14:04:04 +10006001#endif /* HAVE_GETEGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006002
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006003
Guido van Rossumad0ee831995-03-01 10:34:45 +00006004#ifdef HAVE_GETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10006005/*[clinic input]
6006os.geteuid
6007
6008Return the current process's effective user id.
6009[clinic start generated code]*/
6010
Larry Hastings2f936352014-08-05 14:04:04 +10006011static PyObject *
6012os_geteuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006013/*[clinic end generated code: output=1a532c4a66874357 input=4644c662d3bd9f19]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006014{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006015 return _PyLong_FromUid(geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006016}
Larry Hastings2f936352014-08-05 14:04:04 +10006017#endif /* HAVE_GETEUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006018
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006019
Guido van Rossumad0ee831995-03-01 10:34:45 +00006020#ifdef HAVE_GETGID
Larry Hastings2f936352014-08-05 14:04:04 +10006021/*[clinic input]
6022os.getgid
6023
6024Return the current process's group id.
6025[clinic start generated code]*/
6026
Larry Hastings2f936352014-08-05 14:04:04 +10006027static PyObject *
6028os_getgid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006029/*[clinic end generated code: output=91a22021b74ea46b input=58796344cd87c0f6]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006030{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006031 return _PyLong_FromGid(getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006032}
Larry Hastings2f936352014-08-05 14:04:04 +10006033#endif /* HAVE_GETGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006034
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006035
Larry Hastings2f936352014-08-05 14:04:04 +10006036/*[clinic input]
6037os.getpid
6038
6039Return the current process id.
6040[clinic start generated code]*/
6041
Larry Hastings2f936352014-08-05 14:04:04 +10006042static PyObject *
6043os_getpid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006044/*[clinic end generated code: output=8fbf3a934ee09e62 input=5a9a00f0ab68aa00]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00006045{
Victor Stinner8c62be82010-05-06 00:08:46 +00006046 return PyLong_FromPid(getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00006047}
6048
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006049#ifdef HAVE_GETGROUPLIST
Larry Hastings2f936352014-08-05 14:04:04 +10006050
6051/* AC 3.5: funny apple logic below */
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006052PyDoc_STRVAR(posix_getgrouplist__doc__,
6053"getgrouplist(user, group) -> list of groups to which a user belongs\n\n\
6054Returns a list of groups to which a user belongs.\n\n\
6055 user: username to lookup\n\
6056 group: base group id of the user");
6057
6058static PyObject *
6059posix_getgrouplist(PyObject *self, PyObject *args)
6060{
6061#ifdef NGROUPS_MAX
6062#define MAX_GROUPS NGROUPS_MAX
6063#else
6064 /* defined to be 16 on Solaris7, so this should be a small number */
6065#define MAX_GROUPS 64
6066#endif
6067
6068 const char *user;
6069 int i, ngroups;
6070 PyObject *list;
6071#ifdef __APPLE__
6072 int *groups, basegid;
6073#else
6074 gid_t *groups, basegid;
6075#endif
6076 ngroups = MAX_GROUPS;
6077
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006078#ifdef __APPLE__
6079 if (!PyArg_ParseTuple(args, "si:getgrouplist", &user, &basegid))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006080 return NULL;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006081#else
6082 if (!PyArg_ParseTuple(args, "sO&:getgrouplist", &user,
6083 _Py_Gid_Converter, &basegid))
6084 return NULL;
6085#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006086
6087#ifdef __APPLE__
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006088 groups = PyMem_New(int, ngroups);
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006089#else
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006090 groups = PyMem_New(gid_t, ngroups);
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006091#endif
6092 if (groups == NULL)
6093 return PyErr_NoMemory();
6094
6095 if (getgrouplist(user, basegid, groups, &ngroups) == -1) {
6096 PyMem_Del(groups);
6097 return posix_error();
6098 }
6099
6100 list = PyList_New(ngroups);
6101 if (list == NULL) {
6102 PyMem_Del(groups);
6103 return NULL;
6104 }
6105
6106 for (i = 0; i < ngroups; i++) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006107#ifdef __APPLE__
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006108 PyObject *o = PyLong_FromUnsignedLong((unsigned long)groups[i]);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006109#else
6110 PyObject *o = _PyLong_FromGid(groups[i]);
6111#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006112 if (o == NULL) {
6113 Py_DECREF(list);
6114 PyMem_Del(groups);
6115 return NULL;
6116 }
6117 PyList_SET_ITEM(list, i, o);
6118 }
6119
6120 PyMem_Del(groups);
6121
6122 return list;
6123}
Larry Hastings2f936352014-08-05 14:04:04 +10006124#endif /* HAVE_GETGROUPLIST */
6125
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006126
Fred Drakec9680921999-12-13 16:37:25 +00006127#ifdef HAVE_GETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10006128/*[clinic input]
6129os.getgroups
6130
6131Return list of supplemental group IDs for the process.
6132[clinic start generated code]*/
6133
Larry Hastings2f936352014-08-05 14:04:04 +10006134static PyObject *
6135os_getgroups_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006136/*[clinic end generated code: output=6e7c4fd2db6d5c60 input=d3f109412e6a155c]*/
Fred Drakec9680921999-12-13 16:37:25 +00006137{
6138 PyObject *result = NULL;
6139
Fred Drakec9680921999-12-13 16:37:25 +00006140#ifdef NGROUPS_MAX
6141#define MAX_GROUPS NGROUPS_MAX
6142#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006143 /* defined to be 16 on Solaris7, so this should be a small number */
Fred Drakec9680921999-12-13 16:37:25 +00006144#define MAX_GROUPS 64
6145#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00006146 gid_t grouplist[MAX_GROUPS];
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006147
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006148 /* On MacOSX getgroups(2) can return more than MAX_GROUPS results
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006149 * This is a helper variable to store the intermediate result when
6150 * that happens.
6151 *
6152 * To keep the code readable the OSX behaviour is unconditional,
6153 * according to the POSIX spec this should be safe on all unix-y
6154 * systems.
6155 */
6156 gid_t* alt_grouplist = grouplist;
Victor Stinner8c62be82010-05-06 00:08:46 +00006157 int n;
Fred Drakec9680921999-12-13 16:37:25 +00006158
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006159#ifdef __APPLE__
6160 /* Issue #17557: As of OS X 10.8, getgroups(2) no longer raises EINVAL if
6161 * there are more groups than can fit in grouplist. Therefore, on OS X
6162 * always first call getgroups with length 0 to get the actual number
6163 * of groups.
6164 */
6165 n = getgroups(0, NULL);
6166 if (n < 0) {
6167 return posix_error();
6168 } else if (n <= MAX_GROUPS) {
6169 /* groups will fit in existing array */
6170 alt_grouplist = grouplist;
6171 } else {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006172 alt_grouplist = PyMem_New(gid_t, n);
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006173 if (alt_grouplist == NULL) {
6174 errno = EINVAL;
6175 return posix_error();
6176 }
6177 }
6178
6179 n = getgroups(n, alt_grouplist);
6180 if (n == -1) {
6181 if (alt_grouplist != grouplist) {
6182 PyMem_Free(alt_grouplist);
6183 }
6184 return posix_error();
6185 }
6186#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006187 n = getgroups(MAX_GROUPS, grouplist);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006188 if (n < 0) {
6189 if (errno == EINVAL) {
6190 n = getgroups(0, NULL);
6191 if (n == -1) {
6192 return posix_error();
6193 }
6194 if (n == 0) {
6195 /* Avoid malloc(0) */
6196 alt_grouplist = grouplist;
6197 } else {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006198 alt_grouplist = PyMem_New(gid_t, n);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006199 if (alt_grouplist == NULL) {
6200 errno = EINVAL;
6201 return posix_error();
6202 }
6203 n = getgroups(n, alt_grouplist);
6204 if (n == -1) {
6205 PyMem_Free(alt_grouplist);
6206 return posix_error();
6207 }
6208 }
6209 } else {
6210 return posix_error();
6211 }
6212 }
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006213#endif
6214
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006215 result = PyList_New(n);
6216 if (result != NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006217 int i;
6218 for (i = 0; i < n; ++i) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006219 PyObject *o = _PyLong_FromGid(alt_grouplist[i]);
Victor Stinner8c62be82010-05-06 00:08:46 +00006220 if (o == NULL) {
Stefan Krah0e803b32010-11-26 16:16:47 +00006221 Py_DECREF(result);
6222 result = NULL;
6223 break;
Fred Drakec9680921999-12-13 16:37:25 +00006224 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006225 PyList_SET_ITEM(result, i, o);
Fred Drakec9680921999-12-13 16:37:25 +00006226 }
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006227 }
6228
6229 if (alt_grouplist != grouplist) {
6230 PyMem_Free(alt_grouplist);
Victor Stinner8c62be82010-05-06 00:08:46 +00006231 }
Neal Norwitze241ce82003-02-17 18:17:05 +00006232
Fred Drakec9680921999-12-13 16:37:25 +00006233 return result;
6234}
Larry Hastings2f936352014-08-05 14:04:04 +10006235#endif /* HAVE_GETGROUPS */
Fred Drakec9680921999-12-13 16:37:25 +00006236
Antoine Pitroub7572f02009-12-02 20:46:48 +00006237#ifdef HAVE_INITGROUPS
6238PyDoc_STRVAR(posix_initgroups__doc__,
6239"initgroups(username, gid) -> None\n\n\
6240Call the system initgroups() to initialize the group access list with all of\n\
6241the groups of which the specified username is a member, plus the specified\n\
6242group id.");
6243
Larry Hastings2f936352014-08-05 14:04:04 +10006244/* AC 3.5: funny apple logic */
Antoine Pitroub7572f02009-12-02 20:46:48 +00006245static PyObject *
6246posix_initgroups(PyObject *self, PyObject *args)
6247{
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006248 PyObject *oname;
Victor Stinner8c62be82010-05-06 00:08:46 +00006249 char *username;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006250 int res;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006251#ifdef __APPLE__
6252 int gid;
6253#else
6254 gid_t gid;
6255#endif
Antoine Pitroub7572f02009-12-02 20:46:48 +00006256
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006257#ifdef __APPLE__
6258 if (!PyArg_ParseTuple(args, "O&i:initgroups",
6259 PyUnicode_FSConverter, &oname,
6260 &gid))
6261#else
6262 if (!PyArg_ParseTuple(args, "O&O&:initgroups",
6263 PyUnicode_FSConverter, &oname,
6264 _Py_Gid_Converter, &gid))
6265#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00006266 return NULL;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006267 username = PyBytes_AS_STRING(oname);
Antoine Pitroub7572f02009-12-02 20:46:48 +00006268
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006269 res = initgroups(username, gid);
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006270 Py_DECREF(oname);
6271 if (res == -1)
Victor Stinner8c62be82010-05-06 00:08:46 +00006272 return PyErr_SetFromErrno(PyExc_OSError);
Antoine Pitroub7572f02009-12-02 20:46:48 +00006273
Victor Stinner8c62be82010-05-06 00:08:46 +00006274 Py_INCREF(Py_None);
6275 return Py_None;
Antoine Pitroub7572f02009-12-02 20:46:48 +00006276}
Larry Hastings2f936352014-08-05 14:04:04 +10006277#endif /* HAVE_INITGROUPS */
6278
Antoine Pitroub7572f02009-12-02 20:46:48 +00006279
Martin v. Löwis606edc12002-06-13 21:09:11 +00006280#ifdef HAVE_GETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10006281/*[clinic input]
6282os.getpgid
6283
6284 pid: pid_t
6285
6286Call the system call getpgid(), and return the result.
6287[clinic start generated code]*/
6288
Larry Hastings2f936352014-08-05 14:04:04 +10006289static PyObject *
6290os_getpgid_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006291/*[clinic end generated code: output=70e713b4d54b7c61 input=39d710ae3baaf1c7]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006292{
6293 pid_t pgid = getpgid(pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00006294 if (pgid < 0)
6295 return posix_error();
6296 return PyLong_FromPid(pgid);
Martin v. Löwis606edc12002-06-13 21:09:11 +00006297}
6298#endif /* HAVE_GETPGID */
6299
6300
Guido van Rossumb6775db1994-08-01 11:34:53 +00006301#ifdef HAVE_GETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10006302/*[clinic input]
6303os.getpgrp
6304
6305Return the current process group id.
6306[clinic start generated code]*/
6307
Larry Hastings2f936352014-08-05 14:04:04 +10006308static PyObject *
6309os_getpgrp_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006310/*[clinic end generated code: output=cf3403585846811f input=6846fb2bb9a3705e]*/
Guido van Rossum04814471991-06-04 20:23:49 +00006311{
Guido van Rossumb6775db1994-08-01 11:34:53 +00006312#ifdef GETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00006313 return PyLong_FromPid(getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006314#else /* GETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006315 return PyLong_FromPid(getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006316#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00006317}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006318#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00006319
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006320
Guido van Rossumb6775db1994-08-01 11:34:53 +00006321#ifdef HAVE_SETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10006322/*[clinic input]
6323os.setpgrp
6324
6325Make the current process the leader of its process group.
6326[clinic start generated code]*/
6327
Larry Hastings2f936352014-08-05 14:04:04 +10006328static PyObject *
6329os_setpgrp_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006330/*[clinic end generated code: output=59650f55a963d7ac input=1f0619fcb5731e7e]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00006331{
Guido van Rossum64933891994-10-20 21:56:42 +00006332#ifdef SETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00006333 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00006334#else /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006335 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00006336#endif /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006337 return posix_error();
6338 Py_INCREF(Py_None);
6339 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00006340}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006341#endif /* HAVE_SETPGRP */
6342
Guido van Rossumad0ee831995-03-01 10:34:45 +00006343#ifdef HAVE_GETPPID
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006344
6345#ifdef MS_WINDOWS
6346#include <tlhelp32.h>
6347
6348static PyObject*
6349win32_getppid()
6350{
6351 HANDLE snapshot;
6352 pid_t mypid;
6353 PyObject* result = NULL;
6354 BOOL have_record;
6355 PROCESSENTRY32 pe;
6356
6357 mypid = getpid(); /* This function never fails */
6358
6359 snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
6360 if (snapshot == INVALID_HANDLE_VALUE)
6361 return PyErr_SetFromWindowsErr(GetLastError());
6362
6363 pe.dwSize = sizeof(pe);
6364 have_record = Process32First(snapshot, &pe);
6365 while (have_record) {
6366 if (mypid == (pid_t)pe.th32ProcessID) {
6367 /* We could cache the ulong value in a static variable. */
6368 result = PyLong_FromPid((pid_t)pe.th32ParentProcessID);
6369 break;
6370 }
6371
6372 have_record = Process32Next(snapshot, &pe);
6373 }
6374
6375 /* If our loop exits and our pid was not found (result will be NULL)
6376 * then GetLastError will return ERROR_NO_MORE_FILES. This is an
6377 * error anyway, so let's raise it. */
6378 if (!result)
6379 result = PyErr_SetFromWindowsErr(GetLastError());
6380
6381 CloseHandle(snapshot);
6382
6383 return result;
6384}
6385#endif /*MS_WINDOWS*/
6386
Larry Hastings2f936352014-08-05 14:04:04 +10006387
6388/*[clinic input]
6389os.getppid
6390
6391Return the parent's process id.
6392
6393If the parent process has already exited, Windows machines will still
6394return its id; others systems will return the id of the 'init' process (1).
6395[clinic start generated code]*/
6396
Larry Hastings2f936352014-08-05 14:04:04 +10006397static PyObject *
6398os_getppid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006399/*[clinic end generated code: output=4e49c8e7a8738cd2 input=e637cb87539c030e]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00006400{
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006401#ifdef MS_WINDOWS
6402 return win32_getppid();
6403#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006404 return PyLong_FromPid(getppid());
Guido van Rossumad0ee831995-03-01 10:34:45 +00006405#endif
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006406}
6407#endif /* HAVE_GETPPID */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006408
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006409
Fred Drake12c6e2d1999-12-14 21:25:03 +00006410#ifdef HAVE_GETLOGIN
Larry Hastings2f936352014-08-05 14:04:04 +10006411/*[clinic input]
6412os.getlogin
6413
6414Return the actual login name.
6415[clinic start generated code]*/
6416
Larry Hastings2f936352014-08-05 14:04:04 +10006417static PyObject *
6418os_getlogin_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006419/*[clinic end generated code: output=037ebdb3e4b5dac1 input=2a21ab1e917163df]*/
Fred Drake12c6e2d1999-12-14 21:25:03 +00006420{
Victor Stinner8c62be82010-05-06 00:08:46 +00006421 PyObject *result = NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006422#ifdef MS_WINDOWS
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006423 wchar_t user_name[UNLEN + 1];
Victor Stinner63941882011-09-29 00:42:28 +02006424 DWORD num_chars = Py_ARRAY_LENGTH(user_name);
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006425
6426 if (GetUserNameW(user_name, &num_chars)) {
6427 /* num_chars is the number of unicode chars plus null terminator */
6428 result = PyUnicode_FromWideChar(user_name, num_chars - 1);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006429 }
6430 else
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006431 result = PyErr_SetFromWindowsErr(GetLastError());
6432#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006433 char *name;
6434 int old_errno = errno;
Fred Drake12c6e2d1999-12-14 21:25:03 +00006435
Victor Stinner8c62be82010-05-06 00:08:46 +00006436 errno = 0;
6437 name = getlogin();
6438 if (name == NULL) {
6439 if (errno)
Victor Stinnere039ffe2010-08-15 09:33:08 +00006440 posix_error();
Fred Drake12c6e2d1999-12-14 21:25:03 +00006441 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00006442 PyErr_SetString(PyExc_OSError, "unable to determine login name");
Victor Stinner8c62be82010-05-06 00:08:46 +00006443 }
6444 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00006445 result = PyUnicode_DecodeFSDefault(name);
Victor Stinner8c62be82010-05-06 00:08:46 +00006446 errno = old_errno;
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006447#endif
Fred Drake12c6e2d1999-12-14 21:25:03 +00006448 return result;
6449}
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006450#endif /* HAVE_GETLOGIN */
Fred Drake12c6e2d1999-12-14 21:25:03 +00006451
Larry Hastings2f936352014-08-05 14:04:04 +10006452
Guido van Rossumad0ee831995-03-01 10:34:45 +00006453#ifdef HAVE_GETUID
Larry Hastings2f936352014-08-05 14:04:04 +10006454/*[clinic input]
6455os.getuid
6456
6457Return the current process's user id.
6458[clinic start generated code]*/
6459
Larry Hastings2f936352014-08-05 14:04:04 +10006460static PyObject *
6461os_getuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006462/*[clinic end generated code: output=03a8b894cefb3fa5 input=b53c8b35f110a516]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006463{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006464 return _PyLong_FromUid(getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006465}
Larry Hastings2f936352014-08-05 14:04:04 +10006466#endif /* HAVE_GETUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006467
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006468
Brian Curtineb24d742010-04-12 17:16:38 +00006469#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10006470#define HAVE_KILL
6471#endif /* MS_WINDOWS */
6472
6473#ifdef HAVE_KILL
6474/*[clinic input]
6475os.kill
6476
6477 pid: pid_t
6478 signal: Py_ssize_t
6479 /
6480
6481Kill a process with a signal.
6482[clinic start generated code]*/
6483
Larry Hastings2f936352014-08-05 14:04:04 +10006484static PyObject *
6485os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006486/*[clinic end generated code: output=74f907dd00a83c26 input=61a36b86ca275ab9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006487#ifndef MS_WINDOWS
6488{
6489 if (kill(pid, (int)signal) == -1)
6490 return posix_error();
6491 Py_RETURN_NONE;
6492}
6493#else /* !MS_WINDOWS */
Brian Curtineb24d742010-04-12 17:16:38 +00006494{
Amaury Forgeot d'Arc0a589c92010-05-15 20:35:12 +00006495 PyObject *result;
Larry Hastings2f936352014-08-05 14:04:04 +10006496 DWORD sig = (DWORD)signal;
6497 DWORD err;
Victor Stinner8c62be82010-05-06 00:08:46 +00006498 HANDLE handle;
Brian Curtineb24d742010-04-12 17:16:38 +00006499
Victor Stinner8c62be82010-05-06 00:08:46 +00006500 /* Console processes which share a common console can be sent CTRL+C or
6501 CTRL+BREAK events, provided they handle said events. */
6502 if (sig == CTRL_C_EVENT || sig == CTRL_BREAK_EVENT) {
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006503 if (GenerateConsoleCtrlEvent(sig, (DWORD)pid) == 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006504 err = GetLastError();
6505 PyErr_SetFromWindowsErr(err);
6506 }
6507 else
6508 Py_RETURN_NONE;
6509 }
Brian Curtineb24d742010-04-12 17:16:38 +00006510
Victor Stinner8c62be82010-05-06 00:08:46 +00006511 /* If the signal is outside of what GenerateConsoleCtrlEvent can use,
6512 attempt to open and terminate the process. */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006513 handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, (DWORD)pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00006514 if (handle == NULL) {
6515 err = GetLastError();
6516 return PyErr_SetFromWindowsErr(err);
6517 }
Brian Curtineb24d742010-04-12 17:16:38 +00006518
Victor Stinner8c62be82010-05-06 00:08:46 +00006519 if (TerminateProcess(handle, sig) == 0) {
6520 err = GetLastError();
6521 result = PyErr_SetFromWindowsErr(err);
6522 } else {
6523 Py_INCREF(Py_None);
6524 result = Py_None;
6525 }
Brian Curtineb24d742010-04-12 17:16:38 +00006526
Victor Stinner8c62be82010-05-06 00:08:46 +00006527 CloseHandle(handle);
6528 return result;
Brian Curtineb24d742010-04-12 17:16:38 +00006529}
Larry Hastings2f936352014-08-05 14:04:04 +10006530#endif /* !MS_WINDOWS */
6531#endif /* HAVE_KILL */
6532
6533
6534#ifdef HAVE_KILLPG
6535/*[clinic input]
6536os.killpg
6537
6538 pgid: pid_t
6539 signal: int
6540 /
6541
6542Kill a process group with a signal.
6543[clinic start generated code]*/
6544
Larry Hastings2f936352014-08-05 14:04:04 +10006545static PyObject *
6546os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006547/*[clinic end generated code: output=3434a766ef945f93 input=38b5449eb8faec19]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006548{
6549 /* XXX some man pages make the `pgid` parameter an int, others
6550 a pid_t. Since getpgrp() returns a pid_t, we assume killpg should
6551 take the same type. Moreover, pid_t is always at least as wide as
6552 int (else compilation of this module fails), which is safe. */
6553 if (killpg(pgid, signal) == -1)
6554 return posix_error();
6555 Py_RETURN_NONE;
6556}
6557#endif /* HAVE_KILLPG */
6558
Brian Curtineb24d742010-04-12 17:16:38 +00006559
Guido van Rossumc0125471996-06-28 18:55:32 +00006560#ifdef HAVE_PLOCK
Guido van Rossumc0125471996-06-28 18:55:32 +00006561#ifdef HAVE_SYS_LOCK_H
6562#include <sys/lock.h>
6563#endif
6564
Larry Hastings2f936352014-08-05 14:04:04 +10006565/*[clinic input]
6566os.plock
6567 op: int
6568 /
6569
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00006570Lock program segments into memory.");
Larry Hastings2f936352014-08-05 14:04:04 +10006571[clinic start generated code]*/
6572
Larry Hastings2f936352014-08-05 14:04:04 +10006573static PyObject *
6574os_plock_impl(PyModuleDef *module, int op)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006575/*[clinic end generated code: output=5cb851f81b914984 input=e6e5e348e1525f60]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006576{
Victor Stinner8c62be82010-05-06 00:08:46 +00006577 if (plock(op) == -1)
6578 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006579 Py_RETURN_NONE;
Guido van Rossumc0125471996-06-28 18:55:32 +00006580}
Larry Hastings2f936352014-08-05 14:04:04 +10006581#endif /* HAVE_PLOCK */
6582
Guido van Rossumc0125471996-06-28 18:55:32 +00006583
Guido van Rossumb6775db1994-08-01 11:34:53 +00006584#ifdef HAVE_SETUID
Larry Hastings2f936352014-08-05 14:04:04 +10006585/*[clinic input]
6586os.setuid
6587
6588 uid: uid_t
6589 /
6590
6591Set the current process's user id.
6592[clinic start generated code]*/
6593
Larry Hastings2f936352014-08-05 14:04:04 +10006594static PyObject *
6595os_setuid_impl(PyModuleDef *module, uid_t uid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006596/*[clinic end generated code: output=941ea9a8d1e5d565 input=c921a3285aa22256]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006597{
Victor Stinner8c62be82010-05-06 00:08:46 +00006598 if (setuid(uid) < 0)
6599 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006600 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006601}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006602#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006603
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006604
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006605#ifdef HAVE_SETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10006606/*[clinic input]
6607os.seteuid
6608
6609 euid: uid_t
6610 /
6611
6612Set the current process's effective user id.
6613[clinic start generated code]*/
6614
Larry Hastings2f936352014-08-05 14:04:04 +10006615static PyObject *
6616os_seteuid_impl(PyModuleDef *module, uid_t euid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006617/*[clinic end generated code: output=66f4f6823a648d6d input=ba93d927e4781aa9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006618{
6619 if (seteuid(euid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006620 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006621 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006622}
6623#endif /* HAVE_SETEUID */
6624
Larry Hastings2f936352014-08-05 14:04:04 +10006625
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006626#ifdef HAVE_SETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10006627/*[clinic input]
6628os.setegid
6629
6630 egid: gid_t
6631 /
6632
6633Set the current process's effective group id.
6634[clinic start generated code]*/
6635
Larry Hastings2f936352014-08-05 14:04:04 +10006636static PyObject *
6637os_setegid_impl(PyModuleDef *module, gid_t egid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006638/*[clinic end generated code: output=ca094a69a081a60f input=4080526d0ccd6ce3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006639{
6640 if (setegid(egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006641 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006642 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006643}
6644#endif /* HAVE_SETEGID */
6645
Larry Hastings2f936352014-08-05 14:04:04 +10006646
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006647#ifdef HAVE_SETREUID
Larry Hastings2f936352014-08-05 14:04:04 +10006648/*[clinic input]
6649os.setreuid
6650
6651 ruid: uid_t
6652 euid: uid_t
6653 /
6654
6655Set the current process's real and effective user ids.
6656[clinic start generated code]*/
6657
Larry Hastings2f936352014-08-05 14:04:04 +10006658static PyObject *
6659os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006660/*[clinic end generated code: output=b2938c3e73d27ec7 input=0ca8978de663880c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006661{
Victor Stinner8c62be82010-05-06 00:08:46 +00006662 if (setreuid(ruid, euid) < 0) {
6663 return posix_error();
6664 } else {
6665 Py_INCREF(Py_None);
6666 return Py_None;
6667 }
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006668}
6669#endif /* HAVE_SETREUID */
6670
Larry Hastings2f936352014-08-05 14:04:04 +10006671
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006672#ifdef HAVE_SETREGID
Larry Hastings2f936352014-08-05 14:04:04 +10006673/*[clinic input]
6674os.setregid
6675
6676 rgid: gid_t
6677 egid: gid_t
6678 /
6679
6680Set the current process's real and effective group ids.
6681[clinic start generated code]*/
6682
Larry Hastings2f936352014-08-05 14:04:04 +10006683static PyObject *
6684os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006685/*[clinic end generated code: output=db18f1839ababe3d input=c59499f72846db78]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006686{
6687 if (setregid(rgid, egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006688 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006689 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006690}
6691#endif /* HAVE_SETREGID */
6692
Larry Hastings2f936352014-08-05 14:04:04 +10006693
Guido van Rossumb6775db1994-08-01 11:34:53 +00006694#ifdef HAVE_SETGID
Larry Hastings2f936352014-08-05 14:04:04 +10006695/*[clinic input]
6696os.setgid
6697 gid: gid_t
6698 /
6699
6700Set the current process's group id.
6701[clinic start generated code]*/
6702
Larry Hastings2f936352014-08-05 14:04:04 +10006703static PyObject *
6704os_setgid_impl(PyModuleDef *module, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006705/*[clinic end generated code: output=756cb42c6abd9d87 input=27d30c4059045dc6]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006706{
Victor Stinner8c62be82010-05-06 00:08:46 +00006707 if (setgid(gid) < 0)
6708 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006709 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006710}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006711#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006712
Larry Hastings2f936352014-08-05 14:04:04 +10006713
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006714#ifdef HAVE_SETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10006715/*[clinic input]
6716os.setgroups
6717
6718 groups: object
6719 /
6720
6721Set the groups of the current process to list.
6722[clinic start generated code]*/
6723
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006724static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006725os_setgroups(PyModuleDef *module, PyObject *groups)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006726/*[clinic end generated code: output=7945c2e3cc817c58 input=fa742ca3daf85a7e]*/
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006727{
Victor Stinner8c62be82010-05-06 00:08:46 +00006728 int i, len;
6729 gid_t grouplist[MAX_GROUPS];
Tim Peters5aa91602002-01-30 05:46:57 +00006730
Victor Stinner8c62be82010-05-06 00:08:46 +00006731 if (!PySequence_Check(groups)) {
6732 PyErr_SetString(PyExc_TypeError, "setgroups argument must be a sequence");
6733 return NULL;
6734 }
6735 len = PySequence_Size(groups);
6736 if (len > MAX_GROUPS) {
6737 PyErr_SetString(PyExc_ValueError, "too many groups");
6738 return NULL;
6739 }
6740 for(i = 0; i < len; i++) {
6741 PyObject *elem;
6742 elem = PySequence_GetItem(groups, i);
6743 if (!elem)
6744 return NULL;
6745 if (!PyLong_Check(elem)) {
6746 PyErr_SetString(PyExc_TypeError,
6747 "groups must be integers");
6748 Py_DECREF(elem);
6749 return NULL;
6750 } else {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006751 if (!_Py_Gid_Converter(elem, &grouplist[i])) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006752 Py_DECREF(elem);
6753 return NULL;
6754 }
6755 }
6756 Py_DECREF(elem);
6757 }
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006758
Victor Stinner8c62be82010-05-06 00:08:46 +00006759 if (setgroups(len, grouplist) < 0)
6760 return posix_error();
6761 Py_INCREF(Py_None);
6762 return Py_None;
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006763}
6764#endif /* HAVE_SETGROUPS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006765
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006766#if defined(HAVE_WAIT3) || defined(HAVE_WAIT4)
6767static PyObject *
Victor Stinner4195b5c2012-02-08 23:03:19 +01006768wait_helper(pid_t pid, int status, struct rusage *ru)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006769{
Victor Stinner8c62be82010-05-06 00:08:46 +00006770 PyObject *result;
6771 static PyObject *struct_rusage;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02006772 _Py_IDENTIFIER(struct_rusage);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006773
Victor Stinner8c62be82010-05-06 00:08:46 +00006774 if (pid == -1)
6775 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006776
Victor Stinner8c62be82010-05-06 00:08:46 +00006777 if (struct_rusage == NULL) {
6778 PyObject *m = PyImport_ImportModuleNoBlock("resource");
6779 if (m == NULL)
6780 return NULL;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02006781 struct_rusage = _PyObject_GetAttrId(m, &PyId_struct_rusage);
Victor Stinner8c62be82010-05-06 00:08:46 +00006782 Py_DECREF(m);
6783 if (struct_rusage == NULL)
6784 return NULL;
6785 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006786
Victor Stinner8c62be82010-05-06 00:08:46 +00006787 /* XXX(nnorwitz): Copied (w/mods) from resource.c, there should be only one. */
6788 result = PyStructSequence_New((PyTypeObject*) struct_rusage);
6789 if (!result)
6790 return NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006791
6792#ifndef doubletime
6793#define doubletime(TV) ((double)(TV).tv_sec + (TV).tv_usec * 0.000001)
6794#endif
6795
Victor Stinner8c62be82010-05-06 00:08:46 +00006796 PyStructSequence_SET_ITEM(result, 0,
Victor Stinner4195b5c2012-02-08 23:03:19 +01006797 PyFloat_FromDouble(doubletime(ru->ru_utime)));
Victor Stinner8c62be82010-05-06 00:08:46 +00006798 PyStructSequence_SET_ITEM(result, 1,
Victor Stinner4195b5c2012-02-08 23:03:19 +01006799 PyFloat_FromDouble(doubletime(ru->ru_stime)));
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006800#define SET_INT(result, index, value)\
Victor Stinner8c62be82010-05-06 00:08:46 +00006801 PyStructSequence_SET_ITEM(result, index, PyLong_FromLong(value))
6802 SET_INT(result, 2, ru->ru_maxrss);
6803 SET_INT(result, 3, ru->ru_ixrss);
6804 SET_INT(result, 4, ru->ru_idrss);
6805 SET_INT(result, 5, ru->ru_isrss);
6806 SET_INT(result, 6, ru->ru_minflt);
6807 SET_INT(result, 7, ru->ru_majflt);
6808 SET_INT(result, 8, ru->ru_nswap);
6809 SET_INT(result, 9, ru->ru_inblock);
6810 SET_INT(result, 10, ru->ru_oublock);
6811 SET_INT(result, 11, ru->ru_msgsnd);
6812 SET_INT(result, 12, ru->ru_msgrcv);
6813 SET_INT(result, 13, ru->ru_nsignals);
6814 SET_INT(result, 14, ru->ru_nvcsw);
6815 SET_INT(result, 15, ru->ru_nivcsw);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006816#undef SET_INT
6817
Victor Stinner8c62be82010-05-06 00:08:46 +00006818 if (PyErr_Occurred()) {
6819 Py_DECREF(result);
6820 return NULL;
6821 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006822
Victor Stinner8c62be82010-05-06 00:08:46 +00006823 return Py_BuildValue("NiN", PyLong_FromPid(pid), status, result);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006824}
6825#endif /* HAVE_WAIT3 || HAVE_WAIT4 */
6826
Larry Hastings2f936352014-08-05 14:04:04 +10006827
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006828#ifdef HAVE_WAIT3
Larry Hastings2f936352014-08-05 14:04:04 +10006829/*[clinic input]
6830os.wait3
6831
6832 options: int
6833Wait for completion of a child process.
6834
6835Returns a tuple of information about the child process:
6836 (pid, status, rusage)
6837[clinic start generated code]*/
6838
Larry Hastings2f936352014-08-05 14:04:04 +10006839static PyObject *
6840os_wait3_impl(PyModuleDef *module, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006841/*[clinic end generated code: output=e18af4924dc54945 input=8ac4c56956b61710]*/
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006842{
Victor Stinner8c62be82010-05-06 00:08:46 +00006843 pid_t pid;
Victor Stinner8c62be82010-05-06 00:08:46 +00006844 struct rusage ru;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006845 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006846 WAIT_TYPE status;
6847 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006848
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006849 do {
6850 Py_BEGIN_ALLOW_THREADS
6851 pid = wait3(&status, options, &ru);
6852 Py_END_ALLOW_THREADS
6853 } while (pid < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6854 if (pid < 0)
6855 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006856
Victor Stinner4195b5c2012-02-08 23:03:19 +01006857 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006858}
6859#endif /* HAVE_WAIT3 */
6860
Larry Hastings2f936352014-08-05 14:04:04 +10006861
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006862#ifdef HAVE_WAIT4
Larry Hastings2f936352014-08-05 14:04:04 +10006863/*[clinic input]
6864
6865os.wait4
6866
6867 pid: pid_t
6868 options: int
6869
6870Wait for completion of a specific child process.
6871
6872Returns a tuple of information about the child process:
6873 (pid, status, rusage)
6874[clinic start generated code]*/
6875
Larry Hastings2f936352014-08-05 14:04:04 +10006876static PyObject *
6877os_wait4_impl(PyModuleDef *module, pid_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006878/*[clinic end generated code: output=714f19e6ff01e099 input=d11deed0750600ba]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006879{
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006880 pid_t res;
Victor Stinner8c62be82010-05-06 00:08:46 +00006881 struct rusage ru;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006882 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006883 WAIT_TYPE status;
6884 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006885
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006886 do {
6887 Py_BEGIN_ALLOW_THREADS
6888 res = wait4(pid, &status, options, &ru);
6889 Py_END_ALLOW_THREADS
6890 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6891 if (res < 0)
6892 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006893
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006894 return wait_helper(res, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006895}
6896#endif /* HAVE_WAIT4 */
6897
Larry Hastings2f936352014-08-05 14:04:04 +10006898
Ross Lagerwall7807c352011-03-17 20:20:30 +02006899#if defined(HAVE_WAITID) && !defined(__APPLE__)
Larry Hastings2f936352014-08-05 14:04:04 +10006900/*[clinic input]
6901os.waitid
6902
6903 idtype: idtype_t
6904 Must be one of be P_PID, P_PGID or P_ALL.
6905 id: id_t
6906 The id to wait on.
6907 options: int
6908 Constructed from the ORing of one or more of WEXITED, WSTOPPED
6909 or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.
6910 /
6911
6912Returns the result of waiting for a process or processes.
6913
6914Returns either waitid_result or None if WNOHANG is specified and there are
6915no children in a waitable state.
6916[clinic start generated code]*/
6917
Larry Hastings2f936352014-08-05 14:04:04 +10006918static PyObject *
6919os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006920/*[clinic end generated code: output=5c0192750e22fa2e input=d8e7f76e052b7920]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006921{
6922 PyObject *result;
6923 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006924 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006925 siginfo_t si;
6926 si.si_pid = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10006927
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006928 do {
6929 Py_BEGIN_ALLOW_THREADS
6930 res = waitid(idtype, id, &si, options);
6931 Py_END_ALLOW_THREADS
6932 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6933 if (res < 0)
6934 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006935
6936 if (si.si_pid == 0)
6937 Py_RETURN_NONE;
6938
6939 result = PyStructSequence_New(&WaitidResultType);
6940 if (!result)
6941 return NULL;
6942
6943 PyStructSequence_SET_ITEM(result, 0, PyLong_FromPid(si.si_pid));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006944 PyStructSequence_SET_ITEM(result, 1, _PyLong_FromUid(si.si_uid));
Ross Lagerwall7807c352011-03-17 20:20:30 +02006945 PyStructSequence_SET_ITEM(result, 2, PyLong_FromLong((long)(si.si_signo)));
6946 PyStructSequence_SET_ITEM(result, 3, PyLong_FromLong((long)(si.si_status)));
6947 PyStructSequence_SET_ITEM(result, 4, PyLong_FromLong((long)(si.si_code)));
6948 if (PyErr_Occurred()) {
6949 Py_DECREF(result);
6950 return NULL;
6951 }
6952
6953 return result;
6954}
Larry Hastings2f936352014-08-05 14:04:04 +10006955#endif /* defined(HAVE_WAITID) && !defined(__APPLE__) */
Ross Lagerwall7807c352011-03-17 20:20:30 +02006956
Larry Hastings2f936352014-08-05 14:04:04 +10006957
6958#if defined(HAVE_WAITPID)
6959/*[clinic input]
6960os.waitpid
6961 pid: pid_t
6962 options: int
6963 /
6964
6965Wait for completion of a given child process.
6966
6967Returns a tuple of information regarding the child process:
6968 (pid, status)
6969
6970The options argument is ignored on Windows.
6971[clinic start generated code]*/
6972
Larry Hastings2f936352014-08-05 14:04:04 +10006973static PyObject *
6974os_waitpid_impl(PyModuleDef *module, pid_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006975/*[clinic end generated code: output=5e3593353d54b15b input=0bf1666b8758fda3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006976{
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006977 pid_t res;
6978 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006979 WAIT_TYPE status;
6980 WAIT_STATUS_INT(status) = 0;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00006981
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006982 do {
6983 Py_BEGIN_ALLOW_THREADS
6984 res = waitpid(pid, &status, options);
6985 Py_END_ALLOW_THREADS
6986 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6987 if (res < 0)
6988 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006989
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006990 return Py_BuildValue("Ni", PyLong_FromPid(res), WAIT_STATUS_INT(status));
Guido van Rossum21803b81992-08-09 12:55:27 +00006991}
Tim Petersab034fa2002-02-01 11:27:43 +00006992#elif defined(HAVE_CWAIT)
Tim Petersab034fa2002-02-01 11:27:43 +00006993/* MS C has a variant of waitpid() that's usable for most purposes. */
Larry Hastings2f936352014-08-05 14:04:04 +10006994/*[clinic input]
6995os.waitpid
6996 pid: Py_intptr_t
6997 options: int
6998 /
6999
7000Wait for completion of a given process.
7001
7002Returns a tuple of information regarding the process:
7003 (pid, status << 8)
7004
7005The options argument is ignored on Windows.
7006[clinic start generated code]*/
7007
Larry Hastings2f936352014-08-05 14:04:04 +10007008static PyObject *
7009os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007010/*[clinic end generated code: output=fc1d520db019625f input=444c8f51cca5b862]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007011{
7012 int status;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007013 Py_intptr_t res;
7014 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10007015
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007016 do {
7017 Py_BEGIN_ALLOW_THREADS
7018 res = _cwait(&status, pid, options);
7019 Py_END_ALLOW_THREADS
7020 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
7021 if (res != 0)
7022 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00007023
Victor Stinner8c62be82010-05-06 00:08:46 +00007024 /* shift the status left a byte so this is more like the POSIX waitpid */
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007025 return Py_BuildValue(_Py_PARSE_INTPTR "i", res, status << 8);
Tim Petersab034fa2002-02-01 11:27:43 +00007026}
Larry Hastings2f936352014-08-05 14:04:04 +10007027#endif
7028
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007029
Guido van Rossumad0ee831995-03-01 10:34:45 +00007030#ifdef HAVE_WAIT
Larry Hastings2f936352014-08-05 14:04:04 +10007031/*[clinic input]
7032os.wait
7033
7034Wait for completion of a child process.
7035
7036Returns a tuple of information about the child process:
7037 (pid, status)
7038[clinic start generated code]*/
7039
Larry Hastings2f936352014-08-05 14:04:04 +10007040static PyObject *
7041os_wait_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007042/*[clinic end generated code: output=4a7f4978393e0654 input=03b0182d4a4700ce]*/
Guido van Rossum21803b81992-08-09 12:55:27 +00007043{
Victor Stinner8c62be82010-05-06 00:08:46 +00007044 pid_t pid;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007045 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00007046 WAIT_TYPE status;
7047 WAIT_STATUS_INT(status) = 0;
Neal Norwitze241ce82003-02-17 18:17:05 +00007048
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007049 do {
7050 Py_BEGIN_ALLOW_THREADS
7051 pid = wait(&status);
7052 Py_END_ALLOW_THREADS
7053 } while (pid < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
7054 if (pid < 0)
7055 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00007056
Victor Stinner8c62be82010-05-06 00:08:46 +00007057 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum85e3b011991-06-03 12:42:10 +00007058}
Larry Hastings2f936352014-08-05 14:04:04 +10007059#endif /* HAVE_WAIT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00007060
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007061
Larry Hastings9cf065c2012-06-22 16:30:09 -07007062#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
7063PyDoc_STRVAR(readlink__doc__,
7064"readlink(path, *, dir_fd=None) -> path\n\n\
7065Return a string representing the path to which the symbolic link points.\n\
7066\n\
7067If dir_fd is not None, it should be a file descriptor open to a directory,\n\
7068 and path should be relative; path will then be relative to that directory.\n\
7069dir_fd may not be implemented on your platform.\n\
7070 If it is unavailable, using it will raise a NotImplementedError.");
Mark Hammondc2e85bd2002-10-03 05:10:39 +00007071#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007072
Guido van Rossumb6775db1994-08-01 11:34:53 +00007073#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007074
Larry Hastings2f936352014-08-05 14:04:04 +10007075/* AC 3.5: merge win32 and not together */
Barry Warsaw53699e91996-12-10 23:23:01 +00007076static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07007077posix_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007078{
Larry Hastings9cf065c2012-06-22 16:30:09 -07007079 path_t path;
7080 int dir_fd = DEFAULT_DIR_FD;
7081 char buffer[MAXPATHLEN];
7082 ssize_t length;
7083 PyObject *return_value = NULL;
7084 static char *keywords[] = {"path", "dir_fd", NULL};
Thomas Wouters89f507f2006-12-13 04:49:30 +00007085
Larry Hastings9cf065c2012-06-22 16:30:09 -07007086 memset(&path, 0, sizeof(path));
Victor Stinner292c8352012-10-30 02:17:38 +01007087 path.function_name = "readlink";
Larry Hastings9cf065c2012-06-22 16:30:09 -07007088 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O&|$O&:readlink", keywords,
7089 path_converter, &path,
Larry Hastings2f936352014-08-05 14:04:04 +10007090 READLINKAT_DIR_FD_CONVERTER, &dir_fd))
Victor Stinner8c62be82010-05-06 00:08:46 +00007091 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00007092
Victor Stinner8c62be82010-05-06 00:08:46 +00007093 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07007094#ifdef HAVE_READLINKAT
7095 if (dir_fd != DEFAULT_DIR_FD)
7096 length = readlinkat(dir_fd, path.narrow, buffer, sizeof(buffer));
Victor Stinnera45598a2010-05-14 16:35:39 +00007097 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007098#endif
7099 length = readlink(path.narrow, buffer, sizeof(buffer));
7100 Py_END_ALLOW_THREADS
7101
7102 if (length < 0) {
Victor Stinner292c8352012-10-30 02:17:38 +01007103 return_value = path_error(&path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007104 goto exit;
7105 }
7106
7107 if (PyUnicode_Check(path.object))
7108 return_value = PyUnicode_DecodeFSDefaultAndSize(buffer, length);
7109 else
7110 return_value = PyBytes_FromStringAndSize(buffer, length);
7111exit:
7112 path_cleanup(&path);
7113 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007114}
Larry Hastings9cf065c2012-06-22 16:30:09 -07007115
Guido van Rossumb6775db1994-08-01 11:34:53 +00007116#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007117
Larry Hastings2f936352014-08-05 14:04:04 +10007118#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
7119
7120static PyObject *
7121win_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
7122{
7123 wchar_t *path;
7124 DWORD n_bytes_returned;
7125 DWORD io_result;
7126 PyObject *po, *result;
7127 int dir_fd;
7128 HANDLE reparse_point_handle;
7129
7130 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
7131 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
7132 wchar_t *print_name;
7133
7134 static char *keywords[] = {"path", "dir_fd", NULL};
7135
7136 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "U|$O&:readlink", keywords,
7137 &po,
7138 dir_fd_unavailable, &dir_fd
7139 ))
7140 return NULL;
7141
7142 path = PyUnicode_AsUnicode(po);
7143 if (path == NULL)
7144 return NULL;
7145
7146 /* First get a handle to the reparse point */
7147 Py_BEGIN_ALLOW_THREADS
7148 reparse_point_handle = CreateFileW(
7149 path,
7150 0,
7151 0,
7152 0,
7153 OPEN_EXISTING,
7154 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS,
7155 0);
7156 Py_END_ALLOW_THREADS
7157
7158 if (reparse_point_handle==INVALID_HANDLE_VALUE)
7159 return win32_error_object("readlink", po);
7160
7161 Py_BEGIN_ALLOW_THREADS
7162 /* New call DeviceIoControl to read the reparse point */
7163 io_result = DeviceIoControl(
7164 reparse_point_handle,
7165 FSCTL_GET_REPARSE_POINT,
7166 0, 0, /* in buffer */
7167 target_buffer, sizeof(target_buffer),
7168 &n_bytes_returned,
7169 0 /* we're not using OVERLAPPED_IO */
7170 );
7171 CloseHandle(reparse_point_handle);
7172 Py_END_ALLOW_THREADS
7173
7174 if (io_result==0)
7175 return win32_error_object("readlink", po);
7176
7177 if (rdb->ReparseTag != IO_REPARSE_TAG_SYMLINK)
7178 {
7179 PyErr_SetString(PyExc_ValueError,
7180 "not a symbolic link");
7181 return NULL;
7182 }
7183 print_name = rdb->SymbolicLinkReparseBuffer.PathBuffer +
7184 rdb->SymbolicLinkReparseBuffer.PrintNameOffset;
7185
7186 result = PyUnicode_FromWideChar(print_name,
7187 rdb->SymbolicLinkReparseBuffer.PrintNameLength/2);
7188 return result;
7189}
7190
7191#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
7192
7193
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007194
Larry Hastings9cf065c2012-06-22 16:30:09 -07007195#ifdef HAVE_SYMLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -07007196
7197#if defined(MS_WINDOWS)
7198
7199/* Grab CreateSymbolicLinkW dynamically from kernel32 */
7200static DWORD (CALLBACK *Py_CreateSymbolicLinkW)(LPWSTR, LPWSTR, DWORD) = NULL;
7201static DWORD (CALLBACK *Py_CreateSymbolicLinkA)(LPSTR, LPSTR, DWORD) = NULL;
Victor Stinner31b3b922013-06-05 01:49:17 +02007202
Larry Hastings9cf065c2012-06-22 16:30:09 -07007203static int
Victor Stinner31b3b922013-06-05 01:49:17 +02007204check_CreateSymbolicLink(void)
Larry Hastings9cf065c2012-06-22 16:30:09 -07007205{
7206 HINSTANCE hKernel32;
7207 /* only recheck */
7208 if (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA)
7209 return 1;
7210 hKernel32 = GetModuleHandleW(L"KERNEL32");
7211 *(FARPROC*)&Py_CreateSymbolicLinkW = GetProcAddress(hKernel32,
7212 "CreateSymbolicLinkW");
7213 *(FARPROC*)&Py_CreateSymbolicLinkA = GetProcAddress(hKernel32,
7214 "CreateSymbolicLinkA");
7215 return (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA);
7216}
7217
Victor Stinner31b3b922013-06-05 01:49:17 +02007218/* Remove the last portion of the path */
7219static void
7220_dirnameW(WCHAR *path)
7221{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007222 WCHAR *ptr;
7223
7224 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +02007225 for(ptr = path + wcslen(path); ptr != path; ptr--) {
Victor Stinner072318b2013-06-05 02:07:46 +02007226 if (*ptr == L'\\' || *ptr == L'/')
Jason R. Coombs3a092862013-05-27 23:21:28 -04007227 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007228 }
7229 *ptr = 0;
7230}
7231
Victor Stinner31b3b922013-06-05 01:49:17 +02007232/* Remove the last portion of the path */
7233static void
7234_dirnameA(char *path)
7235{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007236 char *ptr;
7237
7238 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +02007239 for(ptr = path + strlen(path); ptr != path; ptr--) {
7240 if (*ptr == '\\' || *ptr == '/')
Jason R. Coombs3a092862013-05-27 23:21:28 -04007241 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007242 }
7243 *ptr = 0;
7244}
7245
Victor Stinner31b3b922013-06-05 01:49:17 +02007246/* Is this path absolute? */
7247static int
7248_is_absW(const WCHAR *path)
7249{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007250 return path[0] == L'\\' || path[0] == L'/' || path[1] == L':';
7251
7252}
7253
Victor Stinner31b3b922013-06-05 01:49:17 +02007254/* Is this path absolute? */
7255static int
7256_is_absA(const char *path)
7257{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007258 return path[0] == '\\' || path[0] == '/' || path[1] == ':';
7259
7260}
7261
Victor Stinner31b3b922013-06-05 01:49:17 +02007262/* join root and rest with a backslash */
7263static void
7264_joinW(WCHAR *dest_path, const WCHAR *root, const WCHAR *rest)
7265{
Victor Stinnere7e7eba2013-06-05 00:35:54 +02007266 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007267
Victor Stinner31b3b922013-06-05 01:49:17 +02007268 if (_is_absW(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007269 wcscpy(dest_path, rest);
7270 return;
7271 }
7272
7273 root_len = wcslen(root);
7274
7275 wcscpy(dest_path, root);
7276 if(root_len) {
Victor Stinner31b3b922013-06-05 01:49:17 +02007277 dest_path[root_len] = L'\\';
7278 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007279 }
7280 wcscpy(dest_path+root_len, rest);
7281}
7282
Victor Stinner31b3b922013-06-05 01:49:17 +02007283/* join root and rest with a backslash */
7284static void
7285_joinA(char *dest_path, const char *root, const char *rest)
7286{
Victor Stinnere7e7eba2013-06-05 00:35:54 +02007287 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007288
Victor Stinner31b3b922013-06-05 01:49:17 +02007289 if (_is_absA(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007290 strcpy(dest_path, rest);
7291 return;
7292 }
7293
7294 root_len = strlen(root);
7295
7296 strcpy(dest_path, root);
7297 if(root_len) {
7298 dest_path[root_len] = '\\';
Victor Stinner31b3b922013-06-05 01:49:17 +02007299 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007300 }
7301 strcpy(dest_path+root_len, rest);
7302}
7303
Victor Stinner31b3b922013-06-05 01:49:17 +02007304/* Return True if the path at src relative to dest is a directory */
7305static int
7306_check_dirW(WCHAR *src, WCHAR *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -04007307{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007308 WIN32_FILE_ATTRIBUTE_DATA src_info;
7309 WCHAR dest_parent[MAX_PATH];
7310 WCHAR src_resolved[MAX_PATH] = L"";
7311
7312 /* dest_parent = os.path.dirname(dest) */
7313 wcscpy(dest_parent, dest);
7314 _dirnameW(dest_parent);
7315 /* src_resolved = os.path.join(dest_parent, src) */
7316 _joinW(src_resolved, dest_parent, src);
7317 return (
7318 GetFileAttributesExW(src_resolved, GetFileExInfoStandard, &src_info)
7319 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
7320 );
7321}
7322
Victor Stinner31b3b922013-06-05 01:49:17 +02007323/* Return True if the path at src relative to dest is a directory */
7324static int
7325_check_dirA(char *src, char *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -04007326{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007327 WIN32_FILE_ATTRIBUTE_DATA src_info;
7328 char dest_parent[MAX_PATH];
7329 char src_resolved[MAX_PATH] = "";
7330
7331 /* dest_parent = os.path.dirname(dest) */
7332 strcpy(dest_parent, dest);
Victor Stinner5a436762013-06-05 00:37:12 +02007333 _dirnameA(dest_parent);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007334 /* src_resolved = os.path.join(dest_parent, src) */
Victor Stinner5a436762013-06-05 00:37:12 +02007335 _joinA(src_resolved, dest_parent, src);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007336 return (
7337 GetFileAttributesExA(src_resolved, GetFileExInfoStandard, &src_info)
7338 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
7339 );
7340}
Larry Hastings9cf065c2012-06-22 16:30:09 -07007341#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007342
Larry Hastings2f936352014-08-05 14:04:04 +10007343
7344/*[clinic input]
7345os.symlink
7346 src: path_t
7347 dst: path_t
7348 target_is_directory: bool = False
7349 *
7350 dir_fd: dir_fd(requires='symlinkat')=None
7351
7352# "symlink(src, dst, target_is_directory=False, *, dir_fd=None)\n\n\
7353
7354Create a symbolic link pointing to src named dst.
7355
7356target_is_directory is required on Windows if the target is to be
7357 interpreted as a directory. (On Windows, symlink requires
7358 Windows 6.0 or greater, and raises a NotImplementedError otherwise.)
7359 target_is_directory is ignored on non-Windows platforms.
7360
7361If dir_fd is not None, it should be a file descriptor open to a directory,
7362 and path should be relative; path will then be relative to that directory.
7363dir_fd may not be implemented on your platform.
7364 If it is unavailable, using it will raise a NotImplementedError.
7365
7366[clinic start generated code]*/
7367
Larry Hastings2f936352014-08-05 14:04:04 +10007368static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04007369os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst,
7370 int target_is_directory, int dir_fd)
7371/*[clinic end generated code: output=a01b4bcf32403ccd input=e820ec4472547bc3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007372{
Larry Hastings9cf065c2012-06-22 16:30:09 -07007373#ifdef MS_WINDOWS
7374 DWORD result;
7375#else
7376 int result;
7377#endif
7378
Larry Hastings9cf065c2012-06-22 16:30:09 -07007379#ifdef MS_WINDOWS
7380 if (!check_CreateSymbolicLink()) {
7381 PyErr_SetString(PyExc_NotImplementedError,
7382 "CreateSymbolicLink functions not found");
Larry Hastings2f936352014-08-05 14:04:04 +10007383 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03007384 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007385 if (!win32_can_symlink) {
7386 PyErr_SetString(PyExc_OSError, "symbolic link privilege not held");
Larry Hastings2f936352014-08-05 14:04:04 +10007387 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03007388 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007389#endif
7390
Larry Hastings2f936352014-08-05 14:04:04 +10007391 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07007392 PyErr_SetString(PyExc_ValueError,
7393 "symlink: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10007394 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07007395 }
7396
7397#ifdef MS_WINDOWS
Jason R. Coombs3a092862013-05-27 23:21:28 -04007398
Larry Hastings9cf065c2012-06-22 16:30:09 -07007399 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007400 if (dst->wide) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007401 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +10007402 target_is_directory |= _check_dirW(src->wide, dst->wide);
7403 result = Py_CreateSymbolicLinkW(dst->wide, src->wide,
Larry Hastings9cf065c2012-06-22 16:30:09 -07007404 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007405 }
7406 else {
7407 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +10007408 target_is_directory |= _check_dirA(src->narrow, dst->narrow);
7409 result = Py_CreateSymbolicLinkA(dst->narrow, src->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07007410 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007411 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007412 Py_END_ALLOW_THREADS
7413
Larry Hastings2f936352014-08-05 14:04:04 +10007414 if (!result)
7415 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007416
7417#else
7418
7419 Py_BEGIN_ALLOW_THREADS
7420#if HAVE_SYMLINKAT
7421 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10007422 result = symlinkat(src->narrow, dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007423 else
7424#endif
Larry Hastings2f936352014-08-05 14:04:04 +10007425 result = symlink(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007426 Py_END_ALLOW_THREADS
7427
Larry Hastings2f936352014-08-05 14:04:04 +10007428 if (result)
7429 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007430#endif
7431
Larry Hastings2f936352014-08-05 14:04:04 +10007432 Py_RETURN_NONE;
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00007433}
7434#endif /* HAVE_SYMLINK */
7435
Larry Hastings9cf065c2012-06-22 16:30:09 -07007436
Brian Curtind40e6f72010-07-08 21:39:08 +00007437
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00007438
Larry Hastings605a62d2012-06-24 04:33:36 -07007439static PyStructSequence_Field times_result_fields[] = {
7440 {"user", "user time"},
7441 {"system", "system time"},
7442 {"children_user", "user time of children"},
7443 {"children_system", "system time of children"},
7444 {"elapsed", "elapsed time since an arbitrary point in the past"},
7445 {NULL}
7446};
7447
7448PyDoc_STRVAR(times_result__doc__,
7449"times_result: Result from os.times().\n\n\
7450This object may be accessed either as a tuple of\n\
7451 (user, system, children_user, children_system, elapsed),\n\
7452or via the attributes user, system, children_user, children_system,\n\
7453and elapsed.\n\
7454\n\
7455See os.times for more information.");
7456
7457static PyStructSequence_Desc times_result_desc = {
7458 "times_result", /* name */
7459 times_result__doc__, /* doc */
7460 times_result_fields,
7461 5
7462};
7463
7464static PyTypeObject TimesResultType;
7465
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007466#ifdef MS_WINDOWS
7467#define HAVE_TIMES /* mandatory, for the method table */
7468#endif
Larry Hastings605a62d2012-06-24 04:33:36 -07007469
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007470#ifdef HAVE_TIMES
Larry Hastings605a62d2012-06-24 04:33:36 -07007471
7472static PyObject *
7473build_times_result(double user, double system,
7474 double children_user, double children_system,
7475 double elapsed)
7476{
7477 PyObject *value = PyStructSequence_New(&TimesResultType);
7478 if (value == NULL)
7479 return NULL;
7480
7481#define SET(i, field) \
7482 { \
7483 PyObject *o = PyFloat_FromDouble(field); \
7484 if (!o) { \
7485 Py_DECREF(value); \
7486 return NULL; \
7487 } \
7488 PyStructSequence_SET_ITEM(value, i, o); \
7489 } \
7490
7491 SET(0, user);
7492 SET(1, system);
7493 SET(2, children_user);
7494 SET(3, children_system);
7495 SET(4, elapsed);
7496
7497#undef SET
7498
7499 return value;
7500}
7501
Larry Hastings605a62d2012-06-24 04:33:36 -07007502
Larry Hastings2f936352014-08-05 14:04:04 +10007503#ifndef MS_WINDOWS
7504#define NEED_TICKS_PER_SECOND
7505static long ticks_per_second = -1;
7506#endif /* MS_WINDOWS */
7507
7508/*[clinic input]
7509os.times
7510
7511Return a collection containing process timing information.
7512
7513The object returned behaves like a named tuple with these fields:
7514 (utime, stime, cutime, cstime, elapsed_time)
7515All fields are floating point numbers.
7516[clinic start generated code]*/
7517
Larry Hastings2f936352014-08-05 14:04:04 +10007518static PyObject *
7519os_times_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007520/*[clinic end generated code: output=df0a63ebe6e6f091 input=2bf9df3d6ab2e48b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007521#ifdef MS_WINDOWS
Guido van Rossum14ed0b21994-09-29 09:50:09 +00007522{
Victor Stinner8c62be82010-05-06 00:08:46 +00007523 FILETIME create, exit, kernel, user;
7524 HANDLE hProc;
7525 hProc = GetCurrentProcess();
7526 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
7527 /* The fields of a FILETIME structure are the hi and lo part
7528 of a 64-bit value expressed in 100 nanosecond units.
7529 1e7 is one second in such units; 1e-7 the inverse.
7530 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
7531 */
Larry Hastings605a62d2012-06-24 04:33:36 -07007532 return build_times_result(
Victor Stinner8c62be82010-05-06 00:08:46 +00007533 (double)(user.dwHighDateTime*429.4967296 +
7534 user.dwLowDateTime*1e-7),
7535 (double)(kernel.dwHighDateTime*429.4967296 +
7536 kernel.dwLowDateTime*1e-7),
7537 (double)0,
7538 (double)0,
7539 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +00007540}
Larry Hastings2f936352014-08-05 14:04:04 +10007541#else /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007542{
Larry Hastings2f936352014-08-05 14:04:04 +10007543
7544
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007545 struct tms t;
7546 clock_t c;
7547 errno = 0;
7548 c = times(&t);
7549 if (c == (clock_t) -1)
7550 return posix_error();
7551 return build_times_result(
7552 (double)t.tms_utime / ticks_per_second,
7553 (double)t.tms_stime / ticks_per_second,
7554 (double)t.tms_cutime / ticks_per_second,
7555 (double)t.tms_cstime / ticks_per_second,
7556 (double)c / ticks_per_second);
7557}
Larry Hastings2f936352014-08-05 14:04:04 +10007558#endif /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007559#endif /* HAVE_TIMES */
7560
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007561
Martin v. Löwis49ee14d2003-11-10 06:35:36 +00007562#ifdef HAVE_GETSID
Larry Hastings2f936352014-08-05 14:04:04 +10007563/*[clinic input]
7564os.getsid
7565
7566 pid: pid_t
7567 /
7568
7569Call the system call getsid(pid) and return the result.
7570[clinic start generated code]*/
7571
Larry Hastings2f936352014-08-05 14:04:04 +10007572static PyObject *
7573os_getsid_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007574/*[clinic end generated code: output=a074f80c0e6bfb38 input=eeb2b923a30ce04e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007575{
Victor Stinner8c62be82010-05-06 00:08:46 +00007576 int sid;
Victor Stinner8c62be82010-05-06 00:08:46 +00007577 sid = getsid(pid);
7578 if (sid < 0)
7579 return posix_error();
7580 return PyLong_FromLong((long)sid);
Martin v. Löwis49ee14d2003-11-10 06:35:36 +00007581}
7582#endif /* HAVE_GETSID */
7583
7584
Guido van Rossumb6775db1994-08-01 11:34:53 +00007585#ifdef HAVE_SETSID
Larry Hastings2f936352014-08-05 14:04:04 +10007586/*[clinic input]
7587os.setsid
7588
7589Call the system call setsid().
7590[clinic start generated code]*/
7591
Larry Hastings2f936352014-08-05 14:04:04 +10007592static PyObject *
7593os_setsid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007594/*[clinic end generated code: output=398fc152ae327330 input=5fff45858e2f0776]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00007595{
Victor Stinner8c62be82010-05-06 00:08:46 +00007596 if (setsid() < 0)
7597 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007598 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +00007599}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007600#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00007601
Larry Hastings2f936352014-08-05 14:04:04 +10007602
Guido van Rossumb6775db1994-08-01 11:34:53 +00007603#ifdef HAVE_SETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10007604/*[clinic input]
7605os.setpgid
7606
7607 pid: pid_t
7608 pgrp: pid_t
7609 /
7610
7611Call the system call setpgid(pid, pgrp).
7612[clinic start generated code]*/
7613
Larry Hastings2f936352014-08-05 14:04:04 +10007614static PyObject *
7615os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007616/*[clinic end generated code: output=7079a8e932912841 input=fceb395eca572e1a]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007617{
Victor Stinner8c62be82010-05-06 00:08:46 +00007618 if (setpgid(pid, pgrp) < 0)
7619 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007620 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +00007621}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007622#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00007623
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007624
Guido van Rossumb6775db1994-08-01 11:34:53 +00007625#ifdef HAVE_TCGETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10007626/*[clinic input]
7627os.tcgetpgrp
7628
7629 fd: int
7630 /
7631
7632Return the process group associated with the terminal specified by fd.
7633[clinic start generated code]*/
7634
Larry Hastings2f936352014-08-05 14:04:04 +10007635static PyObject *
7636os_tcgetpgrp_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007637/*[clinic end generated code: output=ebb6dc5f111c7dc0 input=7f6c18eac10ada86]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007638{
7639 pid_t pgid = tcgetpgrp(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00007640 if (pgid < 0)
7641 return posix_error();
7642 return PyLong_FromPid(pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +00007643}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007644#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +00007645
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007646
Guido van Rossumb6775db1994-08-01 11:34:53 +00007647#ifdef HAVE_TCSETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10007648/*[clinic input]
7649os.tcsetpgrp
7650
7651 fd: int
7652 pgid: pid_t
7653 /
7654
7655Set the process group associated with the terminal specified by fd.
7656[clinic start generated code]*/
7657
Larry Hastings2f936352014-08-05 14:04:04 +10007658static PyObject *
7659os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007660/*[clinic end generated code: output=3e4b05177462cd22 input=5bdc997c6a619020]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007661{
Victor Stinner8c62be82010-05-06 00:08:46 +00007662 if (tcsetpgrp(fd, pgid) < 0)
7663 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007664 Py_RETURN_NONE;
Guido van Rossum7066dd71992-09-17 17:54:56 +00007665}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007666#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +00007667
Guido van Rossum687dd131993-05-17 08:34:16 +00007668/* Functions acting on file descriptors */
7669
Victor Stinnerdaf45552013-08-28 00:53:59 +02007670#ifdef O_CLOEXEC
7671extern int _Py_open_cloexec_works;
7672#endif
7673
Larry Hastings2f936352014-08-05 14:04:04 +10007674
7675/*[clinic input]
7676os.open -> int
7677 path: path_t
7678 flags: int
7679 mode: int = 0o777
7680 *
7681 dir_fd: dir_fd(requires='openat') = None
7682
7683# "open(path, flags, mode=0o777, *, dir_fd=None)\n\n\
7684
7685Open a file for low level IO. Returns a file descriptor (integer).
7686
7687If dir_fd is not None, it should be a file descriptor open to a directory,
7688 and path should be relative; path will then be relative to that directory.
7689dir_fd may not be implemented on your platform.
7690 If it is unavailable, using it will raise a NotImplementedError.
7691[clinic start generated code]*/
7692
Larry Hastings2f936352014-08-05 14:04:04 +10007693static int
Larry Hastings89964c42015-04-14 18:07:59 -04007694os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode,
7695 int dir_fd)
7696/*[clinic end generated code: output=47e8cc63559f5ddd input=ad8623b29acd2934]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007697{
7698 int fd;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007699 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10007700
Victor Stinnerdaf45552013-08-28 00:53:59 +02007701#ifdef O_CLOEXEC
7702 int *atomic_flag_works = &_Py_open_cloexec_works;
7703#elif !defined(MS_WINDOWS)
7704 int *atomic_flag_works = NULL;
7705#endif
Mark Hammondc2e85bd2002-10-03 05:10:39 +00007706
Victor Stinnerdaf45552013-08-28 00:53:59 +02007707#ifdef MS_WINDOWS
7708 flags |= O_NOINHERIT;
7709#elif defined(O_CLOEXEC)
7710 flags |= O_CLOEXEC;
7711#endif
7712
Steve Dower8fc89802015-04-12 00:26:27 -04007713 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007714 do {
7715 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07007716#ifdef MS_WINDOWS
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007717 if (path->wide)
7718 fd = _wopen(path->wide, flags, mode);
7719 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007720#endif
7721#ifdef HAVE_OPENAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007722 if (dir_fd != DEFAULT_DIR_FD)
7723 fd = openat(dir_fd, path->narrow, flags, mode);
7724 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007725#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007726 fd = open(path->narrow, flags, mode);
7727 Py_END_ALLOW_THREADS
7728 } while (fd < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Steve Dower8fc89802015-04-12 00:26:27 -04007729 _Py_END_SUPPRESS_IPH
Guido van Rossum687dd131993-05-17 08:34:16 +00007730
Larry Hastings9cf065c2012-06-22 16:30:09 -07007731 if (fd == -1) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007732 if (!async_err)
7733 PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings2f936352014-08-05 14:04:04 +10007734 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07007735 }
7736
Victor Stinnerdaf45552013-08-28 00:53:59 +02007737#ifndef MS_WINDOWS
7738 if (_Py_set_inheritable(fd, 0, atomic_flag_works) < 0) {
7739 close(fd);
Larry Hastings2f936352014-08-05 14:04:04 +10007740 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +02007741 }
7742#endif
7743
Larry Hastings2f936352014-08-05 14:04:04 +10007744 return fd;
7745}
7746
7747
7748/*[clinic input]
7749os.close
7750
7751 fd: int
7752
7753Close a file descriptor.
7754[clinic start generated code]*/
7755
Barry Warsaw53699e91996-12-10 23:23:01 +00007756static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007757os_close_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007758/*[clinic end generated code: output=47bf2ea536445a26 input=2bc42451ca5c3223]*/
Guido van Rossum687dd131993-05-17 08:34:16 +00007759{
Larry Hastings2f936352014-08-05 14:04:04 +10007760 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00007761 if (!_PyVerify_fd(fd))
7762 return posix_error();
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007763 /* We do not want to retry upon EINTR: see http://lwn.net/Articles/576478/
7764 * and http://linux.derkeiler.com/Mailing-Lists/Kernel/2005-09/3000.html
7765 * for more details.
7766 */
Victor Stinner8c62be82010-05-06 00:08:46 +00007767 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007768 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007769 res = close(fd);
Steve Dower8fc89802015-04-12 00:26:27 -04007770 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007771 Py_END_ALLOW_THREADS
7772 if (res < 0)
7773 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007774 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +00007775}
7776
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007777
Larry Hastings2f936352014-08-05 14:04:04 +10007778/*[clinic input]
7779os.closerange
7780
7781 fd_low: int
7782 fd_high: int
7783 /
7784
7785Closes all file descriptors in [fd_low, fd_high), ignoring errors.
7786[clinic start generated code]*/
7787
Larry Hastings2f936352014-08-05 14:04:04 +10007788static PyObject *
7789os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007790/*[clinic end generated code: output=70e6adb95220ba96 input=5855a3d053ebd4ec]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007791{
7792 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00007793 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007794 _Py_BEGIN_SUPPRESS_IPH
Larry Hastings2f936352014-08-05 14:04:04 +10007795 for (i = fd_low; i < fd_high; i++)
Victor Stinner8c62be82010-05-06 00:08:46 +00007796 if (_PyVerify_fd(i))
7797 close(i);
Steve Dower8fc89802015-04-12 00:26:27 -04007798 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007799 Py_END_ALLOW_THREADS
7800 Py_RETURN_NONE;
Christian Heimesfdab48e2008-01-20 09:06:41 +00007801}
7802
7803
Larry Hastings2f936352014-08-05 14:04:04 +10007804/*[clinic input]
7805os.dup -> int
7806
7807 fd: int
7808 /
7809
7810Return a duplicate of a file descriptor.
7811[clinic start generated code]*/
7812
Larry Hastings2f936352014-08-05 14:04:04 +10007813static int
7814os_dup_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007815/*[clinic end generated code: output=f4bbac8c7652d05e input=6f10f7ea97f7852a]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007816{
7817 return _Py_dup(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00007818}
7819
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007820
Larry Hastings2f936352014-08-05 14:04:04 +10007821/*[clinic input]
7822os.dup2
7823 fd: int
7824 fd2: int
7825 inheritable: bool=True
7826
7827Duplicate file descriptor.
7828[clinic start generated code]*/
7829
Larry Hastings2f936352014-08-05 14:04:04 +10007830static PyObject *
7831os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007832/*[clinic end generated code: output=9a099d95881a7923 input=76e96f511be0352f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007833{
Victor Stinnerdaf45552013-08-28 00:53:59 +02007834 int res;
7835#if defined(HAVE_DUP3) && \
7836 !(defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC))
7837 /* dup3() is available on Linux 2.6.27+ and glibc 2.9 */
7838 int dup3_works = -1;
7839#endif
7840
Victor Stinner8c62be82010-05-06 00:08:46 +00007841 if (!_PyVerify_fd_dup2(fd, fd2))
7842 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +02007843
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007844 /* dup2() can fail with EINTR if the target FD is already open, because it
7845 * then has to be closed. See os_close_impl() for why we don't handle EINTR
7846 * upon close(), and therefore below.
7847 */
Victor Stinnerdaf45552013-08-28 00:53:59 +02007848#ifdef MS_WINDOWS
7849 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007850 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007851 res = dup2(fd, fd2);
Steve Dower8fc89802015-04-12 00:26:27 -04007852 _Py_END_SUPPRESS_IPH
Victor Stinnerdaf45552013-08-28 00:53:59 +02007853 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00007854 if (res < 0)
7855 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +02007856
7857 /* Character files like console cannot be make non-inheritable */
7858 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
7859 close(fd2);
7860 return NULL;
7861 }
7862
7863#elif defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC)
7864 Py_BEGIN_ALLOW_THREADS
7865 if (!inheritable)
7866 res = fcntl(fd, F_DUP2FD_CLOEXEC, fd2);
7867 else
7868 res = dup2(fd, fd2);
7869 Py_END_ALLOW_THREADS
7870 if (res < 0)
7871 return posix_error();
7872
7873#else
7874
7875#ifdef HAVE_DUP3
7876 if (!inheritable && dup3_works != 0) {
7877 Py_BEGIN_ALLOW_THREADS
7878 res = dup3(fd, fd2, O_CLOEXEC);
7879 Py_END_ALLOW_THREADS
7880 if (res < 0) {
7881 if (dup3_works == -1)
7882 dup3_works = (errno != ENOSYS);
7883 if (dup3_works)
7884 return posix_error();
7885 }
7886 }
7887
7888 if (inheritable || dup3_works == 0)
7889 {
7890#endif
7891 Py_BEGIN_ALLOW_THREADS
7892 res = dup2(fd, fd2);
7893 Py_END_ALLOW_THREADS
7894 if (res < 0)
7895 return posix_error();
7896
7897 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
7898 close(fd2);
7899 return NULL;
7900 }
7901#ifdef HAVE_DUP3
7902 }
7903#endif
7904
7905#endif
7906
Larry Hastings2f936352014-08-05 14:04:04 +10007907 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +00007908}
7909
Larry Hastings2f936352014-08-05 14:04:04 +10007910
Ross Lagerwall7807c352011-03-17 20:20:30 +02007911#ifdef HAVE_LOCKF
Larry Hastings2f936352014-08-05 14:04:04 +10007912/*[clinic input]
7913os.lockf
7914
7915 fd: int
7916 An open file descriptor.
7917 command: int
7918 One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.
7919 length: Py_off_t
7920 The number of bytes to lock, starting at the current position.
7921 /
7922
7923Apply, test or remove a POSIX lock on an open file descriptor.
7924
7925[clinic start generated code]*/
7926
Larry Hastings2f936352014-08-05 14:04:04 +10007927static PyObject *
7928os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007929/*[clinic end generated code: output=25ff778f9e2fbf1b input=65da41d2106e9b79]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007930{
7931 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +02007932
7933 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007934 res = lockf(fd, command, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +02007935 Py_END_ALLOW_THREADS
7936
7937 if (res < 0)
7938 return posix_error();
7939
7940 Py_RETURN_NONE;
7941}
Larry Hastings2f936352014-08-05 14:04:04 +10007942#endif /* HAVE_LOCKF */
Ross Lagerwall7807c352011-03-17 20:20:30 +02007943
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007944
Larry Hastings2f936352014-08-05 14:04:04 +10007945/*[clinic input]
7946os.lseek -> Py_off_t
7947
7948 fd: int
7949 position: Py_off_t
7950 how: int
7951 /
7952
7953Set the position of a file descriptor. Return the new position.
7954
7955Return the new cursor position in number of bytes
7956relative to the beginning of the file.
7957[clinic start generated code]*/
7958
Larry Hastings2f936352014-08-05 14:04:04 +10007959static Py_off_t
7960os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007961/*[clinic end generated code: output=65d4ab96d664998c input=902654ad3f96a6d3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007962{
7963 Py_off_t result;
7964
7965 if (!_PyVerify_fd(fd)) {
7966 posix_error();
7967 return -1;
7968 }
Guido van Rossum687dd131993-05-17 08:34:16 +00007969#ifdef SEEK_SET
Victor Stinner8c62be82010-05-06 00:08:46 +00007970 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
7971 switch (how) {
Larry Hastings2f936352014-08-05 14:04:04 +10007972 case 0: how = SEEK_SET; break;
7973 case 1: how = SEEK_CUR; break;
7974 case 2: how = SEEK_END; break;
Victor Stinner8c62be82010-05-06 00:08:46 +00007975 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00007976#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +00007977
Victor Stinner8c62be82010-05-06 00:08:46 +00007978 if (PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +10007979 return -1;
Guido van Rossum94f6f721999-01-06 18:42:14 +00007980
Larry Hastings2f936352014-08-05 14:04:04 +10007981 if (!_PyVerify_fd(fd)) {
7982 posix_error();
7983 return -1;
7984 }
Victor Stinner8c62be82010-05-06 00:08:46 +00007985 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007986 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner14b9b112013-06-25 00:37:25 +02007987#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10007988 result = _lseeki64(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +00007989#else
Larry Hastings2f936352014-08-05 14:04:04 +10007990 result = lseek(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +00007991#endif
Steve Dower8fc89802015-04-12 00:26:27 -04007992 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007993 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007994 if (result < 0)
7995 posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +00007996
Larry Hastings2f936352014-08-05 14:04:04 +10007997 return result;
Guido van Rossum687dd131993-05-17 08:34:16 +00007998}
7999
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008000
Larry Hastings2f936352014-08-05 14:04:04 +10008001/*[clinic input]
8002os.read
8003 fd: int
8004 length: Py_ssize_t
8005 /
8006
8007Read from a file descriptor. Returns a bytes object.
8008[clinic start generated code]*/
8009
Larry Hastings2f936352014-08-05 14:04:04 +10008010static PyObject *
8011os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008012/*[clinic end generated code: output=be24f44178455e8b input=1df2eaa27c0bf1d3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008013{
Victor Stinner8c62be82010-05-06 00:08:46 +00008014 Py_ssize_t n;
8015 PyObject *buffer;
Larry Hastings2f936352014-08-05 14:04:04 +10008016
8017 if (length < 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008018 errno = EINVAL;
8019 return posix_error();
8020 }
Larry Hastings2f936352014-08-05 14:04:04 +10008021
8022#ifdef MS_WINDOWS
Victor Stinner66aab0c2015-03-19 22:53:20 +01008023 /* On Windows, the count parameter of read() is an int */
Larry Hastings2f936352014-08-05 14:04:04 +10008024 if (length > INT_MAX)
8025 length = INT_MAX;
Larry Hastings2f936352014-08-05 14:04:04 +10008026#endif
8027
8028 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Victor Stinner8c62be82010-05-06 00:08:46 +00008029 if (buffer == NULL)
8030 return NULL;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008031
Victor Stinner66aab0c2015-03-19 22:53:20 +01008032 n = _Py_read(fd, PyBytes_AS_STRING(buffer), length);
8033 if (n == -1) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008034 Py_DECREF(buffer);
Victor Stinner66aab0c2015-03-19 22:53:20 +01008035 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00008036 }
Larry Hastings2f936352014-08-05 14:04:04 +10008037
8038 if (n != length)
Victor Stinner8c62be82010-05-06 00:08:46 +00008039 _PyBytes_Resize(&buffer, n);
Larry Hastings2f936352014-08-05 14:04:04 +10008040
Victor Stinner8c62be82010-05-06 00:08:46 +00008041 return buffer;
Guido van Rossum687dd131993-05-17 08:34:16 +00008042}
8043
Ross Lagerwall7807c352011-03-17 20:20:30 +02008044#if (defined(HAVE_SENDFILE) && (defined(__FreeBSD__) || defined(__DragonFly__) \
8045 || defined(__APPLE__))) || defined(HAVE_READV) || defined(HAVE_WRITEV)
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008046static Py_ssize_t
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008047iov_setup(struct iovec **iov, Py_buffer **buf, PyObject *seq, int cnt, int type)
8048{
8049 int i, j;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008050 Py_ssize_t blen, total = 0;
8051
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008052 *iov = PyMem_New(struct iovec, cnt);
8053 if (*iov == NULL) {
8054 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +01008055 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008056 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008057
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008058 *buf = PyMem_New(Py_buffer, cnt);
8059 if (*buf == NULL) {
8060 PyMem_Del(*iov);
8061 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +01008062 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008063 }
8064
8065 for (i = 0; i < cnt; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008066 PyObject *item = PySequence_GetItem(seq, i);
8067 if (item == NULL)
8068 goto fail;
8069 if (PyObject_GetBuffer(item, &(*buf)[i], type) == -1) {
8070 Py_DECREF(item);
8071 goto fail;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008072 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008073 Py_DECREF(item);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008074 (*iov)[i].iov_base = (*buf)[i].buf;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008075 blen = (*buf)[i].len;
8076 (*iov)[i].iov_len = blen;
8077 total += blen;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008078 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008079 return total;
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008080
8081fail:
8082 PyMem_Del(*iov);
8083 for (j = 0; j < i; j++) {
8084 PyBuffer_Release(&(*buf)[j]);
8085 }
8086 PyMem_Del(*buf);
Victor Stinner57ddf782014-01-08 15:21:28 +01008087 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008088}
8089
8090static void
8091iov_cleanup(struct iovec *iov, Py_buffer *buf, int cnt)
8092{
8093 int i;
8094 PyMem_Del(iov);
8095 for (i = 0; i < cnt; i++) {
8096 PyBuffer_Release(&buf[i]);
8097 }
8098 PyMem_Del(buf);
8099}
8100#endif
8101
Larry Hastings2f936352014-08-05 14:04:04 +10008102
Ross Lagerwall7807c352011-03-17 20:20:30 +02008103#ifdef HAVE_READV
Larry Hastings2f936352014-08-05 14:04:04 +10008104/*[clinic input]
8105os.readv -> Py_ssize_t
8106
8107 fd: int
8108 buffers: object
8109 /
8110
8111Read from a file descriptor fd into an iterable of buffers.
8112
8113The buffers should be mutable buffers accepting bytes.
8114readv will transfer data into each buffer until it is full
8115and then move on to the next buffer in the sequence to hold
8116the rest of the data.
8117
8118readv returns the total number of bytes read,
8119which may be less than the total capacity of all the buffers.
8120[clinic start generated code]*/
8121
Larry Hastings2f936352014-08-05 14:04:04 +10008122static Py_ssize_t
8123os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008124/*[clinic end generated code: output=00fc56ff1800059f input=e679eb5dbfa0357d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008125{
8126 int cnt;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008127 Py_ssize_t n;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008128 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008129 struct iovec *iov;
8130 Py_buffer *buf;
8131
Larry Hastings2f936352014-08-05 14:04:04 +10008132 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008133 PyErr_SetString(PyExc_TypeError,
8134 "readv() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +10008135 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008136 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02008137
Larry Hastings2f936352014-08-05 14:04:04 +10008138 cnt = PySequence_Size(buffers);
8139
8140 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_WRITABLE) < 0)
8141 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008142
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008143 do {
8144 Py_BEGIN_ALLOW_THREADS
8145 n = readv(fd, iov, cnt);
8146 Py_END_ALLOW_THREADS
8147 } while (n < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Ross Lagerwall7807c352011-03-17 20:20:30 +02008148
8149 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +10008150 if (n < 0) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008151 if (!async_err)
8152 posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10008153 return -1;
8154 }
Victor Stinner57ddf782014-01-08 15:21:28 +01008155
Larry Hastings2f936352014-08-05 14:04:04 +10008156 return n;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008157}
Larry Hastings2f936352014-08-05 14:04:04 +10008158#endif /* HAVE_READV */
8159
Ross Lagerwall7807c352011-03-17 20:20:30 +02008160
8161#ifdef HAVE_PREAD
Larry Hastings2f936352014-08-05 14:04:04 +10008162/*[clinic input]
8163# TODO length should be size_t! but Python doesn't support parsing size_t yet.
8164os.pread
8165
8166 fd: int
8167 length: int
8168 offset: Py_off_t
8169 /
8170
8171Read a number of bytes from a file descriptor starting at a particular offset.
8172
8173Read length bytes from file descriptor fd, starting at offset bytes from
8174the beginning of the file. The file offset remains unchanged.
8175[clinic start generated code]*/
8176
Larry Hastings2f936352014-08-05 14:04:04 +10008177static PyObject *
8178os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008179/*[clinic end generated code: output=90d1fed87f68fa33 input=084948dcbaa35d4c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008180{
Ross Lagerwall7807c352011-03-17 20:20:30 +02008181 Py_ssize_t n;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008182 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008183 PyObject *buffer;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008184
Larry Hastings2f936352014-08-05 14:04:04 +10008185 if (length < 0) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008186 errno = EINVAL;
8187 return posix_error();
8188 }
Larry Hastings2f936352014-08-05 14:04:04 +10008189 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008190 if (buffer == NULL)
8191 return NULL;
8192 if (!_PyVerify_fd(fd)) {
8193 Py_DECREF(buffer);
8194 return posix_error();
8195 }
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008196
8197 do {
8198 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04008199 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008200 n = pread(fd, PyBytes_AS_STRING(buffer), length, offset);
Steve Dower8fc89802015-04-12 00:26:27 -04008201 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008202 Py_END_ALLOW_THREADS
8203 } while (n < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
8204
Ross Lagerwall7807c352011-03-17 20:20:30 +02008205 if (n < 0) {
8206 Py_DECREF(buffer);
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008207 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008208 }
Larry Hastings2f936352014-08-05 14:04:04 +10008209 if (n != length)
Ross Lagerwall7807c352011-03-17 20:20:30 +02008210 _PyBytes_Resize(&buffer, n);
8211 return buffer;
8212}
Larry Hastings2f936352014-08-05 14:04:04 +10008213#endif /* HAVE_PREAD */
Ross Lagerwall7807c352011-03-17 20:20:30 +02008214
Larry Hastings2f936352014-08-05 14:04:04 +10008215
8216/*[clinic input]
8217os.write -> Py_ssize_t
8218
8219 fd: int
8220 data: Py_buffer
8221 /
8222
8223Write a bytes object to a file descriptor.
8224[clinic start generated code]*/
8225
Larry Hastings2f936352014-08-05 14:04:04 +10008226static Py_ssize_t
8227os_write_impl(PyModuleDef *module, int fd, Py_buffer *data)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008228/*[clinic end generated code: output=58845c93c9ee1dda input=3207e28963234f3c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008229{
Victor Stinner66aab0c2015-03-19 22:53:20 +01008230 return _Py_write(fd, data->buf, data->len);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008231}
8232
8233#ifdef HAVE_SENDFILE
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008234PyDoc_STRVAR(posix_sendfile__doc__,
8235"sendfile(out, in, offset, nbytes) -> byteswritten\n\
8236sendfile(out, in, offset, nbytes, headers=None, trailers=None, flags=0)\n\
8237 -> byteswritten\n\
8238Copy nbytes bytes from file descriptor in to file descriptor out.");
8239
Larry Hastings2f936352014-08-05 14:04:04 +10008240/* AC 3.5: don't bother converting, has optional group*/
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008241static PyObject *
8242posix_sendfile(PyObject *self, PyObject *args, PyObject *kwdict)
8243{
8244 int in, out;
8245 Py_ssize_t ret;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008246 int async_err = 0;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008247 off_t offset;
8248
8249#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
8250#ifndef __APPLE__
8251 Py_ssize_t len;
8252#endif
8253 PyObject *headers = NULL, *trailers = NULL;
8254 Py_buffer *hbuf, *tbuf;
8255 off_t sbytes;
8256 struct sf_hdtr sf;
8257 int flags = 0;
Benjamin Petersond8a43b42011-02-26 21:35:16 +00008258 static char *keywords[] = {"out", "in",
8259 "offset", "count",
8260 "headers", "trailers", "flags", NULL};
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008261
Victor Stinner6ce0dbf2013-07-07 16:32:36 +02008262 sf.headers = NULL;
8263 sf.trailers = NULL;
8264
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008265#ifdef __APPLE__
8266 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&O&|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +10008267 keywords, &out, &in, Py_off_t_converter, &offset, Py_off_t_converter, &sbytes,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008268#else
8269 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&n|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +10008270 keywords, &out, &in, Py_off_t_converter, &offset, &len,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008271#endif
8272 &headers, &trailers, &flags))
8273 return NULL;
8274 if (headers != NULL) {
8275 if (!PySequence_Check(headers)) {
8276 PyErr_SetString(PyExc_TypeError,
8277 "sendfile() headers must be a sequence or None");
8278 return NULL;
8279 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008280 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008281 sf.hdr_cnt = PySequence_Size(headers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008282 if (sf.hdr_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +01008283 (i = iov_setup(&(sf.headers), &hbuf,
8284 headers, sf.hdr_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008285 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008286#ifdef __APPLE__
8287 sbytes += i;
8288#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008289 }
8290 }
8291 if (trailers != NULL) {
8292 if (!PySequence_Check(trailers)) {
8293 PyErr_SetString(PyExc_TypeError,
8294 "sendfile() trailers must be a sequence or None");
8295 return NULL;
8296 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008297 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008298 sf.trl_cnt = PySequence_Size(trailers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008299 if (sf.trl_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +01008300 (i = iov_setup(&(sf.trailers), &tbuf,
8301 trailers, sf.trl_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008302 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008303#ifdef __APPLE__
8304 sbytes += i;
8305#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008306 }
8307 }
8308
Steve Dower8fc89802015-04-12 00:26:27 -04008309 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008310 do {
8311 Py_BEGIN_ALLOW_THREADS
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008312#ifdef __APPLE__
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008313 ret = sendfile(in, out, offset, &sbytes, &sf, flags);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008314#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008315 ret = sendfile(in, out, offset, len, &sf, &sbytes, flags);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008316#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008317 Py_END_ALLOW_THREADS
8318 } while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Steve Dower8fc89802015-04-12 00:26:27 -04008319 _Py_END_SUPPRESS_IPH
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008320
8321 if (sf.headers != NULL)
8322 iov_cleanup(sf.headers, hbuf, sf.hdr_cnt);
8323 if (sf.trailers != NULL)
8324 iov_cleanup(sf.trailers, tbuf, sf.trl_cnt);
8325
8326 if (ret < 0) {
8327 if ((errno == EAGAIN) || (errno == EBUSY)) {
8328 if (sbytes != 0) {
8329 // some data has been sent
8330 goto done;
8331 }
8332 else {
8333 // no data has been sent; upper application is supposed
8334 // to retry on EAGAIN or EBUSY
8335 return posix_error();
8336 }
8337 }
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008338 return (!async_err) ? posix_error() : NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008339 }
8340 goto done;
8341
8342done:
8343 #if !defined(HAVE_LARGEFILE_SUPPORT)
8344 return Py_BuildValue("l", sbytes);
8345 #else
8346 return Py_BuildValue("L", sbytes);
8347 #endif
8348
8349#else
8350 Py_ssize_t count;
8351 PyObject *offobj;
8352 static char *keywords[] = {"out", "in",
8353 "offset", "count", NULL};
8354 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiOn:sendfile",
8355 keywords, &out, &in, &offobj, &count))
8356 return NULL;
8357#ifdef linux
8358 if (offobj == Py_None) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008359 do {
8360 Py_BEGIN_ALLOW_THREADS
8361 ret = sendfile(out, in, NULL, count);
8362 Py_END_ALLOW_THREADS
8363 } while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008364 if (ret < 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008365 return (!async_err) ? posix_error() : NULL;
Giampaolo Rodola'ff1a7352011-04-19 09:47:16 +02008366 return Py_BuildValue("n", ret);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008367 }
8368#endif
Larry Hastings2f936352014-08-05 14:04:04 +10008369 if (!Py_off_t_converter(offobj, &offset))
Antoine Pitroudcc20b82011-02-26 13:38:35 +00008370 return NULL;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008371
8372 do {
8373 Py_BEGIN_ALLOW_THREADS
8374 ret = sendfile(out, in, &offset, count);
8375 Py_END_ALLOW_THREADS
8376 } while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008377 if (ret < 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008378 return (!async_err) ? posix_error() : NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008379 return Py_BuildValue("n", ret);
8380#endif
8381}
Larry Hastings2f936352014-08-05 14:04:04 +10008382#endif /* HAVE_SENDFILE */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008383
Larry Hastings2f936352014-08-05 14:04:04 +10008384
8385/*[clinic input]
8386os.fstat
8387
8388 fd : int
8389
8390Perform a stat system call on the given file descriptor.
8391
8392Like stat(), but for an open file descriptor.
8393Equivalent to os.stat(fd).
8394[clinic start generated code]*/
8395
Larry Hastings2f936352014-08-05 14:04:04 +10008396static PyObject *
8397os_fstat_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008398/*[clinic end generated code: output=d71fe98bf042b626 input=27e0e0ebbe5600c9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008399{
Victor Stinner8c62be82010-05-06 00:08:46 +00008400 STRUCT_STAT st;
8401 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008402 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008403
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008404 do {
8405 Py_BEGIN_ALLOW_THREADS
8406 res = FSTAT(fd, &st);
8407 Py_END_ALLOW_THREADS
8408 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Victor Stinner8c62be82010-05-06 00:08:46 +00008409 if (res != 0) {
Martin v. Löwis14694662006-02-03 12:54:16 +00008410#ifdef MS_WINDOWS
Victor Stinnerb024e842012-10-31 22:24:06 +01008411 return PyErr_SetFromWindowsErr(0);
Martin v. Löwis14694662006-02-03 12:54:16 +00008412#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008413 return (!async_err) ? posix_error() : NULL;
Martin v. Löwis14694662006-02-03 12:54:16 +00008414#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008415 }
Tim Peters5aa91602002-01-30 05:46:57 +00008416
Victor Stinner4195b5c2012-02-08 23:03:19 +01008417 return _pystat_fromstructstat(&st);
Guido van Rossum687dd131993-05-17 08:34:16 +00008418}
8419
Larry Hastings2f936352014-08-05 14:04:04 +10008420
8421/*[clinic input]
8422os.isatty -> bool
8423 fd: int
8424 /
8425
8426Return True if the fd is connected to a terminal.
8427
8428Return True if the file descriptor is an open file descriptor
8429connected to the slave end of a terminal.
8430[clinic start generated code]*/
8431
Larry Hastings2f936352014-08-05 14:04:04 +10008432static int
8433os_isatty_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008434/*[clinic end generated code: output=acec9d3c29d16d33 input=08ce94aa1eaf7b5e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008435{
Steve Dower8fc89802015-04-12 00:26:27 -04008436 int return_value;
Larry Hastings2f936352014-08-05 14:04:04 +10008437 if (!_PyVerify_fd(fd))
8438 return 0;
Steve Dower8fc89802015-04-12 00:26:27 -04008439 _Py_BEGIN_SUPPRESS_IPH
8440 return_value = isatty(fd);
8441 _Py_END_SUPPRESS_IPH
8442 return return_value;
Larry Hastings2f936352014-08-05 14:04:04 +10008443}
8444
8445
Guido van Rossuma4916fa1996-05-23 22:58:55 +00008446#ifdef HAVE_PIPE
Larry Hastings2f936352014-08-05 14:04:04 +10008447/*[clinic input]
8448os.pipe
8449
8450Create a pipe.
8451
8452Returns a tuple of two file descriptors:
8453 (read_fd, write_fd)
8454[clinic start generated code]*/
8455
Larry Hastings2f936352014-08-05 14:04:04 +10008456static PyObject *
8457os_pipe_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008458/*[clinic end generated code: output=6b0cd3f868ec3c40 input=02535e8c8fa6c4d4]*/
Guido van Rossum687dd131993-05-17 08:34:16 +00008459{
Victor Stinner8c62be82010-05-06 00:08:46 +00008460 int fds[2];
Victor Stinnerdaf45552013-08-28 00:53:59 +02008461#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00008462 HANDLE read, write;
Victor Stinnerdaf45552013-08-28 00:53:59 +02008463 SECURITY_ATTRIBUTES attr;
Victor Stinner8c62be82010-05-06 00:08:46 +00008464 BOOL ok;
Victor Stinnerdaf45552013-08-28 00:53:59 +02008465#else
8466 int res;
8467#endif
8468
8469#ifdef MS_WINDOWS
8470 attr.nLength = sizeof(attr);
8471 attr.lpSecurityDescriptor = NULL;
8472 attr.bInheritHandle = FALSE;
8473
8474 Py_BEGIN_ALLOW_THREADS
8475 ok = CreatePipe(&read, &write, &attr, 0);
8476 if (ok) {
8477 fds[0] = _open_osfhandle((Py_intptr_t)read, _O_RDONLY);
8478 fds[1] = _open_osfhandle((Py_intptr_t)write, _O_WRONLY);
8479 if (fds[0] == -1 || fds[1] == -1) {
8480 CloseHandle(read);
8481 CloseHandle(write);
8482 ok = 0;
8483 }
8484 }
8485 Py_END_ALLOW_THREADS
8486
Victor Stinner8c62be82010-05-06 00:08:46 +00008487 if (!ok)
Victor Stinnerb024e842012-10-31 22:24:06 +01008488 return PyErr_SetFromWindowsErr(0);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008489#else
8490
8491#ifdef HAVE_PIPE2
8492 Py_BEGIN_ALLOW_THREADS
8493 res = pipe2(fds, O_CLOEXEC);
8494 Py_END_ALLOW_THREADS
8495
8496 if (res != 0 && errno == ENOSYS)
8497 {
8498#endif
8499 Py_BEGIN_ALLOW_THREADS
8500 res = pipe(fds);
8501 Py_END_ALLOW_THREADS
8502
8503 if (res == 0) {
8504 if (_Py_set_inheritable(fds[0], 0, NULL) < 0) {
8505 close(fds[0]);
8506 close(fds[1]);
8507 return NULL;
8508 }
8509 if (_Py_set_inheritable(fds[1], 0, NULL) < 0) {
8510 close(fds[0]);
8511 close(fds[1]);
8512 return NULL;
8513 }
8514 }
8515#ifdef HAVE_PIPE2
8516 }
8517#endif
8518
8519 if (res != 0)
8520 return PyErr_SetFromErrno(PyExc_OSError);
8521#endif /* !MS_WINDOWS */
8522 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum687dd131993-05-17 08:34:16 +00008523}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00008524#endif /* HAVE_PIPE */
8525
Larry Hastings2f936352014-08-05 14:04:04 +10008526
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008527#ifdef HAVE_PIPE2
Larry Hastings2f936352014-08-05 14:04:04 +10008528/*[clinic input]
8529os.pipe2
8530
8531 flags: int
8532 /
8533
8534Create a pipe with flags set atomically.
8535
8536Returns a tuple of two file descriptors:
8537 (read_fd, write_fd)
8538
8539flags can be constructed by ORing together one or more of these values:
8540O_NONBLOCK, O_CLOEXEC.
8541[clinic start generated code]*/
8542
Larry Hastings2f936352014-08-05 14:04:04 +10008543static PyObject *
8544os_pipe2_impl(PyModuleDef *module, int flags)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008545/*[clinic end generated code: output=c15b6075d0c6b2e7 input=f261b6e7e63c6817]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008546{
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008547 int fds[2];
8548 int res;
8549
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008550 res = pipe2(fds, flags);
8551 if (res != 0)
8552 return posix_error();
8553 return Py_BuildValue("(ii)", fds[0], fds[1]);
8554}
8555#endif /* HAVE_PIPE2 */
8556
Larry Hastings2f936352014-08-05 14:04:04 +10008557
Ross Lagerwall7807c352011-03-17 20:20:30 +02008558#ifdef HAVE_WRITEV
Larry Hastings2f936352014-08-05 14:04:04 +10008559/*[clinic input]
8560os.writev -> Py_ssize_t
8561 fd: int
8562 buffers: object
8563 /
8564
8565Iterate over buffers, and write the contents of each to a file descriptor.
8566
8567Returns the total number of bytes written.
8568buffers must be a sequence of bytes-like objects.
8569[clinic start generated code]*/
8570
Larry Hastings2f936352014-08-05 14:04:04 +10008571static Py_ssize_t
8572os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008573/*[clinic end generated code: output=a48925dbf2d5c238 input=5b8d17fe4189d2fe]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008574{
8575 int cnt;
8576 Py_ssize_t result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008577 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008578 struct iovec *iov;
8579 Py_buffer *buf;
Larry Hastings2f936352014-08-05 14:04:04 +10008580
8581 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008582 PyErr_SetString(PyExc_TypeError,
8583 "writev() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +10008584 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008585 }
Larry Hastings2f936352014-08-05 14:04:04 +10008586 cnt = PySequence_Size(buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008587
Larry Hastings2f936352014-08-05 14:04:04 +10008588 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_SIMPLE) < 0) {
8589 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008590 }
8591
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008592 do {
8593 Py_BEGIN_ALLOW_THREADS
8594 result = writev(fd, iov, cnt);
8595 Py_END_ALLOW_THREADS
8596 } while (result < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Ross Lagerwall7807c352011-03-17 20:20:30 +02008597
8598 iov_cleanup(iov, buf, cnt);
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008599 if (result < 0 && !async_err)
Larry Hastings2f936352014-08-05 14:04:04 +10008600 posix_error();
Victor Stinner57ddf782014-01-08 15:21:28 +01008601
Georg Brandl306336b2012-06-24 12:55:33 +02008602 return result;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008603}
Larry Hastings2f936352014-08-05 14:04:04 +10008604#endif /* HAVE_WRITEV */
8605
8606
8607#ifdef HAVE_PWRITE
8608/*[clinic input]
8609os.pwrite -> Py_ssize_t
8610
8611 fd: int
8612 buffer: Py_buffer
8613 offset: Py_off_t
8614 /
8615
8616Write bytes to a file descriptor starting at a particular offset.
8617
8618Write buffer to fd, starting at offset bytes from the beginning of
8619the file. Returns the number of bytes writte. Does not change the
8620current file offset.
8621[clinic start generated code]*/
8622
Larry Hastings2f936352014-08-05 14:04:04 +10008623static Py_ssize_t
Larry Hastings89964c42015-04-14 18:07:59 -04008624os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer,
8625 Py_off_t offset)
8626/*[clinic end generated code: output=93aabdb40e17d325 input=19903f1b3dd26377]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008627{
8628 Py_ssize_t size;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008629 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008630
8631 if (!_PyVerify_fd(fd)) {
8632 posix_error();
8633 return -1;
8634 }
8635
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008636 do {
8637 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04008638 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008639 size = pwrite(fd, buffer->buf, (size_t)buffer->len, offset);
Steve Dower8fc89802015-04-12 00:26:27 -04008640 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008641 Py_END_ALLOW_THREADS
8642 } while (size < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Larry Hastings2f936352014-08-05 14:04:04 +10008643
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008644 if (size < 0 && !async_err)
Larry Hastings2f936352014-08-05 14:04:04 +10008645 posix_error();
8646 return size;
8647}
8648#endif /* HAVE_PWRITE */
8649
8650
8651#ifdef HAVE_MKFIFO
8652/*[clinic input]
8653os.mkfifo
8654
8655 path: path_t
8656 mode: int=0o666
8657 *
8658 dir_fd: dir_fd(requires='mkfifoat')=None
8659
8660Create a "fifo" (a POSIX named pipe).
8661
8662If dir_fd is not None, it should be a file descriptor open to a directory,
8663 and path should be relative; path will then be relative to that directory.
8664dir_fd may not be implemented on your platform.
8665 If it is unavailable, using it will raise a NotImplementedError.
8666[clinic start generated code]*/
8667
Larry Hastings2f936352014-08-05 14:04:04 +10008668static PyObject *
8669os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008670/*[clinic end generated code: output=8f5f5e72c630049a input=73032e98a36e0e19]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008671{
8672 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008673 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008674
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008675 do {
8676 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10008677#ifdef HAVE_MKFIFOAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008678 if (dir_fd != DEFAULT_DIR_FD)
8679 result = mkfifoat(dir_fd, path->narrow, mode);
8680 else
Ross Lagerwall7807c352011-03-17 20:20:30 +02008681#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008682 result = mkfifo(path->narrow, mode);
8683 Py_END_ALLOW_THREADS
8684 } while (result != 0 && errno == EINTR &&
8685 !(async_err = PyErr_CheckSignals()));
8686 if (result != 0)
8687 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008688
8689 Py_RETURN_NONE;
8690}
8691#endif /* HAVE_MKFIFO */
8692
8693
8694#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
8695/*[clinic input]
8696os.mknod
8697
8698 path: path_t
8699 mode: int=0o600
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008700 device: dev_t=0
Larry Hastings2f936352014-08-05 14:04:04 +10008701 *
8702 dir_fd: dir_fd(requires='mknodat')=None
8703
8704Create a node in the file system.
8705
8706Create a node in the file system (file, device special file or named pipe)
8707at path. mode specifies both the permissions to use and the
8708type of node to be created, being combined (bitwise OR) with one of
8709S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,
8710device defines the newly created device special file (probably using
8711os.makedev()). Otherwise device is ignored.
8712
8713If dir_fd is not None, it should be a file descriptor open to a directory,
8714 and path should be relative; path will then be relative to that directory.
8715dir_fd may not be implemented on your platform.
8716 If it is unavailable, using it will raise a NotImplementedError.
8717[clinic start generated code]*/
8718
Larry Hastings2f936352014-08-05 14:04:04 +10008719static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008720os_mknod_impl(PyModuleDef *module, path_t *path, int mode, dev_t device,
8721 int dir_fd)
8722/*[clinic end generated code: output=5151a8a9f754d272 input=ee44531551a4d83b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008723{
8724 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008725 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008726
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008727 do {
8728 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10008729#ifdef HAVE_MKNODAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008730 if (dir_fd != DEFAULT_DIR_FD)
8731 result = mknodat(dir_fd, path->narrow, mode, device);
8732 else
Larry Hastings2f936352014-08-05 14:04:04 +10008733#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008734 result = mknod(path->narrow, mode, device);
8735 Py_END_ALLOW_THREADS
8736 } while (result != 0 && errno == EINTR &&
8737 !(async_err = PyErr_CheckSignals()));
8738 if (result != 0)
8739 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008740
8741 Py_RETURN_NONE;
8742}
8743#endif /* defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV) */
8744
8745
8746#ifdef HAVE_DEVICE_MACROS
8747/*[clinic input]
8748os.major -> unsigned_int
8749
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008750 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008751 /
8752
8753Extracts a device major number from a raw device number.
8754[clinic start generated code]*/
8755
Larry Hastings2f936352014-08-05 14:04:04 +10008756static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008757os_major_impl(PyModuleDef *module, dev_t device)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008758/*[clinic end generated code: output=ba55693ab49bac34 input=1e16a4d30c4d4462]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008759{
8760 return major(device);
8761}
8762
8763
8764/*[clinic input]
8765os.minor -> unsigned_int
8766
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008767 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008768 /
8769
8770Extracts a device minor number from a raw device number.
8771[clinic start generated code]*/
8772
Larry Hastings2f936352014-08-05 14:04:04 +10008773static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008774os_minor_impl(PyModuleDef *module, dev_t device)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008775/*[clinic end generated code: output=2867219ebf274e27 input=0842c6d23f24c65e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008776{
8777 return minor(device);
8778}
8779
8780
8781/*[clinic input]
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008782os.makedev -> dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008783
8784 major: int
8785 minor: int
8786 /
8787
8788Composes a raw device number from the major and minor device numbers.
8789[clinic start generated code]*/
8790
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008791static dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008792os_makedev_impl(PyModuleDef *module, int major, int minor)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008793/*[clinic end generated code: output=7cb6264352437660 input=4b9fd8fc73cbe48f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008794{
8795 return makedev(major, minor);
8796}
8797#endif /* HAVE_DEVICE_MACROS */
8798
8799
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008800#if defined HAVE_FTRUNCATE || defined MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008801/*[clinic input]
8802os.ftruncate
8803
8804 fd: int
8805 length: Py_off_t
8806 /
8807
8808Truncate a file, specified by file descriptor, to a specific length.
8809[clinic start generated code]*/
8810
Larry Hastings2f936352014-08-05 14:04:04 +10008811static PyObject *
8812os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008813/*[clinic end generated code: output=3666f401d76bf834 input=63b43641e52818f2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008814{
8815 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008816 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008817
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008818 if (!_PyVerify_fd(fd))
8819 return posix_error();
8820
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008821 do {
8822 Py_BEGIN_ALLOW_THREADS
Steve Dowera1c7e722015-04-12 00:26:43 -04008823 _Py_BEGIN_SUPPRESS_IPH
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008824#ifdef MS_WINDOWS
8825 result = _chsize_s(fd, length);
8826#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008827 result = ftruncate(fd, length);
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008828#endif
Steve Dowera1c7e722015-04-12 00:26:43 -04008829 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008830 Py_END_ALLOW_THREADS
8831 } while (result != 0 && errno == EINTR &&
8832 !(async_err = PyErr_CheckSignals()));
8833 if (result != 0)
8834 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008835 Py_RETURN_NONE;
8836}
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008837#endif /* HAVE_FTRUNCATE || MS_WINDOWS */
Larry Hastings2f936352014-08-05 14:04:04 +10008838
8839
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008840#if defined HAVE_TRUNCATE || defined MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008841/*[clinic input]
8842os.truncate
8843 path: path_t(allow_fd='PATH_HAVE_FTRUNCATE')
8844 length: Py_off_t
8845
8846Truncate a file, specified by path, to a specific length.
8847
8848On some platforms, path may also be specified as an open file descriptor.
8849 If this functionality is unavailable, using it raises an exception.
8850[clinic start generated code]*/
8851
Larry Hastings2f936352014-08-05 14:04:04 +10008852static PyObject *
8853os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008854/*[clinic end generated code: output=f60a9e08370e9e2e input=77229cf0b50a9b77]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008855{
8856 int result;
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008857#ifdef MS_WINDOWS
8858 int fd;
8859#endif
8860
8861 if (path->fd != -1)
8862 return os_ftruncate_impl(module, path->fd, length);
Larry Hastings2f936352014-08-05 14:04:04 +10008863
8864 Py_BEGIN_ALLOW_THREADS
Steve Dowera1c7e722015-04-12 00:26:43 -04008865 _Py_BEGIN_SUPPRESS_IPH
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008866#ifdef MS_WINDOWS
8867 if (path->wide)
8868 fd = _wopen(path->wide, _O_WRONLY | _O_BINARY | _O_NOINHERIT);
Larry Hastings2f936352014-08-05 14:04:04 +10008869 else
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008870 fd = _open(path->narrow, _O_WRONLY | _O_BINARY | _O_NOINHERIT);
8871 if (fd < 0)
8872 result = -1;
8873 else {
8874 result = _chsize_s(fd, length);
8875 close(fd);
8876 if (result < 0)
8877 errno = result;
8878 }
8879#else
8880 result = truncate(path->narrow, length);
Larry Hastings2f936352014-08-05 14:04:04 +10008881#endif
Steve Dowera1c7e722015-04-12 00:26:43 -04008882 _Py_END_SUPPRESS_IPH
Larry Hastings2f936352014-08-05 14:04:04 +10008883 Py_END_ALLOW_THREADS
8884 if (result < 0)
8885 return path_error(path);
8886
8887 Py_RETURN_NONE;
8888}
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008889#endif /* HAVE_TRUNCATE || MS_WINDOWS */
Larry Hastings2f936352014-08-05 14:04:04 +10008890
Ross Lagerwall7807c352011-03-17 20:20:30 +02008891
Victor Stinnerd6b17692014-09-30 12:20:05 +02008892/* Issue #22396: On 32-bit AIX platform, the prototypes of os.posix_fadvise()
8893 and os.posix_fallocate() in system headers are wrong if _LARGE_FILES is
8894 defined, which is the case in Python on AIX. AIX bug report:
8895 http://www-01.ibm.com/support/docview.wss?uid=isg1IV56170 */
8896#if defined(_AIX) && defined(_LARGE_FILES) && !defined(__64BIT__)
8897# define POSIX_FADVISE_AIX_BUG
8898#endif
8899
Victor Stinnerec39e262014-09-30 12:35:58 +02008900
Victor Stinnerd6b17692014-09-30 12:20:05 +02008901#if defined(HAVE_POSIX_FALLOCATE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +10008902/*[clinic input]
8903os.posix_fallocate
8904
8905 fd: int
8906 offset: Py_off_t
8907 length: Py_off_t
8908 /
8909
8910Ensure a file has allocated at least a particular number of bytes on disk.
8911
8912Ensure that the file specified by fd encompasses a range of bytes
8913starting at offset bytes from the beginning and continuing for length bytes.
8914[clinic start generated code]*/
8915
Larry Hastings2f936352014-08-05 14:04:04 +10008916static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008917os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset,
8918 Py_off_t length)
8919/*[clinic end generated code: output=7f6f87a8c751e1b4 input=d7a2ef0ab2ca52fb]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008920{
8921 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008922 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008923
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008924 do {
8925 Py_BEGIN_ALLOW_THREADS
8926 result = posix_fallocate(fd, offset, length);
8927 Py_END_ALLOW_THREADS
8928 } while (result != 0 && errno == EINTR &&
8929 !(async_err = PyErr_CheckSignals()));
8930 if (result != 0)
8931 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008932 Py_RETURN_NONE;
8933}
Victor Stinnerec39e262014-09-30 12:35:58 +02008934#endif /* HAVE_POSIX_FALLOCATE) && !POSIX_FADVISE_AIX_BUG */
Larry Hastings2f936352014-08-05 14:04:04 +10008935
Ross Lagerwall7807c352011-03-17 20:20:30 +02008936
Victor Stinnerd6b17692014-09-30 12:20:05 +02008937#if defined(HAVE_POSIX_FADVISE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +10008938/*[clinic input]
8939os.posix_fadvise
8940
8941 fd: int
8942 offset: Py_off_t
8943 length: Py_off_t
8944 advice: int
8945 /
8946
8947Announce an intention to access data in a specific pattern.
8948
8949Announce an intention to access data in a specific pattern, thus allowing
8950the kernel to make optimizations.
8951The advice applies to the region of the file specified by fd starting at
8952offset and continuing for length bytes.
8953advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,
8954POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or
8955POSIX_FADV_DONTNEED.
8956[clinic start generated code]*/
8957
Larry Hastings2f936352014-08-05 14:04:04 +10008958static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008959os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset,
8960 Py_off_t length, int advice)
8961/*[clinic end generated code: output=457ce6a67189e10d input=0fbe554edc2f04b5]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008962{
8963 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008964 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008965
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008966 do {
8967 Py_BEGIN_ALLOW_THREADS
8968 result = posix_fadvise(fd, offset, length, advice);
8969 Py_END_ALLOW_THREADS
8970 } while (result != 0 && errno == EINTR &&
8971 !(async_err = PyErr_CheckSignals()));
8972 if (result != 0)
8973 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008974 Py_RETURN_NONE;
8975}
Victor Stinnerec39e262014-09-30 12:35:58 +02008976#endif /* HAVE_POSIX_FADVISE && !POSIX_FADVISE_AIX_BUG */
Ross Lagerwall7807c352011-03-17 20:20:30 +02008977
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00008978#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008979
Fred Drake762e2061999-08-26 17:23:54 +00008980/* Save putenv() parameters as values here, so we can collect them when they
8981 * get re-set with another call for the same key. */
8982static PyObject *posix_putenv_garbage;
8983
Larry Hastings2f936352014-08-05 14:04:04 +10008984static void
8985posix_putenv_garbage_setitem(PyObject *name, PyObject *value)
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00008986{
Larry Hastings2f936352014-08-05 14:04:04 +10008987 /* Install the first arg and newstr in posix_putenv_garbage;
8988 * this will cause previous value to be collected. This has to
8989 * happen after the real putenv() call because the old value
8990 * was still accessible until then. */
8991 if (PyDict_SetItem(posix_putenv_garbage, name, value))
8992 /* really not much we can do; just leak */
8993 PyErr_Clear();
8994 else
8995 Py_DECREF(value);
8996}
8997
8998
Thomas Hellerf78f12a2007-11-08 19:33:05 +00008999#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10009000/*[clinic input]
9001os.putenv
9002
9003 name: unicode
9004 value: unicode
9005 /
9006
9007Change or add an environment variable.
9008[clinic start generated code]*/
9009
Larry Hastings2f936352014-08-05 14:04:04 +10009010static PyObject *
9011os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009012/*[clinic end generated code: output=a2438cf95e5a0c1c input=ba586581c2e6105f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009013{
9014 wchar_t *env;
9015
9016 PyObject *unicode = PyUnicode_FromFormat("%U=%U", name, value);
9017 if (unicode == NULL) {
Victor Stinner84ae1182010-05-06 22:05:07 +00009018 PyErr_NoMemory();
Larry Hastings2f936352014-08-05 14:04:04 +10009019 return NULL;
Victor Stinner84ae1182010-05-06 22:05:07 +00009020 }
Larry Hastings2f936352014-08-05 14:04:04 +10009021 if (_MAX_ENV < PyUnicode_GET_LENGTH(unicode)) {
Victor Stinner65170952011-11-22 22:16:17 +01009022 PyErr_Format(PyExc_ValueError,
9023 "the environment variable is longer than %u characters",
9024 _MAX_ENV);
9025 goto error;
9026 }
9027
Larry Hastings2f936352014-08-05 14:04:04 +10009028 env = PyUnicode_AsUnicode(unicode);
9029 if (env == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02009030 goto error;
Larry Hastings2f936352014-08-05 14:04:04 +10009031 if (_wputenv(env)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009032 posix_error();
Victor Stinner84ae1182010-05-06 22:05:07 +00009033 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00009034 }
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009035
Larry Hastings2f936352014-08-05 14:04:04 +10009036 posix_putenv_garbage_setitem(name, unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +00009037 Py_RETURN_NONE;
9038
9039error:
Larry Hastings2f936352014-08-05 14:04:04 +10009040 Py_DECREF(unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +00009041 return NULL;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009042}
Larry Hastings2f936352014-08-05 14:04:04 +10009043#else /* MS_WINDOWS */
9044/*[clinic input]
9045os.putenv
Guido van Rossumb6a47161997-09-15 22:54:34 +00009046
Larry Hastings2f936352014-08-05 14:04:04 +10009047 name: FSConverter
9048 value: FSConverter
9049 /
9050
9051Change or add an environment variable.
9052[clinic start generated code]*/
9053
Larry Hastings2f936352014-08-05 14:04:04 +10009054static PyObject *
9055os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009056/*[clinic end generated code: output=a2438cf95e5a0c1c input=a97bc6152f688d31]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009057{
9058 PyObject *bytes = NULL;
9059 char *env;
9060 char *name_string = PyBytes_AsString(name);
9061 char *value_string = PyBytes_AsString(value);
9062
9063 bytes = PyBytes_FromFormat("%s=%s", name_string, value_string);
9064 if (bytes == NULL) {
9065 PyErr_NoMemory();
9066 return NULL;
9067 }
9068
9069 env = PyBytes_AS_STRING(bytes);
9070 if (putenv(env)) {
9071 Py_DECREF(bytes);
9072 return posix_error();
9073 }
9074
9075 posix_putenv_garbage_setitem(name, bytes);
9076 Py_RETURN_NONE;
9077}
9078#endif /* MS_WINDOWS */
9079#endif /* HAVE_PUTENV */
9080
9081
9082#ifdef HAVE_UNSETENV
9083/*[clinic input]
9084os.unsetenv
9085 name: FSConverter
9086 /
9087
9088Delete an environment variable.
9089[clinic start generated code]*/
9090
Larry Hastings2f936352014-08-05 14:04:04 +10009091static PyObject *
9092os_unsetenv_impl(PyModuleDef *module, PyObject *name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009093/*[clinic end generated code: output=25994b57016a2dc9 input=2bb5288a599c7107]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009094{
Victor Stinner984890f2011-11-24 13:53:38 +01009095#ifndef HAVE_BROKEN_UNSETENV
Victor Stinner60b385e2011-11-22 22:01:28 +01009096 int err;
Victor Stinner984890f2011-11-24 13:53:38 +01009097#endif
Victor Stinner84ae1182010-05-06 22:05:07 +00009098
Victor Stinner984890f2011-11-24 13:53:38 +01009099#ifdef HAVE_BROKEN_UNSETENV
9100 unsetenv(PyBytes_AS_STRING(name));
9101#else
Victor Stinner65170952011-11-22 22:16:17 +01009102 err = unsetenv(PyBytes_AS_STRING(name));
Larry Hastings2f936352014-08-05 14:04:04 +10009103 if (err)
Victor Stinner60b385e2011-11-22 22:01:28 +01009104 return posix_error();
Victor Stinner984890f2011-11-24 13:53:38 +01009105#endif
Guido van Rossumc524d952001-10-19 01:31:59 +00009106
Victor Stinner8c62be82010-05-06 00:08:46 +00009107 /* Remove the key from posix_putenv_garbage;
9108 * this will cause it to be collected. This has to
9109 * happen after the real unsetenv() call because the
9110 * old value was still accessible until then.
9111 */
Victor Stinner65170952011-11-22 22:16:17 +01009112 if (PyDict_DelItem(posix_putenv_garbage, name)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009113 /* really not much we can do; just leak */
9114 PyErr_Clear();
9115 }
Victor Stinner84ae1182010-05-06 22:05:07 +00009116 Py_RETURN_NONE;
Guido van Rossumc524d952001-10-19 01:31:59 +00009117}
Larry Hastings2f936352014-08-05 14:04:04 +10009118#endif /* HAVE_UNSETENV */
Guido van Rossumc524d952001-10-19 01:31:59 +00009119
Larry Hastings2f936352014-08-05 14:04:04 +10009120
9121/*[clinic input]
9122os.strerror
9123
9124 code: int
9125 /
9126
9127Translate an error code to a message string.
9128[clinic start generated code]*/
9129
Larry Hastings2f936352014-08-05 14:04:04 +10009130static PyObject *
9131os_strerror_impl(PyModuleDef *module, int code)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009132/*[clinic end generated code: output=0280c6af51e5c9fe input=75a8673d97915a91]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009133{
9134 char *message = strerror(code);
Victor Stinner8c62be82010-05-06 00:08:46 +00009135 if (message == NULL) {
9136 PyErr_SetString(PyExc_ValueError,
9137 "strerror() argument out of range");
9138 return NULL;
9139 }
Victor Stinner1b579672011-12-17 05:47:23 +01009140 return PyUnicode_DecodeLocale(message, "surrogateescape");
Guido van Rossumb6a47161997-09-15 22:54:34 +00009141}
Guido van Rossumb6a47161997-09-15 22:54:34 +00009142
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009143
Guido van Rossumc9641791998-08-04 15:26:23 +00009144#ifdef HAVE_SYS_WAIT_H
Fred Drake106c1a02002-04-23 15:58:02 +00009145#ifdef WCOREDUMP
Larry Hastings2f936352014-08-05 14:04:04 +10009146/*[clinic input]
9147os.WCOREDUMP -> bool
9148
9149 status: int
9150 /
9151
9152Return True if the process returning status was dumped to a core file.
9153[clinic start generated code]*/
9154
Larry Hastings2f936352014-08-05 14:04:04 +10009155static int
9156os_WCOREDUMP_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009157/*[clinic end generated code: output=134f70bbe63fbf41 input=8b05e7ab38528d04]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009158{
9159 WAIT_TYPE wait_status;
9160 WAIT_STATUS_INT(wait_status) = status;
9161 return WCOREDUMP(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +00009162}
9163#endif /* WCOREDUMP */
9164
Larry Hastings2f936352014-08-05 14:04:04 +10009165
Fred Drake106c1a02002-04-23 15:58:02 +00009166#ifdef WIFCONTINUED
Larry Hastings2f936352014-08-05 14:04:04 +10009167/*[clinic input]
9168os.WIFCONTINUED -> bool
9169
9170 status: int
9171
9172Return True if a particular process was continued from a job control stop.
9173
9174Return True if the process returning status was continued from a
9175job control stop.
9176[clinic start generated code]*/
9177
Larry Hastings2f936352014-08-05 14:04:04 +10009178static int
9179os_WIFCONTINUED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009180/*[clinic end generated code: output=9cdd26543ebb6dcd input=e777e7d38eb25bd9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009181{
9182 WAIT_TYPE wait_status;
9183 WAIT_STATUS_INT(wait_status) = status;
9184 return WIFCONTINUED(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +00009185}
9186#endif /* WIFCONTINUED */
9187
Larry Hastings2f936352014-08-05 14:04:04 +10009188
Guido van Rossumc9641791998-08-04 15:26:23 +00009189#ifdef WIFSTOPPED
Larry Hastings2f936352014-08-05 14:04:04 +10009190/*[clinic input]
9191os.WIFSTOPPED -> bool
9192
9193 status: int
9194
9195Return True if the process returning status was stopped.
9196[clinic start generated code]*/
9197
Larry Hastings2f936352014-08-05 14:04:04 +10009198static int
9199os_WIFSTOPPED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009200/*[clinic end generated code: output=73bf35e44994a724 input=043cb7f1289ef904]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009201{
9202 WAIT_TYPE wait_status;
9203 WAIT_STATUS_INT(wait_status) = status;
9204 return WIFSTOPPED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009205}
9206#endif /* WIFSTOPPED */
9207
Larry Hastings2f936352014-08-05 14:04:04 +10009208
Guido van Rossumc9641791998-08-04 15:26:23 +00009209#ifdef WIFSIGNALED
Larry Hastings2f936352014-08-05 14:04:04 +10009210/*[clinic input]
9211os.WIFSIGNALED -> bool
9212
9213 status: int
9214
9215Return True if the process returning status was terminated by a signal.
9216[clinic start generated code]*/
9217
Larry Hastings2f936352014-08-05 14:04:04 +10009218static int
9219os_WIFSIGNALED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009220/*[clinic end generated code: output=2697975771872420 input=d55ba7cc9ce5dc43]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009221{
9222 WAIT_TYPE wait_status;
9223 WAIT_STATUS_INT(wait_status) = status;
9224 return WIFSIGNALED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009225}
9226#endif /* WIFSIGNALED */
9227
Larry Hastings2f936352014-08-05 14:04:04 +10009228
Guido van Rossumc9641791998-08-04 15:26:23 +00009229#ifdef WIFEXITED
Larry Hastings2f936352014-08-05 14:04:04 +10009230/*[clinic input]
9231os.WIFEXITED -> bool
9232
9233 status: int
9234
9235Return True if the process returning status exited via the exit() system call.
9236[clinic start generated code]*/
9237
Larry Hastings2f936352014-08-05 14:04:04 +10009238static int
9239os_WIFEXITED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009240/*[clinic end generated code: output=ca8f8c61f0b8532e input=d63775a6791586c0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009241{
9242 WAIT_TYPE wait_status;
9243 WAIT_STATUS_INT(wait_status) = status;
9244 return WIFEXITED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009245}
9246#endif /* WIFEXITED */
9247
Larry Hastings2f936352014-08-05 14:04:04 +10009248
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00009249#ifdef WEXITSTATUS
Larry Hastings2f936352014-08-05 14:04:04 +10009250/*[clinic input]
9251os.WEXITSTATUS -> int
9252
9253 status: int
9254
9255Return the process return code from status.
9256[clinic start generated code]*/
9257
Larry Hastings2f936352014-08-05 14:04:04 +10009258static int
9259os_WEXITSTATUS_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009260/*[clinic end generated code: output=ea54da23d9e0f6af input=e1fb4944e377585b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009261{
9262 WAIT_TYPE wait_status;
9263 WAIT_STATUS_INT(wait_status) = status;
9264 return WEXITSTATUS(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009265}
9266#endif /* WEXITSTATUS */
9267
Larry Hastings2f936352014-08-05 14:04:04 +10009268
Guido van Rossumc9641791998-08-04 15:26:23 +00009269#ifdef WTERMSIG
Larry Hastings2f936352014-08-05 14:04:04 +10009270/*[clinic input]
9271os.WTERMSIG -> int
9272
9273 status: int
9274
9275Return the signal that terminated the process that provided the status value.
9276[clinic start generated code]*/
9277
Larry Hastings2f936352014-08-05 14:04:04 +10009278static int
9279os_WTERMSIG_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009280/*[clinic end generated code: output=4d25367026cb852c input=727fd7f84ec3f243]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009281{
9282 WAIT_TYPE wait_status;
9283 WAIT_STATUS_INT(wait_status) = status;
9284 return WTERMSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009285}
9286#endif /* WTERMSIG */
9287
Larry Hastings2f936352014-08-05 14:04:04 +10009288
Guido van Rossumc9641791998-08-04 15:26:23 +00009289#ifdef WSTOPSIG
Larry Hastings2f936352014-08-05 14:04:04 +10009290/*[clinic input]
9291os.WSTOPSIG -> int
9292
9293 status: int
9294
9295Return the signal that stopped the process that provided the status value.
9296[clinic start generated code]*/
9297
Larry Hastings2f936352014-08-05 14:04:04 +10009298static int
9299os_WSTOPSIG_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009300/*[clinic end generated code: output=54eb9c13b001adb4 input=46ebf1d1b293c5c1]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009301{
9302 WAIT_TYPE wait_status;
9303 WAIT_STATUS_INT(wait_status) = status;
9304 return WSTOPSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009305}
9306#endif /* WSTOPSIG */
Guido van Rossumc9641791998-08-04 15:26:23 +00009307#endif /* HAVE_SYS_WAIT_H */
9308
9309
Thomas Wouters477c8d52006-05-27 19:21:47 +00009310#if defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossumd5753e11999-10-19 13:29:23 +00009311#ifdef _SCO_DS
9312/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
9313 needed definitions in sys/statvfs.h */
9314#define _SVID3
9315#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00009316#include <sys/statvfs.h>
9317
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009318static PyObject*
9319_pystatvfs_fromstructstatvfs(struct statvfs st) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009320 PyObject *v = PyStructSequence_New(&StatVFSResultType);
9321 if (v == NULL)
9322 return NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009323
9324#if !defined(HAVE_LARGEFILE_SUPPORT)
Victor Stinner8c62be82010-05-06 00:08:46 +00009325 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
9326 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
9327 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long) st.f_blocks));
9328 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long) st.f_bfree));
9329 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong((long) st.f_bavail));
9330 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong((long) st.f_files));
9331 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong((long) st.f_ffree));
9332 PyStructSequence_SET_ITEM(v, 7, PyLong_FromLong((long) st.f_favail));
9333 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
9334 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009335#else
Victor Stinner8c62be82010-05-06 00:08:46 +00009336 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
9337 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
9338 PyStructSequence_SET_ITEM(v, 2,
9339 PyLong_FromLongLong((PY_LONG_LONG) st.f_blocks));
9340 PyStructSequence_SET_ITEM(v, 3,
9341 PyLong_FromLongLong((PY_LONG_LONG) st.f_bfree));
9342 PyStructSequence_SET_ITEM(v, 4,
9343 PyLong_FromLongLong((PY_LONG_LONG) st.f_bavail));
9344 PyStructSequence_SET_ITEM(v, 5,
9345 PyLong_FromLongLong((PY_LONG_LONG) st.f_files));
9346 PyStructSequence_SET_ITEM(v, 6,
9347 PyLong_FromLongLong((PY_LONG_LONG) st.f_ffree));
9348 PyStructSequence_SET_ITEM(v, 7,
9349 PyLong_FromLongLong((PY_LONG_LONG) st.f_favail));
9350 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
9351 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009352#endif
Victor Stinnerf0a7bac2013-10-30 18:55:24 +01009353 if (PyErr_Occurred()) {
9354 Py_DECREF(v);
9355 return NULL;
9356 }
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009357
Victor Stinner8c62be82010-05-06 00:08:46 +00009358 return v;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009359}
9360
Larry Hastings2f936352014-08-05 14:04:04 +10009361
9362/*[clinic input]
9363os.fstatvfs
9364 fd: int
9365 /
9366
9367Perform an fstatvfs system call on the given fd.
9368
9369Equivalent to statvfs(fd).
9370[clinic start generated code]*/
9371
Larry Hastings2f936352014-08-05 14:04:04 +10009372static PyObject *
9373os_fstatvfs_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009374/*[clinic end generated code: output=584a94a754497ac0 input=d8122243ac50975e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009375{
9376 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009377 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009378 struct statvfs st;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009379
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009380 do {
9381 Py_BEGIN_ALLOW_THREADS
9382 result = fstatvfs(fd, &st);
9383 Py_END_ALLOW_THREADS
9384 } while (result != 0 && errno == EINTR &&
9385 !(async_err = PyErr_CheckSignals()));
Larry Hastings2f936352014-08-05 14:04:04 +10009386 if (result != 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009387 return (!async_err) ? posix_error() : NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009388
Victor Stinner8c62be82010-05-06 00:08:46 +00009389 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +00009390}
Larry Hastings2f936352014-08-05 14:04:04 +10009391#endif /* defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H) */
Guido van Rossum94f6f721999-01-06 18:42:14 +00009392
9393
Thomas Wouters477c8d52006-05-27 19:21:47 +00009394#if defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossum94f6f721999-01-06 18:42:14 +00009395#include <sys/statvfs.h>
Larry Hastings2f936352014-08-05 14:04:04 +10009396/*[clinic input]
9397os.statvfs
Guido van Rossum94f6f721999-01-06 18:42:14 +00009398
Larry Hastings2f936352014-08-05 14:04:04 +10009399 path: path_t(allow_fd='PATH_HAVE_FSTATVFS')
9400
9401Perform a statvfs system call on the given path.
9402
9403path may always be specified as a string.
9404On some platforms, path may also be specified as an open file descriptor.
9405 If this functionality is unavailable, using it raises an exception.
9406[clinic start generated code]*/
9407
Larry Hastings2f936352014-08-05 14:04:04 +10009408static PyObject *
9409os_statvfs_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009410/*[clinic end generated code: output=5ced07a2cf931f41 input=3f5c35791c669bd9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009411{
9412 int result;
9413 struct statvfs st;
Larry Hastings9cf065c2012-06-22 16:30:09 -07009414
9415 Py_BEGIN_ALLOW_THREADS
9416#ifdef HAVE_FSTATVFS
Larry Hastings2f936352014-08-05 14:04:04 +10009417 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07009418#ifdef __APPLE__
9419 /* handle weak-linking on Mac OS X 10.3 */
9420 if (fstatvfs == NULL) {
Larry Hastings2f936352014-08-05 14:04:04 +10009421 fd_specified("statvfs", path->fd);
9422 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07009423 }
9424#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009425 result = fstatvfs(path->fd, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009426 }
9427 else
9428#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009429 result = statvfs(path->narrow, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009430 Py_END_ALLOW_THREADS
9431
9432 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10009433 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009434 }
9435
Larry Hastings2f936352014-08-05 14:04:04 +10009436 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +00009437}
Larry Hastings2f936352014-08-05 14:04:04 +10009438#endif /* defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H) */
9439
Guido van Rossum94f6f721999-01-06 18:42:14 +00009440
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009441#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10009442/*[clinic input]
9443os._getdiskusage
9444
9445 path: Py_UNICODE
9446
9447Return disk usage statistics about the given path as a (total, free) tuple.
9448[clinic start generated code]*/
9449
Larry Hastings2f936352014-08-05 14:04:04 +10009450static PyObject *
9451os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009452/*[clinic end generated code: output=60a9cf33449db1dd input=6458133aed893c78]*/
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009453{
9454 BOOL retval;
9455 ULARGE_INTEGER _, total, free;
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009456
9457 Py_BEGIN_ALLOW_THREADS
Victor Stinner6139c1b2011-11-09 22:14:14 +01009458 retval = GetDiskFreeSpaceExW(path, &_, &total, &free);
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009459 Py_END_ALLOW_THREADS
9460 if (retval == 0)
9461 return PyErr_SetFromWindowsErr(0);
9462
9463 return Py_BuildValue("(LL)", total.QuadPart, free.QuadPart);
9464}
Larry Hastings2f936352014-08-05 14:04:04 +10009465#endif /* MS_WINDOWS */
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009466
9467
Fred Drakec9680921999-12-13 16:37:25 +00009468/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
9469 * It maps strings representing configuration variable names to
9470 * integer values, allowing those functions to be called with the
Thomas Wouters7e474022000-07-16 12:04:32 +00009471 * magic names instead of polluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +00009472 * rarely-used constants. There are three separate tables that use
9473 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +00009474 *
9475 * This code is always included, even if none of the interfaces that
9476 * need it are included. The #if hackery needed to avoid it would be
9477 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +00009478 */
9479struct constdef {
9480 char *name;
9481 long value;
9482};
9483
Fred Drake12c6e2d1999-12-14 21:25:03 +00009484static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009485conv_confname(PyObject *arg, int *valuep, struct constdef *table,
Guido van Rossum7d5baac2007-08-27 23:24:46 +00009486 size_t tablesize)
Fred Drake12c6e2d1999-12-14 21:25:03 +00009487{
Christian Heimes217cfd12007-12-02 14:31:20 +00009488 if (PyLong_Check(arg)) {
Stefan Krah0e803b32010-11-26 16:16:47 +00009489 *valuep = PyLong_AS_LONG(arg);
9490 return 1;
Fred Drake12c6e2d1999-12-14 21:25:03 +00009491 }
Guido van Rossumbce56a62007-05-10 18:04:33 +00009492 else {
Stefan Krah0e803b32010-11-26 16:16:47 +00009493 /* look up the value in the table using a binary search */
9494 size_t lo = 0;
9495 size_t mid;
9496 size_t hi = tablesize;
9497 int cmp;
9498 const char *confname;
9499 if (!PyUnicode_Check(arg)) {
9500 PyErr_SetString(PyExc_TypeError,
9501 "configuration names must be strings or integers");
9502 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009503 }
Stefan Krah0e803b32010-11-26 16:16:47 +00009504 confname = _PyUnicode_AsString(arg);
9505 if (confname == NULL)
9506 return 0;
9507 while (lo < hi) {
9508 mid = (lo + hi) / 2;
9509 cmp = strcmp(confname, table[mid].name);
9510 if (cmp < 0)
9511 hi = mid;
9512 else if (cmp > 0)
9513 lo = mid + 1;
9514 else {
9515 *valuep = table[mid].value;
9516 return 1;
9517 }
9518 }
9519 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
9520 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009521 }
Fred Drake12c6e2d1999-12-14 21:25:03 +00009522}
9523
9524
9525#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
9526static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +00009527#ifdef _PC_ABI_AIO_XFER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009528 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
Fred Draked86ed291999-12-15 15:34:33 +00009529#endif
9530#ifdef _PC_ABI_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009531 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
Fred Draked86ed291999-12-15 15:34:33 +00009532#endif
Fred Drakec9680921999-12-13 16:37:25 +00009533#ifdef _PC_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009534 {"PC_ASYNC_IO", _PC_ASYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009535#endif
9536#ifdef _PC_CHOWN_RESTRICTED
Victor Stinner8c62be82010-05-06 00:08:46 +00009537 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
Fred Drakec9680921999-12-13 16:37:25 +00009538#endif
9539#ifdef _PC_FILESIZEBITS
Victor Stinner8c62be82010-05-06 00:08:46 +00009540 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
Fred Drakec9680921999-12-13 16:37:25 +00009541#endif
9542#ifdef _PC_LAST
Victor Stinner8c62be82010-05-06 00:08:46 +00009543 {"PC_LAST", _PC_LAST},
Fred Drakec9680921999-12-13 16:37:25 +00009544#endif
9545#ifdef _PC_LINK_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009546 {"PC_LINK_MAX", _PC_LINK_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009547#endif
9548#ifdef _PC_MAX_CANON
Victor Stinner8c62be82010-05-06 00:08:46 +00009549 {"PC_MAX_CANON", _PC_MAX_CANON},
Fred Drakec9680921999-12-13 16:37:25 +00009550#endif
9551#ifdef _PC_MAX_INPUT
Victor Stinner8c62be82010-05-06 00:08:46 +00009552 {"PC_MAX_INPUT", _PC_MAX_INPUT},
Fred Drakec9680921999-12-13 16:37:25 +00009553#endif
9554#ifdef _PC_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009555 {"PC_NAME_MAX", _PC_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009556#endif
9557#ifdef _PC_NO_TRUNC
Victor Stinner8c62be82010-05-06 00:08:46 +00009558 {"PC_NO_TRUNC", _PC_NO_TRUNC},
Fred Drakec9680921999-12-13 16:37:25 +00009559#endif
9560#ifdef _PC_PATH_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009561 {"PC_PATH_MAX", _PC_PATH_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009562#endif
9563#ifdef _PC_PIPE_BUF
Victor Stinner8c62be82010-05-06 00:08:46 +00009564 {"PC_PIPE_BUF", _PC_PIPE_BUF},
Fred Drakec9680921999-12-13 16:37:25 +00009565#endif
9566#ifdef _PC_PRIO_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009567 {"PC_PRIO_IO", _PC_PRIO_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009568#endif
9569#ifdef _PC_SOCK_MAXBUF
Victor Stinner8c62be82010-05-06 00:08:46 +00009570 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
Fred Drakec9680921999-12-13 16:37:25 +00009571#endif
9572#ifdef _PC_SYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009573 {"PC_SYNC_IO", _PC_SYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009574#endif
9575#ifdef _PC_VDISABLE
Victor Stinner8c62be82010-05-06 00:08:46 +00009576 {"PC_VDISABLE", _PC_VDISABLE},
Fred Drakec9680921999-12-13 16:37:25 +00009577#endif
Jesus Cea7e9065c2010-10-25 13:02:04 +00009578#ifdef _PC_ACL_ENABLED
9579 {"PC_ACL_ENABLED", _PC_ACL_ENABLED},
9580#endif
9581#ifdef _PC_MIN_HOLE_SIZE
9582 {"PC_MIN_HOLE_SIZE", _PC_MIN_HOLE_SIZE},
9583#endif
9584#ifdef _PC_ALLOC_SIZE_MIN
9585 {"PC_ALLOC_SIZE_MIN", _PC_ALLOC_SIZE_MIN},
9586#endif
9587#ifdef _PC_REC_INCR_XFER_SIZE
9588 {"PC_REC_INCR_XFER_SIZE", _PC_REC_INCR_XFER_SIZE},
9589#endif
9590#ifdef _PC_REC_MAX_XFER_SIZE
9591 {"PC_REC_MAX_XFER_SIZE", _PC_REC_MAX_XFER_SIZE},
9592#endif
9593#ifdef _PC_REC_MIN_XFER_SIZE
9594 {"PC_REC_MIN_XFER_SIZE", _PC_REC_MIN_XFER_SIZE},
9595#endif
9596#ifdef _PC_REC_XFER_ALIGN
9597 {"PC_REC_XFER_ALIGN", _PC_REC_XFER_ALIGN},
9598#endif
9599#ifdef _PC_SYMLINK_MAX
9600 {"PC_SYMLINK_MAX", _PC_SYMLINK_MAX},
9601#endif
9602#ifdef _PC_XATTR_ENABLED
9603 {"PC_XATTR_ENABLED", _PC_XATTR_ENABLED},
9604#endif
9605#ifdef _PC_XATTR_EXISTS
9606 {"PC_XATTR_EXISTS", _PC_XATTR_EXISTS},
9607#endif
9608#ifdef _PC_TIMESTAMP_RESOLUTION
9609 {"PC_TIMESTAMP_RESOLUTION", _PC_TIMESTAMP_RESOLUTION},
9610#endif
Fred Drakec9680921999-12-13 16:37:25 +00009611};
9612
Fred Drakec9680921999-12-13 16:37:25 +00009613static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009614conv_path_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +00009615{
9616 return conv_confname(arg, valuep, posix_constants_pathconf,
9617 sizeof(posix_constants_pathconf)
9618 / sizeof(struct constdef));
9619}
9620#endif
9621
Larry Hastings2f936352014-08-05 14:04:04 +10009622
Fred Drakec9680921999-12-13 16:37:25 +00009623#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009624/*[clinic input]
9625os.fpathconf -> long
9626
9627 fd: int
9628 name: path_confname
9629 /
9630
9631Return the configuration limit name for the file descriptor fd.
9632
9633If there is no limit, return -1.
9634[clinic start generated code]*/
9635
Larry Hastings2f936352014-08-05 14:04:04 +10009636static long
9637os_fpathconf_impl(PyModuleDef *module, int fd, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009638/*[clinic end generated code: output=082b2922d4441de7 input=5942a024d3777810]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009639{
9640 long limit;
9641
9642 errno = 0;
9643 limit = fpathconf(fd, name);
9644 if (limit == -1 && errno != 0)
9645 posix_error();
9646
9647 return limit;
9648}
9649#endif /* HAVE_FPATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +00009650
9651
9652#ifdef HAVE_PATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009653/*[clinic input]
9654os.pathconf -> long
9655 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
9656 name: path_confname
9657
9658Return the configuration limit name for the file or directory path.
9659
9660If there is no limit, return -1.
9661On some platforms, path may also be specified as an open file descriptor.
9662 If this functionality is unavailable, using it raises an exception.
9663[clinic start generated code]*/
9664
Larry Hastings2f936352014-08-05 14:04:04 +10009665static long
9666os_pathconf_impl(PyModuleDef *module, path_t *path, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009667/*[clinic end generated code: output=3713029e9501f5ab input=bc3e2a985af27e5e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009668{
Victor Stinner8c62be82010-05-06 00:08:46 +00009669 long limit;
Fred Drakec9680921999-12-13 16:37:25 +00009670
Victor Stinner8c62be82010-05-06 00:08:46 +00009671 errno = 0;
Georg Brandl306336b2012-06-24 12:55:33 +02009672#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009673 if (path->fd != -1)
9674 limit = fpathconf(path->fd, name);
Georg Brandl306336b2012-06-24 12:55:33 +02009675 else
9676#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009677 limit = pathconf(path->narrow, name);
Victor Stinner8c62be82010-05-06 00:08:46 +00009678 if (limit == -1 && errno != 0) {
9679 if (errno == EINVAL)
Stefan Krah99439262010-11-26 12:58:05 +00009680 /* could be a path or name problem */
9681 posix_error();
Fred Drakec9680921999-12-13 16:37:25 +00009682 else
Larry Hastings2f936352014-08-05 14:04:04 +10009683 path_error(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00009684 }
Larry Hastings2f936352014-08-05 14:04:04 +10009685
9686 return limit;
Fred Drakec9680921999-12-13 16:37:25 +00009687}
Larry Hastings2f936352014-08-05 14:04:04 +10009688#endif /* HAVE_PATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +00009689
9690#ifdef HAVE_CONFSTR
9691static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +00009692#ifdef _CS_ARCHITECTURE
Victor Stinner8c62be82010-05-06 00:08:46 +00009693 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
Fred Draked86ed291999-12-15 15:34:33 +00009694#endif
Mark Dickinson876d7c82010-04-16 12:47:52 +00009695#ifdef _CS_GNU_LIBC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009696 {"CS_GNU_LIBC_VERSION", _CS_GNU_LIBC_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +00009697#endif
9698#ifdef _CS_GNU_LIBPTHREAD_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009699 {"CS_GNU_LIBPTHREAD_VERSION", _CS_GNU_LIBPTHREAD_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +00009700#endif
Fred Draked86ed291999-12-15 15:34:33 +00009701#ifdef _CS_HOSTNAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009702 {"CS_HOSTNAME", _CS_HOSTNAME},
Fred Draked86ed291999-12-15 15:34:33 +00009703#endif
9704#ifdef _CS_HW_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +00009705 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +00009706#endif
9707#ifdef _CS_HW_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +00009708 {"CS_HW_SERIAL", _CS_HW_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +00009709#endif
9710#ifdef _CS_INITTAB_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009711 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009712#endif
Fred Drakec9680921999-12-13 16:37:25 +00009713#ifdef _CS_LFS64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009714 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009715#endif
9716#ifdef _CS_LFS64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009717 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009718#endif
9719#ifdef _CS_LFS64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009720 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009721#endif
9722#ifdef _CS_LFS64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009723 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009724#endif
9725#ifdef _CS_LFS_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009726 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009727#endif
9728#ifdef _CS_LFS_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009729 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009730#endif
9731#ifdef _CS_LFS_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009732 {"CS_LFS_LIBS", _CS_LFS_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009733#endif
9734#ifdef _CS_LFS_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009735 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009736#endif
Fred Draked86ed291999-12-15 15:34:33 +00009737#ifdef _CS_MACHINE
Victor Stinner8c62be82010-05-06 00:08:46 +00009738 {"CS_MACHINE", _CS_MACHINE},
Fred Draked86ed291999-12-15 15:34:33 +00009739#endif
Fred Drakec9680921999-12-13 16:37:25 +00009740#ifdef _CS_PATH
Victor Stinner8c62be82010-05-06 00:08:46 +00009741 {"CS_PATH", _CS_PATH},
Fred Drakec9680921999-12-13 16:37:25 +00009742#endif
Fred Draked86ed291999-12-15 15:34:33 +00009743#ifdef _CS_RELEASE
Victor Stinner8c62be82010-05-06 00:08:46 +00009744 {"CS_RELEASE", _CS_RELEASE},
Fred Draked86ed291999-12-15 15:34:33 +00009745#endif
9746#ifdef _CS_SRPC_DOMAIN
Victor Stinner8c62be82010-05-06 00:08:46 +00009747 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
Fred Draked86ed291999-12-15 15:34:33 +00009748#endif
9749#ifdef _CS_SYSNAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009750 {"CS_SYSNAME", _CS_SYSNAME},
Fred Draked86ed291999-12-15 15:34:33 +00009751#endif
9752#ifdef _CS_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009753 {"CS_VERSION", _CS_VERSION},
Fred Draked86ed291999-12-15 15:34:33 +00009754#endif
Fred Drakec9680921999-12-13 16:37:25 +00009755#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009756 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009757#endif
9758#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009759 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009760#endif
9761#ifdef _CS_XBS5_ILP32_OFF32_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009762 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009763#endif
9764#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009765 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009766#endif
9767#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009768 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009769#endif
9770#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009771 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009772#endif
9773#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009774 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009775#endif
9776#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009777 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009778#endif
9779#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009780 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009781#endif
9782#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009783 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009784#endif
9785#ifdef _CS_XBS5_LP64_OFF64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009786 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009787#endif
9788#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009789 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009790#endif
9791#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009792 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009793#endif
9794#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009795 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009796#endif
9797#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009798 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009799#endif
9800#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009801 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009802#endif
Fred Draked86ed291999-12-15 15:34:33 +00009803#ifdef _MIPS_CS_AVAIL_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009804 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009805#endif
9806#ifdef _MIPS_CS_BASE
Victor Stinner8c62be82010-05-06 00:08:46 +00009807 {"MIPS_CS_BASE", _MIPS_CS_BASE},
Fred Draked86ed291999-12-15 15:34:33 +00009808#endif
9809#ifdef _MIPS_CS_HOSTID
Victor Stinner8c62be82010-05-06 00:08:46 +00009810 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
Fred Draked86ed291999-12-15 15:34:33 +00009811#endif
9812#ifdef _MIPS_CS_HW_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009813 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009814#endif
9815#ifdef _MIPS_CS_NUM_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009816 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009817#endif
9818#ifdef _MIPS_CS_OSREL_MAJ
Victor Stinner8c62be82010-05-06 00:08:46 +00009819 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
Fred Draked86ed291999-12-15 15:34:33 +00009820#endif
9821#ifdef _MIPS_CS_OSREL_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +00009822 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
Fred Draked86ed291999-12-15 15:34:33 +00009823#endif
9824#ifdef _MIPS_CS_OSREL_PATCH
Victor Stinner8c62be82010-05-06 00:08:46 +00009825 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
Fred Draked86ed291999-12-15 15:34:33 +00009826#endif
9827#ifdef _MIPS_CS_OS_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009828 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009829#endif
9830#ifdef _MIPS_CS_OS_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +00009831 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +00009832#endif
9833#ifdef _MIPS_CS_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009834 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009835#endif
9836#ifdef _MIPS_CS_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +00009837 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +00009838#endif
9839#ifdef _MIPS_CS_VENDOR
Victor Stinner8c62be82010-05-06 00:08:46 +00009840 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
Fred Draked86ed291999-12-15 15:34:33 +00009841#endif
Fred Drakec9680921999-12-13 16:37:25 +00009842};
9843
9844static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009845conv_confstr_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +00009846{
9847 return conv_confname(arg, valuep, posix_constants_confstr,
9848 sizeof(posix_constants_confstr)
9849 / sizeof(struct constdef));
9850}
9851
Larry Hastings2f936352014-08-05 14:04:04 +10009852
9853/*[clinic input]
9854os.confstr
9855
9856 name: confstr_confname
9857 /
9858
9859Return a string-valued system configuration variable.
9860[clinic start generated code]*/
9861
Larry Hastings2f936352014-08-05 14:04:04 +10009862static PyObject *
9863os_confstr_impl(PyModuleDef *module, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009864/*[clinic end generated code: output=6ff79c9eed8c2daf input=18fb4d0567242e65]*/
Fred Drakec9680921999-12-13 16:37:25 +00009865{
9866 PyObject *result = NULL;
Victor Stinnercb043522010-09-10 23:49:04 +00009867 char buffer[255];
Victor Stinnerdd3a6a52013-06-25 23:13:47 +02009868 size_t len;
Fred Drakec9680921999-12-13 16:37:25 +00009869
Victor Stinnercb043522010-09-10 23:49:04 +00009870 errno = 0;
9871 len = confstr(name, buffer, sizeof(buffer));
9872 if (len == 0) {
9873 if (errno) {
9874 posix_error();
9875 return NULL;
Fred Drakec9680921999-12-13 16:37:25 +00009876 }
9877 else {
Victor Stinnercb043522010-09-10 23:49:04 +00009878 Py_RETURN_NONE;
Fred Drakec9680921999-12-13 16:37:25 +00009879 }
9880 }
Victor Stinnercb043522010-09-10 23:49:04 +00009881
Victor Stinnerdd3a6a52013-06-25 23:13:47 +02009882 if (len >= sizeof(buffer)) {
Victor Stinnercbc18f32014-12-05 22:51:51 +01009883 size_t len2;
Victor Stinnercb043522010-09-10 23:49:04 +00009884 char *buf = PyMem_Malloc(len);
9885 if (buf == NULL)
9886 return PyErr_NoMemory();
Victor Stinnercbc18f32014-12-05 22:51:51 +01009887 len2 = confstr(name, buf, len);
9888 assert(len == len2);
Victor Stinnercb043522010-09-10 23:49:04 +00009889 result = PyUnicode_DecodeFSDefaultAndSize(buf, len-1);
9890 PyMem_Free(buf);
9891 }
9892 else
9893 result = PyUnicode_DecodeFSDefaultAndSize(buffer, len-1);
Fred Drakec9680921999-12-13 16:37:25 +00009894 return result;
9895}
Larry Hastings2f936352014-08-05 14:04:04 +10009896#endif /* HAVE_CONFSTR */
Fred Drakec9680921999-12-13 16:37:25 +00009897
9898
9899#ifdef HAVE_SYSCONF
9900static struct constdef posix_constants_sysconf[] = {
9901#ifdef _SC_2_CHAR_TERM
Victor Stinner8c62be82010-05-06 00:08:46 +00009902 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
Fred Drakec9680921999-12-13 16:37:25 +00009903#endif
9904#ifdef _SC_2_C_BIND
Victor Stinner8c62be82010-05-06 00:08:46 +00009905 {"SC_2_C_BIND", _SC_2_C_BIND},
Fred Drakec9680921999-12-13 16:37:25 +00009906#endif
9907#ifdef _SC_2_C_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009908 {"SC_2_C_DEV", _SC_2_C_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009909#endif
9910#ifdef _SC_2_C_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009911 {"SC_2_C_VERSION", _SC_2_C_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +00009912#endif
9913#ifdef _SC_2_FORT_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009914 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009915#endif
9916#ifdef _SC_2_FORT_RUN
Victor Stinner8c62be82010-05-06 00:08:46 +00009917 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
Fred Drakec9680921999-12-13 16:37:25 +00009918#endif
9919#ifdef _SC_2_LOCALEDEF
Victor Stinner8c62be82010-05-06 00:08:46 +00009920 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
Fred Drakec9680921999-12-13 16:37:25 +00009921#endif
9922#ifdef _SC_2_SW_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009923 {"SC_2_SW_DEV", _SC_2_SW_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009924#endif
9925#ifdef _SC_2_UPE
Victor Stinner8c62be82010-05-06 00:08:46 +00009926 {"SC_2_UPE", _SC_2_UPE},
Fred Drakec9680921999-12-13 16:37:25 +00009927#endif
9928#ifdef _SC_2_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009929 {"SC_2_VERSION", _SC_2_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +00009930#endif
Fred Draked86ed291999-12-15 15:34:33 +00009931#ifdef _SC_ABI_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009932 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
Fred Draked86ed291999-12-15 15:34:33 +00009933#endif
9934#ifdef _SC_ACL
Victor Stinner8c62be82010-05-06 00:08:46 +00009935 {"SC_ACL", _SC_ACL},
Fred Draked86ed291999-12-15 15:34:33 +00009936#endif
Fred Drakec9680921999-12-13 16:37:25 +00009937#ifdef _SC_AIO_LISTIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009938 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009939#endif
Fred Drakec9680921999-12-13 16:37:25 +00009940#ifdef _SC_AIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009941 {"SC_AIO_MAX", _SC_AIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009942#endif
9943#ifdef _SC_AIO_PRIO_DELTA_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009944 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009945#endif
9946#ifdef _SC_ARG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009947 {"SC_ARG_MAX", _SC_ARG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009948#endif
9949#ifdef _SC_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009950 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009951#endif
9952#ifdef _SC_ATEXIT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009953 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009954#endif
Fred Draked86ed291999-12-15 15:34:33 +00009955#ifdef _SC_AUDIT
Victor Stinner8c62be82010-05-06 00:08:46 +00009956 {"SC_AUDIT", _SC_AUDIT},
Fred Draked86ed291999-12-15 15:34:33 +00009957#endif
Fred Drakec9680921999-12-13 16:37:25 +00009958#ifdef _SC_AVPHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +00009959 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +00009960#endif
9961#ifdef _SC_BC_BASE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009962 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009963#endif
9964#ifdef _SC_BC_DIM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009965 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009966#endif
9967#ifdef _SC_BC_SCALE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009968 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009969#endif
9970#ifdef _SC_BC_STRING_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009971 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009972#endif
Fred Draked86ed291999-12-15 15:34:33 +00009973#ifdef _SC_CAP
Victor Stinner8c62be82010-05-06 00:08:46 +00009974 {"SC_CAP", _SC_CAP},
Fred Draked86ed291999-12-15 15:34:33 +00009975#endif
Fred Drakec9680921999-12-13 16:37:25 +00009976#ifdef _SC_CHARCLASS_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009977 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009978#endif
9979#ifdef _SC_CHAR_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +00009980 {"SC_CHAR_BIT", _SC_CHAR_BIT},
Fred Drakec9680921999-12-13 16:37:25 +00009981#endif
9982#ifdef _SC_CHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009983 {"SC_CHAR_MAX", _SC_CHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009984#endif
9985#ifdef _SC_CHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +00009986 {"SC_CHAR_MIN", _SC_CHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +00009987#endif
9988#ifdef _SC_CHILD_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009989 {"SC_CHILD_MAX", _SC_CHILD_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009990#endif
9991#ifdef _SC_CLK_TCK
Victor Stinner8c62be82010-05-06 00:08:46 +00009992 {"SC_CLK_TCK", _SC_CLK_TCK},
Fred Drakec9680921999-12-13 16:37:25 +00009993#endif
9994#ifdef _SC_COHER_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +00009995 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +00009996#endif
9997#ifdef _SC_COLL_WEIGHTS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009998 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009999#endif
10000#ifdef _SC_DCACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000010001 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000010002#endif
10003#ifdef _SC_DCACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010004 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010005#endif
10006#ifdef _SC_DCACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010007 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000010008#endif
10009#ifdef _SC_DCACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010010 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000010011#endif
10012#ifdef _SC_DCACHE_TBLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010013 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010014#endif
10015#ifdef _SC_DELAYTIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010016 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010017#endif
10018#ifdef _SC_EQUIV_CLASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010019 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010020#endif
10021#ifdef _SC_EXPR_NEST_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010022 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010023#endif
10024#ifdef _SC_FSYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000010025 {"SC_FSYNC", _SC_FSYNC},
Fred Drakec9680921999-12-13 16:37:25 +000010026#endif
10027#ifdef _SC_GETGR_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010028 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010029#endif
10030#ifdef _SC_GETPW_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010031 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010032#endif
10033#ifdef _SC_ICACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000010034 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000010035#endif
10036#ifdef _SC_ICACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010037 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010038#endif
10039#ifdef _SC_ICACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010040 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000010041#endif
10042#ifdef _SC_ICACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010043 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000010044#endif
Fred Draked86ed291999-12-15 15:34:33 +000010045#ifdef _SC_INF
Victor Stinner8c62be82010-05-06 00:08:46 +000010046 {"SC_INF", _SC_INF},
Fred Draked86ed291999-12-15 15:34:33 +000010047#endif
Fred Drakec9680921999-12-13 16:37:25 +000010048#ifdef _SC_INT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010049 {"SC_INT_MAX", _SC_INT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010050#endif
10051#ifdef _SC_INT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010052 {"SC_INT_MIN", _SC_INT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010053#endif
10054#ifdef _SC_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010055 {"SC_IOV_MAX", _SC_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010056#endif
Fred Draked86ed291999-12-15 15:34:33 +000010057#ifdef _SC_IP_SECOPTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010058 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
Fred Draked86ed291999-12-15 15:34:33 +000010059#endif
Fred Drakec9680921999-12-13 16:37:25 +000010060#ifdef _SC_JOB_CONTROL
Victor Stinner8c62be82010-05-06 00:08:46 +000010061 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
Fred Drakec9680921999-12-13 16:37:25 +000010062#endif
Fred Draked86ed291999-12-15 15:34:33 +000010063#ifdef _SC_KERN_POINTERS
Victor Stinner8c62be82010-05-06 00:08:46 +000010064 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
Fred Draked86ed291999-12-15 15:34:33 +000010065#endif
10066#ifdef _SC_KERN_SIM
Victor Stinner8c62be82010-05-06 00:08:46 +000010067 {"SC_KERN_SIM", _SC_KERN_SIM},
Fred Draked86ed291999-12-15 15:34:33 +000010068#endif
Fred Drakec9680921999-12-13 16:37:25 +000010069#ifdef _SC_LINE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010070 {"SC_LINE_MAX", _SC_LINE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010071#endif
10072#ifdef _SC_LOGIN_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010073 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010074#endif
10075#ifdef _SC_LOGNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010076 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010077#endif
10078#ifdef _SC_LONG_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010079 {"SC_LONG_BIT", _SC_LONG_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000010080#endif
Fred Draked86ed291999-12-15 15:34:33 +000010081#ifdef _SC_MAC
Victor Stinner8c62be82010-05-06 00:08:46 +000010082 {"SC_MAC", _SC_MAC},
Fred Draked86ed291999-12-15 15:34:33 +000010083#endif
Fred Drakec9680921999-12-13 16:37:25 +000010084#ifdef _SC_MAPPED_FILES
Victor Stinner8c62be82010-05-06 00:08:46 +000010085 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
Fred Drakec9680921999-12-13 16:37:25 +000010086#endif
10087#ifdef _SC_MAXPID
Victor Stinner8c62be82010-05-06 00:08:46 +000010088 {"SC_MAXPID", _SC_MAXPID},
Fred Drakec9680921999-12-13 16:37:25 +000010089#endif
10090#ifdef _SC_MB_LEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010091 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010092#endif
10093#ifdef _SC_MEMLOCK
Victor Stinner8c62be82010-05-06 00:08:46 +000010094 {"SC_MEMLOCK", _SC_MEMLOCK},
Fred Drakec9680921999-12-13 16:37:25 +000010095#endif
10096#ifdef _SC_MEMLOCK_RANGE
Victor Stinner8c62be82010-05-06 00:08:46 +000010097 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
Fred Drakec9680921999-12-13 16:37:25 +000010098#endif
10099#ifdef _SC_MEMORY_PROTECTION
Victor Stinner8c62be82010-05-06 00:08:46 +000010100 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
Fred Drakec9680921999-12-13 16:37:25 +000010101#endif
10102#ifdef _SC_MESSAGE_PASSING
Victor Stinner8c62be82010-05-06 00:08:46 +000010103 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
Fred Drakec9680921999-12-13 16:37:25 +000010104#endif
Fred Draked86ed291999-12-15 15:34:33 +000010105#ifdef _SC_MMAP_FIXED_ALIGNMENT
Victor Stinner8c62be82010-05-06 00:08:46 +000010106 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
Fred Draked86ed291999-12-15 15:34:33 +000010107#endif
Fred Drakec9680921999-12-13 16:37:25 +000010108#ifdef _SC_MQ_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010109 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010110#endif
10111#ifdef _SC_MQ_PRIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010112 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010113#endif
Fred Draked86ed291999-12-15 15:34:33 +000010114#ifdef _SC_NACLS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010115 {"SC_NACLS_MAX", _SC_NACLS_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000010116#endif
Fred Drakec9680921999-12-13 16:37:25 +000010117#ifdef _SC_NGROUPS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010118 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010119#endif
10120#ifdef _SC_NL_ARGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010121 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010122#endif
10123#ifdef _SC_NL_LANGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010124 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010125#endif
10126#ifdef _SC_NL_MSGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010127 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010128#endif
10129#ifdef _SC_NL_NMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010130 {"SC_NL_NMAX", _SC_NL_NMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010131#endif
10132#ifdef _SC_NL_SETMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010133 {"SC_NL_SETMAX", _SC_NL_SETMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010134#endif
10135#ifdef _SC_NL_TEXTMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010136 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010137#endif
10138#ifdef _SC_NPROCESSORS_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000010139 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
Fred Drakec9680921999-12-13 16:37:25 +000010140#endif
10141#ifdef _SC_NPROCESSORS_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000010142 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
Fred Drakec9680921999-12-13 16:37:25 +000010143#endif
Fred Draked86ed291999-12-15 15:34:33 +000010144#ifdef _SC_NPROC_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000010145 {"SC_NPROC_CONF", _SC_NPROC_CONF},
Fred Draked86ed291999-12-15 15:34:33 +000010146#endif
10147#ifdef _SC_NPROC_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000010148 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
Fred Draked86ed291999-12-15 15:34:33 +000010149#endif
Fred Drakec9680921999-12-13 16:37:25 +000010150#ifdef _SC_NZERO
Victor Stinner8c62be82010-05-06 00:08:46 +000010151 {"SC_NZERO", _SC_NZERO},
Fred Drakec9680921999-12-13 16:37:25 +000010152#endif
10153#ifdef _SC_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010154 {"SC_OPEN_MAX", _SC_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010155#endif
10156#ifdef _SC_PAGESIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010157 {"SC_PAGESIZE", _SC_PAGESIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010158#endif
10159#ifdef _SC_PAGE_SIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010160 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010161#endif
10162#ifdef _SC_PASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010163 {"SC_PASS_MAX", _SC_PASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010164#endif
10165#ifdef _SC_PHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000010166 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000010167#endif
10168#ifdef _SC_PII
Victor Stinner8c62be82010-05-06 00:08:46 +000010169 {"SC_PII", _SC_PII},
Fred Drakec9680921999-12-13 16:37:25 +000010170#endif
10171#ifdef _SC_PII_INTERNET
Victor Stinner8c62be82010-05-06 00:08:46 +000010172 {"SC_PII_INTERNET", _SC_PII_INTERNET},
Fred Drakec9680921999-12-13 16:37:25 +000010173#endif
10174#ifdef _SC_PII_INTERNET_DGRAM
Victor Stinner8c62be82010-05-06 00:08:46 +000010175 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
Fred Drakec9680921999-12-13 16:37:25 +000010176#endif
10177#ifdef _SC_PII_INTERNET_STREAM
Victor Stinner8c62be82010-05-06 00:08:46 +000010178 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
Fred Drakec9680921999-12-13 16:37:25 +000010179#endif
10180#ifdef _SC_PII_OSI
Victor Stinner8c62be82010-05-06 00:08:46 +000010181 {"SC_PII_OSI", _SC_PII_OSI},
Fred Drakec9680921999-12-13 16:37:25 +000010182#endif
10183#ifdef _SC_PII_OSI_CLTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010184 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
Fred Drakec9680921999-12-13 16:37:25 +000010185#endif
10186#ifdef _SC_PII_OSI_COTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010187 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
Fred Drakec9680921999-12-13 16:37:25 +000010188#endif
10189#ifdef _SC_PII_OSI_M
Victor Stinner8c62be82010-05-06 00:08:46 +000010190 {"SC_PII_OSI_M", _SC_PII_OSI_M},
Fred Drakec9680921999-12-13 16:37:25 +000010191#endif
10192#ifdef _SC_PII_SOCKET
Victor Stinner8c62be82010-05-06 00:08:46 +000010193 {"SC_PII_SOCKET", _SC_PII_SOCKET},
Fred Drakec9680921999-12-13 16:37:25 +000010194#endif
10195#ifdef _SC_PII_XTI
Victor Stinner8c62be82010-05-06 00:08:46 +000010196 {"SC_PII_XTI", _SC_PII_XTI},
Fred Drakec9680921999-12-13 16:37:25 +000010197#endif
10198#ifdef _SC_POLL
Victor Stinner8c62be82010-05-06 00:08:46 +000010199 {"SC_POLL", _SC_POLL},
Fred Drakec9680921999-12-13 16:37:25 +000010200#endif
10201#ifdef _SC_PRIORITIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000010202 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000010203#endif
10204#ifdef _SC_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000010205 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000010206#endif
10207#ifdef _SC_REALTIME_SIGNALS
Victor Stinner8c62be82010-05-06 00:08:46 +000010208 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
Fred Drakec9680921999-12-13 16:37:25 +000010209#endif
10210#ifdef _SC_RE_DUP_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010211 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010212#endif
10213#ifdef _SC_RTSIG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010214 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010215#endif
10216#ifdef _SC_SAVED_IDS
Victor Stinner8c62be82010-05-06 00:08:46 +000010217 {"SC_SAVED_IDS", _SC_SAVED_IDS},
Fred Drakec9680921999-12-13 16:37:25 +000010218#endif
10219#ifdef _SC_SCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010220 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010221#endif
10222#ifdef _SC_SCHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010223 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010224#endif
10225#ifdef _SC_SELECT
Victor Stinner8c62be82010-05-06 00:08:46 +000010226 {"SC_SELECT", _SC_SELECT},
Fred Drakec9680921999-12-13 16:37:25 +000010227#endif
10228#ifdef _SC_SEMAPHORES
Victor Stinner8c62be82010-05-06 00:08:46 +000010229 {"SC_SEMAPHORES", _SC_SEMAPHORES},
Fred Drakec9680921999-12-13 16:37:25 +000010230#endif
10231#ifdef _SC_SEM_NSEMS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010232 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010233#endif
10234#ifdef _SC_SEM_VALUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010235 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010236#endif
10237#ifdef _SC_SHARED_MEMORY_OBJECTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010238 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
Fred Drakec9680921999-12-13 16:37:25 +000010239#endif
10240#ifdef _SC_SHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010241 {"SC_SHRT_MAX", _SC_SHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010242#endif
10243#ifdef _SC_SHRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010244 {"SC_SHRT_MIN", _SC_SHRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010245#endif
10246#ifdef _SC_SIGQUEUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010247 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010248#endif
10249#ifdef _SC_SIGRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010250 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010251#endif
10252#ifdef _SC_SIGRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010253 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010254#endif
Fred Draked86ed291999-12-15 15:34:33 +000010255#ifdef _SC_SOFTPOWER
Victor Stinner8c62be82010-05-06 00:08:46 +000010256 {"SC_SOFTPOWER", _SC_SOFTPOWER},
Fred Draked86ed291999-12-15 15:34:33 +000010257#endif
Fred Drakec9680921999-12-13 16:37:25 +000010258#ifdef _SC_SPLIT_CACHE
Victor Stinner8c62be82010-05-06 00:08:46 +000010259 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
Fred Drakec9680921999-12-13 16:37:25 +000010260#endif
10261#ifdef _SC_SSIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010262 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010263#endif
10264#ifdef _SC_STACK_PROT
Victor Stinner8c62be82010-05-06 00:08:46 +000010265 {"SC_STACK_PROT", _SC_STACK_PROT},
Fred Drakec9680921999-12-13 16:37:25 +000010266#endif
10267#ifdef _SC_STREAM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010268 {"SC_STREAM_MAX", _SC_STREAM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010269#endif
10270#ifdef _SC_SYNCHRONIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000010271 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000010272#endif
10273#ifdef _SC_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000010274 {"SC_THREADS", _SC_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000010275#endif
10276#ifdef _SC_THREAD_ATTR_STACKADDR
Victor Stinner8c62be82010-05-06 00:08:46 +000010277 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
Fred Drakec9680921999-12-13 16:37:25 +000010278#endif
10279#ifdef _SC_THREAD_ATTR_STACKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010280 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010281#endif
10282#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000010283 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
Fred Drakec9680921999-12-13 16:37:25 +000010284#endif
10285#ifdef _SC_THREAD_KEYS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010286 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010287#endif
10288#ifdef _SC_THREAD_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000010289 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000010290#endif
10291#ifdef _SC_THREAD_PRIO_INHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010292 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
Fred Drakec9680921999-12-13 16:37:25 +000010293#endif
10294#ifdef _SC_THREAD_PRIO_PROTECT
Victor Stinner8c62be82010-05-06 00:08:46 +000010295 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
Fred Drakec9680921999-12-13 16:37:25 +000010296#endif
10297#ifdef _SC_THREAD_PROCESS_SHARED
Victor Stinner8c62be82010-05-06 00:08:46 +000010298 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
Fred Drakec9680921999-12-13 16:37:25 +000010299#endif
10300#ifdef _SC_THREAD_SAFE_FUNCTIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000010301 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
Fred Drakec9680921999-12-13 16:37:25 +000010302#endif
10303#ifdef _SC_THREAD_STACK_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010304 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010305#endif
10306#ifdef _SC_THREAD_THREADS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010307 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010308#endif
10309#ifdef _SC_TIMERS
Victor Stinner8c62be82010-05-06 00:08:46 +000010310 {"SC_TIMERS", _SC_TIMERS},
Fred Drakec9680921999-12-13 16:37:25 +000010311#endif
10312#ifdef _SC_TIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010313 {"SC_TIMER_MAX", _SC_TIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010314#endif
10315#ifdef _SC_TTY_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010316 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010317#endif
10318#ifdef _SC_TZNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010319 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010320#endif
10321#ifdef _SC_T_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010322 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010323#endif
10324#ifdef _SC_UCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010325 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010326#endif
10327#ifdef _SC_UINT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010328 {"SC_UINT_MAX", _SC_UINT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010329#endif
10330#ifdef _SC_UIO_MAXIOV
Victor Stinner8c62be82010-05-06 00:08:46 +000010331 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
Fred Drakec9680921999-12-13 16:37:25 +000010332#endif
10333#ifdef _SC_ULONG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010334 {"SC_ULONG_MAX", _SC_ULONG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010335#endif
10336#ifdef _SC_USHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010337 {"SC_USHRT_MAX", _SC_USHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010338#endif
10339#ifdef _SC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010340 {"SC_VERSION", _SC_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010341#endif
10342#ifdef _SC_WORD_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010343 {"SC_WORD_BIT", _SC_WORD_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000010344#endif
10345#ifdef _SC_XBS5_ILP32_OFF32
Victor Stinner8c62be82010-05-06 00:08:46 +000010346 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
Fred Drakec9680921999-12-13 16:37:25 +000010347#endif
10348#ifdef _SC_XBS5_ILP32_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000010349 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000010350#endif
10351#ifdef _SC_XBS5_LP64_OFF64
Victor Stinner8c62be82010-05-06 00:08:46 +000010352 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
Fred Drakec9680921999-12-13 16:37:25 +000010353#endif
10354#ifdef _SC_XBS5_LPBIG_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000010355 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000010356#endif
10357#ifdef _SC_XOPEN_CRYPT
Victor Stinner8c62be82010-05-06 00:08:46 +000010358 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
Fred Drakec9680921999-12-13 16:37:25 +000010359#endif
10360#ifdef _SC_XOPEN_ENH_I18N
Victor Stinner8c62be82010-05-06 00:08:46 +000010361 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
Fred Drakec9680921999-12-13 16:37:25 +000010362#endif
10363#ifdef _SC_XOPEN_LEGACY
Victor Stinner8c62be82010-05-06 00:08:46 +000010364 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
Fred Drakec9680921999-12-13 16:37:25 +000010365#endif
10366#ifdef _SC_XOPEN_REALTIME
Victor Stinner8c62be82010-05-06 00:08:46 +000010367 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
Fred Drakec9680921999-12-13 16:37:25 +000010368#endif
10369#ifdef _SC_XOPEN_REALTIME_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000010370 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000010371#endif
10372#ifdef _SC_XOPEN_SHM
Victor Stinner8c62be82010-05-06 00:08:46 +000010373 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
Fred Drakec9680921999-12-13 16:37:25 +000010374#endif
10375#ifdef _SC_XOPEN_UNIX
Victor Stinner8c62be82010-05-06 00:08:46 +000010376 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
Fred Drakec9680921999-12-13 16:37:25 +000010377#endif
10378#ifdef _SC_XOPEN_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010379 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010380#endif
10381#ifdef _SC_XOPEN_XCU_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010382 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010383#endif
10384#ifdef _SC_XOPEN_XPG2
Victor Stinner8c62be82010-05-06 00:08:46 +000010385 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
Fred Drakec9680921999-12-13 16:37:25 +000010386#endif
10387#ifdef _SC_XOPEN_XPG3
Victor Stinner8c62be82010-05-06 00:08:46 +000010388 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
Fred Drakec9680921999-12-13 16:37:25 +000010389#endif
10390#ifdef _SC_XOPEN_XPG4
Victor Stinner8c62be82010-05-06 00:08:46 +000010391 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
Fred Drakec9680921999-12-13 16:37:25 +000010392#endif
10393};
10394
10395static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010396conv_sysconf_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000010397{
10398 return conv_confname(arg, valuep, posix_constants_sysconf,
10399 sizeof(posix_constants_sysconf)
10400 / sizeof(struct constdef));
10401}
10402
Larry Hastings2f936352014-08-05 14:04:04 +100010403
10404/*[clinic input]
10405os.sysconf -> long
10406 name: sysconf_confname
10407 /
10408
10409Return an integer-valued system configuration variable.
10410[clinic start generated code]*/
10411
Larry Hastings2f936352014-08-05 14:04:04 +100010412static long
10413os_sysconf_impl(PyModuleDef *module, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010414/*[clinic end generated code: output=ed567306f58d69c4 input=279e3430a33f29e4]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010415{
10416 long value;
10417
10418 errno = 0;
10419 value = sysconf(name);
10420 if (value == -1 && errno != 0)
10421 posix_error();
10422 return value;
10423}
10424#endif /* HAVE_SYSCONF */
Fred Drakec9680921999-12-13 16:37:25 +000010425
10426
Fred Drakebec628d1999-12-15 18:31:10 +000010427/* This code is used to ensure that the tables of configuration value names
Serhiy Storchaka56a6d852014-12-01 18:28:43 +020010428 * are in sorted order as required by conv_confname(), and also to build
Fred Drakebec628d1999-12-15 18:31:10 +000010429 * the exported dictionaries that are used to publish information about the
10430 * names available on the host platform.
10431 *
10432 * Sorting the table at runtime ensures that the table is properly ordered
10433 * when used, even for platforms we're not able to test on. It also makes
10434 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +000010435 */
Fred Drakebec628d1999-12-15 18:31:10 +000010436
10437static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010438cmp_constdefs(const void *v1, const void *v2)
Fred Drakebec628d1999-12-15 18:31:10 +000010439{
10440 const struct constdef *c1 =
Victor Stinner8c62be82010-05-06 00:08:46 +000010441 (const struct constdef *) v1;
Fred Drakebec628d1999-12-15 18:31:10 +000010442 const struct constdef *c2 =
Victor Stinner8c62be82010-05-06 00:08:46 +000010443 (const struct constdef *) v2;
Fred Drakebec628d1999-12-15 18:31:10 +000010444
10445 return strcmp(c1->name, c2->name);
10446}
10447
10448static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010449setup_confname_table(struct constdef *table, size_t tablesize,
Victor Stinner8c62be82010-05-06 00:08:46 +000010450 char *tablename, PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000010451{
Fred Drakebec628d1999-12-15 18:31:10 +000010452 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +000010453 size_t i;
Fred Drakebec628d1999-12-15 18:31:10 +000010454
10455 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
10456 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +000010457 if (d == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +000010458 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010459
Barry Warsaw3155db32000-04-13 15:20:40 +000010460 for (i=0; i < tablesize; ++i) {
Victor Stinner8c62be82010-05-06 00:08:46 +000010461 PyObject *o = PyLong_FromLong(table[i].value);
10462 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
10463 Py_XDECREF(o);
10464 Py_DECREF(d);
10465 return -1;
10466 }
10467 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +000010468 }
Fred Drake4d1e64b2002-04-15 19:40:07 +000010469 return PyModule_AddObject(module, tablename, d);
Fred Draked86ed291999-12-15 15:34:33 +000010470}
10471
Fred Drakebec628d1999-12-15 18:31:10 +000010472/* Return -1 on failure, 0 on success. */
10473static int
Fred Drake4d1e64b2002-04-15 19:40:07 +000010474setup_confname_tables(PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000010475{
10476#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +000010477 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +000010478 sizeof(posix_constants_pathconf)
10479 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010480 "pathconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010481 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010482#endif
10483#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +000010484 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +000010485 sizeof(posix_constants_confstr)
10486 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010487 "confstr_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010488 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010489#endif
10490#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +000010491 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +000010492 sizeof(posix_constants_sysconf)
10493 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010494 "sysconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010495 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010496#endif
Fred Drakebec628d1999-12-15 18:31:10 +000010497 return 0;
Fred Draked86ed291999-12-15 15:34:33 +000010498}
Fred Draked86ed291999-12-15 15:34:33 +000010499
10500
Larry Hastings2f936352014-08-05 14:04:04 +100010501/*[clinic input]
10502os.abort
10503
10504Abort the interpreter immediately.
10505
10506This function 'dumps core' or otherwise fails in the hardest way possible
10507on the hosting operating system. This function never returns.
10508[clinic start generated code]*/
10509
Larry Hastings2f936352014-08-05 14:04:04 +100010510static PyObject *
10511os_abort_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010512/*[clinic end generated code: output=486bb96647c299b3 input=cf2c7d98bc504047]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010513{
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010514 abort();
10515 /*NOTREACHED*/
10516 Py_FatalError("abort() called from Python code didn't abort!");
10517 return NULL;
10518}
Fred Drakebec628d1999-12-15 18:31:10 +000010519
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000010520#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100010521/* AC 3.5: change to path_t? but that might change exceptions */
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000010522PyDoc_STRVAR(win32_startfile__doc__,
Larry Hastings2f936352014-08-05 14:04:04 +100010523"startfile(filepath [, operation])\n\
10524\n\
10525Start a file with its associated application.\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000010526\n\
Georg Brandlf4f44152006-02-18 22:29:33 +000010527When \"operation\" is not specified or \"open\", this acts like\n\
10528double-clicking the file in Explorer, or giving the file name as an\n\
10529argument to the DOS \"start\" command: the file is opened with whatever\n\
10530application (if any) its extension is associated.\n\
10531When another \"operation\" is given, it specifies what should be done with\n\
10532the file. A typical operation is \"print\".\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000010533\n\
10534startfile returns as soon as the associated application is launched.\n\
10535There is no option to wait for the application to close, and no way\n\
10536to retrieve the application's exit status.\n\
10537\n\
10538The filepath is relative to the current directory. If you want to use\n\
10539an absolute path, make sure the first character is not a slash (\"/\");\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000010540the underlying Win32 ShellExecute function doesn't work if it is.");
Tim Petersf58a7aa2000-09-22 10:05:54 +000010541
Steve Dower7d0e0c92015-01-24 08:18:24 -080010542/* Grab ShellExecute dynamically from shell32 */
10543static int has_ShellExecute = -1;
10544static HINSTANCE (CALLBACK *Py_ShellExecuteA)(HWND, LPCSTR, LPCSTR, LPCSTR,
10545 LPCSTR, INT);
10546static HINSTANCE (CALLBACK *Py_ShellExecuteW)(HWND, LPCWSTR, LPCWSTR, LPCWSTR,
10547 LPCWSTR, INT);
10548static int
10549check_ShellExecute()
10550{
10551 HINSTANCE hShell32;
10552
10553 /* only recheck */
10554 if (-1 == has_ShellExecute) {
10555 Py_BEGIN_ALLOW_THREADS
10556 hShell32 = LoadLibraryW(L"SHELL32");
10557 Py_END_ALLOW_THREADS
10558 if (hShell32) {
10559 *(FARPROC*)&Py_ShellExecuteA = GetProcAddress(hShell32,
10560 "ShellExecuteA");
10561 *(FARPROC*)&Py_ShellExecuteW = GetProcAddress(hShell32,
10562 "ShellExecuteW");
10563 has_ShellExecute = Py_ShellExecuteA &&
10564 Py_ShellExecuteW;
10565 } else {
10566 has_ShellExecute = 0;
10567 }
10568 }
10569 return has_ShellExecute;
10570}
10571
10572
Tim Petersf58a7aa2000-09-22 10:05:54 +000010573static PyObject *
10574win32_startfile(PyObject *self, PyObject *args)
10575{
Victor Stinner8c62be82010-05-06 00:08:46 +000010576 PyObject *ofilepath;
10577 char *filepath;
10578 char *operation = NULL;
Victor Stinnereb5657a2011-09-30 01:44:27 +020010579 wchar_t *wpath, *woperation;
Victor Stinner8c62be82010-05-06 00:08:46 +000010580 HINSTANCE rc;
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +000010581
Victor Stinnereb5657a2011-09-30 01:44:27 +020010582 PyObject *unipath, *uoperation = NULL;
Steve Dower7d0e0c92015-01-24 08:18:24 -080010583
10584 if(!check_ShellExecute()) {
10585 /* If the OS doesn't have ShellExecute, return a
10586 NotImplementedError. */
10587 return PyErr_Format(PyExc_NotImplementedError,
10588 "startfile not available on this platform");
10589 }
10590
Victor Stinner8c62be82010-05-06 00:08:46 +000010591 if (!PyArg_ParseTuple(args, "U|s:startfile",
10592 &unipath, &operation)) {
10593 PyErr_Clear();
10594 goto normal;
10595 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000010596
Victor Stinner8c62be82010-05-06 00:08:46 +000010597 if (operation) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020010598 uoperation = PyUnicode_DecodeASCII(operation,
Victor Stinner8c62be82010-05-06 00:08:46 +000010599 strlen(operation), NULL);
Victor Stinnereb5657a2011-09-30 01:44:27 +020010600 if (!uoperation) {
Victor Stinner8c62be82010-05-06 00:08:46 +000010601 PyErr_Clear();
10602 operation = NULL;
10603 goto normal;
10604 }
10605 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000010606
Victor Stinnereb5657a2011-09-30 01:44:27 +020010607 wpath = PyUnicode_AsUnicode(unipath);
10608 if (wpath == NULL)
10609 goto normal;
10610 if (uoperation) {
10611 woperation = PyUnicode_AsUnicode(uoperation);
10612 if (woperation == NULL)
10613 goto normal;
10614 }
10615 else
10616 woperation = NULL;
10617
Victor Stinner8c62be82010-05-06 00:08:46 +000010618 Py_BEGIN_ALLOW_THREADS
Steve Dower7d0e0c92015-01-24 08:18:24 -080010619 rc = Py_ShellExecuteW((HWND)0, woperation, wpath,
10620 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000010621 Py_END_ALLOW_THREADS
10622
Victor Stinnereb5657a2011-09-30 01:44:27 +020010623 Py_XDECREF(uoperation);
Victor Stinner8c62be82010-05-06 00:08:46 +000010624 if (rc <= (HINSTANCE)32) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020010625 win32_error_object("startfile", unipath);
10626 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010627 }
10628 Py_INCREF(Py_None);
10629 return Py_None;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000010630
10631normal:
Victor Stinner8c62be82010-05-06 00:08:46 +000010632 if (!PyArg_ParseTuple(args, "O&|s:startfile",
10633 PyUnicode_FSConverter, &ofilepath,
10634 &operation))
10635 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +010010636 if (win32_warn_bytes_api()) {
10637 Py_DECREF(ofilepath);
10638 return NULL;
10639 }
Victor Stinner8c62be82010-05-06 00:08:46 +000010640 filepath = PyBytes_AsString(ofilepath);
10641 Py_BEGIN_ALLOW_THREADS
Steve Dower7d0e0c92015-01-24 08:18:24 -080010642 rc = Py_ShellExecuteA((HWND)0, operation, filepath,
10643 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000010644 Py_END_ALLOW_THREADS
10645 if (rc <= (HINSTANCE)32) {
10646 PyObject *errval = win32_error("startfile", filepath);
10647 Py_DECREF(ofilepath);
10648 return errval;
10649 }
10650 Py_DECREF(ofilepath);
10651 Py_INCREF(Py_None);
10652 return Py_None;
Tim Petersf58a7aa2000-09-22 10:05:54 +000010653}
Larry Hastings2f936352014-08-05 14:04:04 +100010654#endif /* MS_WINDOWS */
10655
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010656
Martin v. Löwis438b5342002-12-27 10:16:42 +000010657#ifdef HAVE_GETLOADAVG
Larry Hastings2f936352014-08-05 14:04:04 +100010658/*[clinic input]
10659os.getloadavg
10660
10661Return average recent system load information.
10662
10663Return the number of processes in the system run queue averaged over
10664the last 1, 5, and 15 minutes as a tuple of three floats.
10665Raises OSError if the load average was unobtainable.
10666[clinic start generated code]*/
10667
Larry Hastings2f936352014-08-05 14:04:04 +100010668static PyObject *
10669os_getloadavg_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010670/*[clinic end generated code: output=2b64c5b675d74c14 input=3d6d826b76d8a34e]*/
Martin v. Löwis438b5342002-12-27 10:16:42 +000010671{
10672 double loadavg[3];
Martin v. Löwis438b5342002-12-27 10:16:42 +000010673 if (getloadavg(loadavg, 3)!=3) {
Stefan Krah0e803b32010-11-26 16:16:47 +000010674 PyErr_SetString(PyExc_OSError, "Load averages are unobtainable");
10675 return NULL;
Martin v. Löwis438b5342002-12-27 10:16:42 +000010676 } else
Stefan Krah0e803b32010-11-26 16:16:47 +000010677 return Py_BuildValue("ddd", loadavg[0], loadavg[1], loadavg[2]);
Martin v. Löwis438b5342002-12-27 10:16:42 +000010678}
Larry Hastings2f936352014-08-05 14:04:04 +100010679#endif /* HAVE_GETLOADAVG */
Martin v. Löwis438b5342002-12-27 10:16:42 +000010680
Larry Hastings2f936352014-08-05 14:04:04 +100010681
10682/*[clinic input]
10683os.device_encoding
10684 fd: int
10685
10686Return a string describing the encoding of a terminal's file descriptor.
10687
10688The file descriptor must be attached to a terminal.
10689If the device is not a terminal, return None.
10690[clinic start generated code]*/
10691
Larry Hastings2f936352014-08-05 14:04:04 +100010692static PyObject *
10693os_device_encoding_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010694/*[clinic end generated code: output=34f14e33468419c1 input=9e1d4a42b66df312]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010695{
Brett Cannonefb00c02012-02-29 18:31:31 -050010696 return _Py_device_encoding(fd);
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000010697}
10698
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010699
Larry Hastings2f936352014-08-05 14:04:04 +100010700#ifdef HAVE_SETRESUID
10701/*[clinic input]
10702os.setresuid
10703
10704 ruid: uid_t
10705 euid: uid_t
10706 suid: uid_t
10707 /
10708
10709Set the current process's real, effective, and saved user ids.
10710[clinic start generated code]*/
10711
Larry Hastings2f936352014-08-05 14:04:04 +100010712static PyObject *
10713os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010714/*[clinic end generated code: output=92cc330812c6ed0f input=9e33cb79a82792f3]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010715{
Victor Stinner8c62be82010-05-06 00:08:46 +000010716 if (setresuid(ruid, euid, suid) < 0)
10717 return posix_error();
10718 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010719}
Larry Hastings2f936352014-08-05 14:04:04 +100010720#endif /* HAVE_SETRESUID */
10721
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010722
10723#ifdef HAVE_SETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100010724/*[clinic input]
10725os.setresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010726
Larry Hastings2f936352014-08-05 14:04:04 +100010727 rgid: gid_t
10728 egid: gid_t
10729 sgid: gid_t
10730 /
10731
10732Set the current process's real, effective, and saved group ids.
10733[clinic start generated code]*/
10734
Larry Hastings2f936352014-08-05 14:04:04 +100010735static PyObject *
10736os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010737/*[clinic end generated code: output=e91dc4842a604429 input=33e9e0785ef426b1]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010738{
Victor Stinner8c62be82010-05-06 00:08:46 +000010739 if (setresgid(rgid, egid, sgid) < 0)
10740 return posix_error();
10741 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010742}
Larry Hastings2f936352014-08-05 14:04:04 +100010743#endif /* HAVE_SETRESGID */
10744
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010745
10746#ifdef HAVE_GETRESUID
Larry Hastings2f936352014-08-05 14:04:04 +100010747/*[clinic input]
10748os.getresuid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010749
Larry Hastings2f936352014-08-05 14:04:04 +100010750Return a tuple of the current process's real, effective, and saved user ids.
10751[clinic start generated code]*/
10752
Larry Hastings2f936352014-08-05 14:04:04 +100010753static PyObject *
10754os_getresuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010755/*[clinic end generated code: output=9ddef62faae8e477 input=41ccfa8e1f6517ad]*/
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010756{
Victor Stinner8c62be82010-05-06 00:08:46 +000010757 uid_t ruid, euid, suid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010758 if (getresuid(&ruid, &euid, &suid) < 0)
10759 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020010760 return Py_BuildValue("(NNN)", _PyLong_FromUid(ruid),
10761 _PyLong_FromUid(euid),
10762 _PyLong_FromUid(suid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010763}
Larry Hastings2f936352014-08-05 14:04:04 +100010764#endif /* HAVE_GETRESUID */
10765
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010766
10767#ifdef HAVE_GETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100010768/*[clinic input]
10769os.getresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010770
Larry Hastings2f936352014-08-05 14:04:04 +100010771Return a tuple of the current process's real, effective, and saved group ids.
10772[clinic start generated code]*/
10773
Larry Hastings2f936352014-08-05 14:04:04 +100010774static PyObject *
10775os_getresgid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010776/*[clinic end generated code: output=e1a553cbcf16234c input=517e68db9ca32df6]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010777{
10778 gid_t rgid, egid, sgid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010779 if (getresgid(&rgid, &egid, &sgid) < 0)
10780 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020010781 return Py_BuildValue("(NNN)", _PyLong_FromGid(rgid),
10782 _PyLong_FromGid(egid),
10783 _PyLong_FromGid(sgid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010784}
Larry Hastings2f936352014-08-05 14:04:04 +100010785#endif /* HAVE_GETRESGID */
10786
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010787
Benjamin Peterson9428d532011-09-14 11:45:52 -040010788#ifdef USE_XATTRS
Larry Hastings2f936352014-08-05 14:04:04 +100010789/*[clinic input]
10790os.getxattr
Benjamin Peterson799bd802011-08-31 22:15:17 -040010791
Larry Hastings2f936352014-08-05 14:04:04 +100010792 path: path_t(allow_fd=True)
10793 attribute: path_t
10794 *
10795 follow_symlinks: bool = True
10796
10797Return the value of extended attribute attribute on path.
10798
10799path may be either a string or an open file descriptor.
10800If follow_symlinks is False, and the last element of the path is a symbolic
10801 link, getxattr will examine the symbolic link itself instead of the file
10802 the link points to.
10803
10804[clinic start generated code]*/
10805
Larry Hastings2f936352014-08-05 14:04:04 +100010806static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010807os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10808 int follow_symlinks)
10809/*[clinic end generated code: output=cf2cede74bd5d412 input=8c8ea3bab78d89c2]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010810{
10811 Py_ssize_t i;
10812 PyObject *buffer = NULL;
10813
10814 if (fd_and_follow_symlinks_invalid("getxattr", path->fd, follow_symlinks))
10815 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010816
Larry Hastings9cf065c2012-06-22 16:30:09 -070010817 for (i = 0; ; i++) {
10818 void *ptr;
10819 ssize_t result;
10820 static Py_ssize_t buffer_sizes[] = {128, XATTR_SIZE_MAX, 0};
10821 Py_ssize_t buffer_size = buffer_sizes[i];
10822 if (!buffer_size) {
Larry Hastings2f936352014-08-05 14:04:04 +100010823 path_error(path);
10824 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010825 }
10826 buffer = PyBytes_FromStringAndSize(NULL, buffer_size);
10827 if (!buffer)
Larry Hastings2f936352014-08-05 14:04:04 +100010828 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010829 ptr = PyBytes_AS_STRING(buffer);
Benjamin Peterson799bd802011-08-31 22:15:17 -040010830
Larry Hastings9cf065c2012-06-22 16:30:09 -070010831 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100010832 if (path->fd >= 0)
10833 result = fgetxattr(path->fd, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010834 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100010835 result = getxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010836 else
Larry Hastings2f936352014-08-05 14:04:04 +100010837 result = lgetxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010838 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010839
Larry Hastings9cf065c2012-06-22 16:30:09 -070010840 if (result < 0) {
10841 Py_DECREF(buffer);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010842 if (errno == ERANGE)
10843 continue;
Larry Hastings2f936352014-08-05 14:04:04 +100010844 path_error(path);
10845 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010846 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010847
Larry Hastings9cf065c2012-06-22 16:30:09 -070010848 if (result != buffer_size) {
10849 /* Can only shrink. */
10850 _PyBytes_Resize(&buffer, result);
10851 }
10852 break;
10853 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010854
Larry Hastings9cf065c2012-06-22 16:30:09 -070010855 return buffer;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010856}
10857
Larry Hastings2f936352014-08-05 14:04:04 +100010858
10859/*[clinic input]
10860os.setxattr
10861
10862 path: path_t(allow_fd=True)
10863 attribute: path_t
10864 value: Py_buffer
10865 flags: int = 0
10866 *
10867 follow_symlinks: bool = True
10868
10869Set extended attribute attribute on path to value.
10870
10871path may be either a string or an open file descriptor.
10872If follow_symlinks is False, and the last element of the path is a symbolic
10873 link, setxattr will modify the symbolic link itself instead of the file
10874 the link points to.
10875
10876[clinic start generated code]*/
10877
Benjamin Peterson799bd802011-08-31 22:15:17 -040010878static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010879os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10880 Py_buffer *value, int flags, int follow_symlinks)
10881/*[clinic end generated code: output=1b395ef82880fea0 input=f0d26833992015c2]*/
Benjamin Peterson799bd802011-08-31 22:15:17 -040010882{
Larry Hastings2f936352014-08-05 14:04:04 +100010883 ssize_t result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010884
Larry Hastings2f936352014-08-05 14:04:04 +100010885 if (fd_and_follow_symlinks_invalid("setxattr", path->fd, follow_symlinks))
Benjamin Peterson799bd802011-08-31 22:15:17 -040010886 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010887
Benjamin Peterson799bd802011-08-31 22:15:17 -040010888 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100010889 if (path->fd > -1)
10890 result = fsetxattr(path->fd, attribute->narrow,
10891 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010892 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100010893 result = setxattr(path->narrow, attribute->narrow,
10894 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010895 else
Larry Hastings2f936352014-08-05 14:04:04 +100010896 result = lsetxattr(path->narrow, attribute->narrow,
10897 value->buf, value->len, flags);
Benjamin Peterson799bd802011-08-31 22:15:17 -040010898 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010899
Larry Hastings9cf065c2012-06-22 16:30:09 -070010900 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100010901 path_error(path);
10902 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010903 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010904
Larry Hastings2f936352014-08-05 14:04:04 +100010905 Py_RETURN_NONE;
10906}
10907
10908
10909/*[clinic input]
10910os.removexattr
10911
10912 path: path_t(allow_fd=True)
10913 attribute: path_t
10914 *
10915 follow_symlinks: bool = True
10916
10917Remove extended attribute attribute on path.
10918
10919path may be either a string or an open file descriptor.
10920If follow_symlinks is False, and the last element of the path is a symbolic
10921 link, removexattr will modify the symbolic link itself instead of the file
10922 the link points to.
10923
10924[clinic start generated code]*/
10925
Larry Hastings2f936352014-08-05 14:04:04 +100010926static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010927os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10928 int follow_symlinks)
10929/*[clinic end generated code: output=f92bb39ab992650d input=cdb54834161e3329]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010930{
10931 ssize_t result;
10932
10933 if (fd_and_follow_symlinks_invalid("removexattr", path->fd, follow_symlinks))
10934 return NULL;
10935
10936 Py_BEGIN_ALLOW_THREADS;
10937 if (path->fd > -1)
10938 result = fremovexattr(path->fd, attribute->narrow);
10939 else if (follow_symlinks)
10940 result = removexattr(path->narrow, attribute->narrow);
10941 else
10942 result = lremovexattr(path->narrow, attribute->narrow);
10943 Py_END_ALLOW_THREADS;
10944
10945 if (result) {
10946 return path_error(path);
10947 }
10948
10949 Py_RETURN_NONE;
10950}
10951
10952
10953/*[clinic input]
10954os.listxattr
10955
10956 path: path_t(allow_fd=True, nullable=True) = None
10957 *
10958 follow_symlinks: bool = True
10959
10960Return a list of extended attributes on path.
10961
10962path may be either None, a string, or an open file descriptor.
10963if path is None, listxattr will examine the current directory.
10964If follow_symlinks is False, and the last element of the path is a symbolic
10965 link, listxattr will examine the symbolic link itself instead of the file
10966 the link points to.
10967[clinic start generated code]*/
10968
Larry Hastings2f936352014-08-05 14:04:04 +100010969static PyObject *
10970os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010971/*[clinic end generated code: output=a87ad6ce56e42a4f input=08cca53ac0b07c13]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010972{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010973 Py_ssize_t i;
10974 PyObject *result = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100010975 const char *name;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010976 char *buffer = NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010977
Larry Hastings2f936352014-08-05 14:04:04 +100010978 if (fd_and_follow_symlinks_invalid("listxattr", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070010979 goto exit;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010980
Larry Hastings2f936352014-08-05 14:04:04 +100010981 name = path->narrow ? path->narrow : ".";
10982
Larry Hastings9cf065c2012-06-22 16:30:09 -070010983 for (i = 0; ; i++) {
10984 char *start, *trace, *end;
10985 ssize_t length;
10986 static Py_ssize_t buffer_sizes[] = { 256, XATTR_LIST_MAX, 0 };
10987 Py_ssize_t buffer_size = buffer_sizes[i];
10988 if (!buffer_size) {
Christian Heimes3b9493b2012-09-23 16:11:15 +020010989 /* ERANGE */
Larry Hastings2f936352014-08-05 14:04:04 +100010990 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010991 break;
10992 }
10993 buffer = PyMem_MALLOC(buffer_size);
10994 if (!buffer) {
10995 PyErr_NoMemory();
10996 break;
10997 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010998
Larry Hastings9cf065c2012-06-22 16:30:09 -070010999 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100011000 if (path->fd > -1)
11001 length = flistxattr(path->fd, buffer, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070011002 else if (follow_symlinks)
11003 length = listxattr(name, buffer, buffer_size);
11004 else
11005 length = llistxattr(name, buffer, buffer_size);
11006 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040011007
Larry Hastings9cf065c2012-06-22 16:30:09 -070011008 if (length < 0) {
Antoine Pitrou7f987392013-05-13 19:46:29 +020011009 if (errno == ERANGE) {
11010 PyMem_FREE(buffer);
Benjamin Petersondedac522013-05-13 19:55:40 -050011011 buffer = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070011012 continue;
Antoine Pitrou7f987392013-05-13 19:46:29 +020011013 }
Larry Hastings2f936352014-08-05 14:04:04 +100011014 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070011015 break;
11016 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040011017
Larry Hastings9cf065c2012-06-22 16:30:09 -070011018 result = PyList_New(0);
11019 if (!result) {
11020 goto exit;
11021 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040011022
Larry Hastings9cf065c2012-06-22 16:30:09 -070011023 end = buffer + length;
11024 for (trace = start = buffer; trace != end; trace++) {
11025 if (!*trace) {
11026 int error;
11027 PyObject *attribute = PyUnicode_DecodeFSDefaultAndSize(start,
11028 trace - start);
11029 if (!attribute) {
11030 Py_DECREF(result);
11031 result = NULL;
11032 goto exit;
11033 }
11034 error = PyList_Append(result, attribute);
11035 Py_DECREF(attribute);
11036 if (error) {
11037 Py_DECREF(result);
11038 result = NULL;
11039 goto exit;
11040 }
11041 start = trace + 1;
11042 }
11043 }
11044 break;
11045 }
11046exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070011047 if (buffer)
11048 PyMem_FREE(buffer);
11049 return result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040011050}
Benjamin Peterson9428d532011-09-14 11:45:52 -040011051#endif /* USE_XATTRS */
Benjamin Peterson799bd802011-08-31 22:15:17 -040011052
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011053
Larry Hastings2f936352014-08-05 14:04:04 +100011054/*[clinic input]
11055os.urandom
11056
11057 size: Py_ssize_t
11058 /
11059
11060Return a bytes object containing random bytes suitable for cryptographic use.
11061[clinic start generated code]*/
11062
Larry Hastings2f936352014-08-05 14:04:04 +100011063static PyObject *
11064os_urandom_impl(PyModuleDef *module, Py_ssize_t size)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011065/*[clinic end generated code: output=e0011f021501f03b input=4067cdb1b6776c29]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011066{
11067 PyObject *bytes;
11068 int result;
11069
Georg Brandl2fb477c2012-02-21 00:33:36 +010011070 if (size < 0)
11071 return PyErr_Format(PyExc_ValueError,
11072 "negative argument not allowed");
Larry Hastings2f936352014-08-05 14:04:04 +100011073 bytes = PyBytes_FromStringAndSize(NULL, size);
11074 if (bytes == NULL)
Georg Brandl2fb477c2012-02-21 00:33:36 +010011075 return NULL;
11076
Larry Hastings2f936352014-08-05 14:04:04 +100011077 result = _PyOS_URandom(PyBytes_AS_STRING(bytes),
11078 PyBytes_GET_SIZE(bytes));
11079 if (result == -1) {
11080 Py_DECREF(bytes);
Georg Brandl2fb477c2012-02-21 00:33:36 +010011081 return NULL;
11082 }
Larry Hastings2f936352014-08-05 14:04:04 +100011083 return bytes;
Georg Brandl2fb477c2012-02-21 00:33:36 +010011084}
11085
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011086/* Terminal size querying */
11087
11088static PyTypeObject TerminalSizeType;
11089
11090PyDoc_STRVAR(TerminalSize_docstring,
11091 "A tuple of (columns, lines) for holding terminal window size");
11092
11093static PyStructSequence_Field TerminalSize_fields[] = {
11094 {"columns", "width of the terminal window in characters"},
11095 {"lines", "height of the terminal window in characters"},
11096 {NULL, NULL}
11097};
11098
11099static PyStructSequence_Desc TerminalSize_desc = {
11100 "os.terminal_size",
11101 TerminalSize_docstring,
11102 TerminalSize_fields,
11103 2,
11104};
11105
11106#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
Larry Hastings2f936352014-08-05 14:04:04 +100011107/* AC 3.5: fd should accept None */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011108PyDoc_STRVAR(termsize__doc__,
11109 "Return the size of the terminal window as (columns, lines).\n" \
11110 "\n" \
11111 "The optional argument fd (default standard output) specifies\n" \
11112 "which file descriptor should be queried.\n" \
11113 "\n" \
11114 "If the file descriptor is not connected to a terminal, an OSError\n" \
11115 "is thrown.\n" \
11116 "\n" \
11117 "This function will only be defined if an implementation is\n" \
11118 "available for this system.\n" \
11119 "\n" \
11120 "shutil.get_terminal_size is the high-level function which should \n" \
11121 "normally be used, os.get_terminal_size is the low-level implementation.");
11122
11123static PyObject*
11124get_terminal_size(PyObject *self, PyObject *args)
11125{
11126 int columns, lines;
11127 PyObject *termsize;
11128
11129 int fd = fileno(stdout);
11130 /* Under some conditions stdout may not be connected and
11131 * fileno(stdout) may point to an invalid file descriptor. For example
11132 * GUI apps don't have valid standard streams by default.
11133 *
11134 * If this happens, and the optional fd argument is not present,
11135 * the ioctl below will fail returning EBADF. This is what we want.
11136 */
11137
11138 if (!PyArg_ParseTuple(args, "|i", &fd))
11139 return NULL;
11140
11141#ifdef TERMSIZE_USE_IOCTL
11142 {
11143 struct winsize w;
11144 if (ioctl(fd, TIOCGWINSZ, &w))
11145 return PyErr_SetFromErrno(PyExc_OSError);
11146 columns = w.ws_col;
11147 lines = w.ws_row;
11148 }
11149#endif /* TERMSIZE_USE_IOCTL */
11150
11151#ifdef TERMSIZE_USE_CONIO
11152 {
11153 DWORD nhandle;
11154 HANDLE handle;
11155 CONSOLE_SCREEN_BUFFER_INFO csbi;
11156 switch (fd) {
11157 case 0: nhandle = STD_INPUT_HANDLE;
11158 break;
11159 case 1: nhandle = STD_OUTPUT_HANDLE;
11160 break;
11161 case 2: nhandle = STD_ERROR_HANDLE;
11162 break;
11163 default:
11164 return PyErr_Format(PyExc_ValueError, "bad file descriptor");
11165 }
11166 handle = GetStdHandle(nhandle);
11167 if (handle == NULL)
11168 return PyErr_Format(PyExc_OSError, "handle cannot be retrieved");
11169 if (handle == INVALID_HANDLE_VALUE)
11170 return PyErr_SetFromWindowsErr(0);
11171
11172 if (!GetConsoleScreenBufferInfo(handle, &csbi))
11173 return PyErr_SetFromWindowsErr(0);
11174
11175 columns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
11176 lines = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
11177 }
11178#endif /* TERMSIZE_USE_CONIO */
11179
11180 termsize = PyStructSequence_New(&TerminalSizeType);
11181 if (termsize == NULL)
11182 return NULL;
11183 PyStructSequence_SET_ITEM(termsize, 0, PyLong_FromLong(columns));
11184 PyStructSequence_SET_ITEM(termsize, 1, PyLong_FromLong(lines));
11185 if (PyErr_Occurred()) {
11186 Py_DECREF(termsize);
11187 return NULL;
11188 }
11189 return termsize;
11190}
11191#endif /* defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL) */
11192
Larry Hastings2f936352014-08-05 14:04:04 +100011193
11194/*[clinic input]
11195os.cpu_count
11196
11197Return the number of CPUs in the system; return None if indeterminable.
11198[clinic start generated code]*/
11199
Larry Hastings2f936352014-08-05 14:04:04 +100011200static PyObject *
11201os_cpu_count_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011202/*[clinic end generated code: output=c59ee7f6bce832b8 input=d55e2f8f3823a628]*/
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011203{
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020011204 int ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011205#ifdef MS_WINDOWS
11206 SYSTEM_INFO sysinfo;
11207 GetSystemInfo(&sysinfo);
11208 ncpu = sysinfo.dwNumberOfProcessors;
11209#elif defined(__hpux)
11210 ncpu = mpctl(MPC_GETNUMSPUS, NULL, NULL);
11211#elif defined(HAVE_SYSCONF) && defined(_SC_NPROCESSORS_ONLN)
11212 ncpu = sysconf(_SC_NPROCESSORS_ONLN);
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011213#elif defined(__DragonFly__) || \
11214 defined(__OpenBSD__) || \
11215 defined(__FreeBSD__) || \
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020011216 defined(__NetBSD__) || \
11217 defined(__APPLE__)
Charles-Francois Natali7c4f8da2013-05-20 17:40:32 +020011218 int mib[2];
11219 size_t len = sizeof(ncpu);
11220 mib[0] = CTL_HW;
11221 mib[1] = HW_NCPU;
11222 if (sysctl(mib, 2, &ncpu, &len, NULL, 0) != 0)
11223 ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011224#endif
11225 if (ncpu >= 1)
11226 return PyLong_FromLong(ncpu);
11227 else
11228 Py_RETURN_NONE;
11229}
11230
Victor Stinnerdaf45552013-08-28 00:53:59 +020011231
Larry Hastings2f936352014-08-05 14:04:04 +100011232/*[clinic input]
11233os.get_inheritable -> bool
11234
11235 fd: int
11236 /
11237
11238Get the close-on-exe flag of the specified file descriptor.
11239[clinic start generated code]*/
11240
Larry Hastings2f936352014-08-05 14:04:04 +100011241static int
11242os_get_inheritable_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011243/*[clinic end generated code: output=36110bb36efaa21e input=89ac008dc9ab6b95]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011244{
Steve Dower8fc89802015-04-12 00:26:27 -040011245 int return_value;
11246 if (!_PyVerify_fd(fd)) {
Larry Hastings2f936352014-08-05 14:04:04 +100011247 posix_error();
11248 return -1;
11249 }
11250
Steve Dower8fc89802015-04-12 00:26:27 -040011251 _Py_BEGIN_SUPPRESS_IPH
11252 return_value = _Py_get_inheritable(fd);
11253 _Py_END_SUPPRESS_IPH
11254 return return_value;
Larry Hastings2f936352014-08-05 14:04:04 +100011255}
11256
11257
11258/*[clinic input]
11259os.set_inheritable
11260 fd: int
11261 inheritable: int
11262 /
11263
11264Set the inheritable flag of the specified file descriptor.
11265[clinic start generated code]*/
11266
Larry Hastings2f936352014-08-05 14:04:04 +100011267static PyObject *
11268os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011269/*[clinic end generated code: output=2ac5c6ce8623f045 input=9ceaead87a1e2402]*/
Victor Stinnerdaf45552013-08-28 00:53:59 +020011270{
Steve Dower8fc89802015-04-12 00:26:27 -040011271 int result;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011272 if (!_PyVerify_fd(fd))
11273 return posix_error();
11274
Steve Dower8fc89802015-04-12 00:26:27 -040011275 _Py_BEGIN_SUPPRESS_IPH
11276 result = _Py_set_inheritable(fd, inheritable, NULL);
11277 _Py_END_SUPPRESS_IPH
11278 if (result < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +020011279 return NULL;
11280 Py_RETURN_NONE;
11281}
11282
11283
11284#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100011285/*[clinic input]
11286os.get_handle_inheritable -> bool
11287 handle: Py_intptr_t
11288 /
Victor Stinnerdaf45552013-08-28 00:53:59 +020011289
Larry Hastings2f936352014-08-05 14:04:04 +100011290Get the close-on-exe flag of the specified file descriptor.
11291[clinic start generated code]*/
11292
Larry Hastings2f936352014-08-05 14:04:04 +100011293static int
11294os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011295/*[clinic end generated code: output=3b7b3e1b43f312b6 input=5f7759443aae3dc5]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011296{
11297 DWORD flags;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011298
11299 if (!GetHandleInformation((HANDLE)handle, &flags)) {
11300 PyErr_SetFromWindowsErr(0);
Larry Hastings2f936352014-08-05 14:04:04 +100011301 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011302 }
11303
Larry Hastings2f936352014-08-05 14:04:04 +100011304 return flags & HANDLE_FLAG_INHERIT;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011305}
11306
Victor Stinnerdaf45552013-08-28 00:53:59 +020011307
Larry Hastings2f936352014-08-05 14:04:04 +100011308/*[clinic input]
11309os.set_handle_inheritable
11310 handle: Py_intptr_t
11311 inheritable: bool
11312 /
11313
11314Set the inheritable flag of the specified handle.
11315[clinic start generated code]*/
11316
Larry Hastings2f936352014-08-05 14:04:04 +100011317static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040011318os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle,
11319 int inheritable)
11320/*[clinic end generated code: output=d2e111a96c9eb296 input=e64b2b2730469def]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011321{
11322 DWORD flags = inheritable ? HANDLE_FLAG_INHERIT : 0;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011323 if (!SetHandleInformation((HANDLE)handle, HANDLE_FLAG_INHERIT, flags)) {
11324 PyErr_SetFromWindowsErr(0);
11325 return NULL;
11326 }
11327 Py_RETURN_NONE;
11328}
Larry Hastings2f936352014-08-05 14:04:04 +100011329#endif /* MS_WINDOWS */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011330
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011331#ifndef MS_WINDOWS
11332PyDoc_STRVAR(get_blocking__doc__,
11333 "get_blocking(fd) -> bool\n" \
11334 "\n" \
11335 "Get the blocking mode of the file descriptor:\n" \
11336 "False if the O_NONBLOCK flag is set, True if the flag is cleared.");
11337
11338static PyObject*
11339posix_get_blocking(PyObject *self, PyObject *args)
11340{
11341 int fd;
11342 int blocking;
11343
11344 if (!PyArg_ParseTuple(args, "i:get_blocking", &fd))
11345 return NULL;
11346
11347 if (!_PyVerify_fd(fd))
11348 return posix_error();
11349
Steve Dower8fc89802015-04-12 00:26:27 -040011350 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011351 blocking = _Py_get_blocking(fd);
Steve Dower8fc89802015-04-12 00:26:27 -040011352 _Py_END_SUPPRESS_IPH
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011353 if (blocking < 0)
11354 return NULL;
11355 return PyBool_FromLong(blocking);
11356}
11357
11358PyDoc_STRVAR(set_blocking__doc__,
11359 "set_blocking(fd, blocking)\n" \
11360 "\n" \
11361 "Set the blocking mode of the specified file descriptor.\n" \
11362 "Set the O_NONBLOCK flag if blocking is False,\n" \
11363 "clear the O_NONBLOCK flag otherwise.");
11364
11365static PyObject*
11366posix_set_blocking(PyObject *self, PyObject *args)
11367{
Steve Dower8fc89802015-04-12 00:26:27 -040011368 int fd, blocking, result;
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011369
11370 if (!PyArg_ParseTuple(args, "ii:set_blocking", &fd, &blocking))
11371 return NULL;
11372
11373 if (!_PyVerify_fd(fd))
11374 return posix_error();
11375
Steve Dower8fc89802015-04-12 00:26:27 -040011376 _Py_BEGIN_SUPPRESS_IPH
11377 result = _Py_set_blocking(fd, blocking);
11378 _Py_END_SUPPRESS_IPH
11379 if (result < 0)
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011380 return NULL;
11381 Py_RETURN_NONE;
11382}
11383#endif /* !MS_WINDOWS */
11384
11385
Victor Stinner6036e442015-03-08 01:58:04 +010011386PyDoc_STRVAR(posix_scandir__doc__,
11387"scandir(path='.') -> iterator of DirEntry objects for given path");
11388
11389static char *follow_symlinks_keywords[] = {"follow_symlinks", NULL};
11390
11391typedef struct {
11392 PyObject_HEAD
11393 PyObject *name;
11394 PyObject *path;
11395 PyObject *stat;
11396 PyObject *lstat;
11397#ifdef MS_WINDOWS
11398 struct _Py_stat_struct win32_lstat;
11399 __int64 win32_file_index;
11400 int got_file_index;
11401#else /* POSIX */
Victor Stinner35a97c02015-03-08 02:59:09 +010011402#ifdef HAVE_DIRENT_D_TYPE
Victor Stinner6036e442015-03-08 01:58:04 +010011403 unsigned char d_type;
Victor Stinner35a97c02015-03-08 02:59:09 +010011404#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011405 ino_t d_ino;
11406#endif
11407} DirEntry;
11408
11409static void
11410DirEntry_dealloc(DirEntry *entry)
11411{
11412 Py_XDECREF(entry->name);
11413 Py_XDECREF(entry->path);
11414 Py_XDECREF(entry->stat);
11415 Py_XDECREF(entry->lstat);
11416 Py_TYPE(entry)->tp_free((PyObject *)entry);
11417}
11418
11419/* Forward reference */
11420static int
11421DirEntry_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits);
11422
11423/* Set exception and return -1 on error, 0 for False, 1 for True */
11424static int
11425DirEntry_is_symlink(DirEntry *self)
11426{
11427#ifdef MS_WINDOWS
11428 return (self->win32_lstat.st_mode & S_IFMT) == S_IFLNK;
Victor Stinner35a97c02015-03-08 02:59:09 +010011429#elif defined(HAVE_DIRENT_D_TYPE)
11430 /* POSIX */
Victor Stinner6036e442015-03-08 01:58:04 +010011431 if (self->d_type != DT_UNKNOWN)
11432 return self->d_type == DT_LNK;
11433 else
11434 return DirEntry_test_mode(self, 0, S_IFLNK);
Victor Stinner35a97c02015-03-08 02:59:09 +010011435#else
11436 /* POSIX without d_type */
11437 return DirEntry_test_mode(self, 0, S_IFLNK);
Victor Stinner6036e442015-03-08 01:58:04 +010011438#endif
11439}
11440
11441static PyObject *
11442DirEntry_py_is_symlink(DirEntry *self)
11443{
11444 int result;
11445
11446 result = DirEntry_is_symlink(self);
11447 if (result == -1)
11448 return NULL;
11449 return PyBool_FromLong(result);
11450}
11451
11452static PyObject *
11453DirEntry_fetch_stat(DirEntry *self, int follow_symlinks)
11454{
11455 int result;
11456 struct _Py_stat_struct st;
11457
11458#ifdef MS_WINDOWS
11459 wchar_t *path;
11460
11461 path = PyUnicode_AsUnicode(self->path);
11462 if (!path)
11463 return NULL;
11464
11465 if (follow_symlinks)
11466 result = win32_stat_w(path, &st);
11467 else
11468 result = win32_lstat_w(path, &st);
11469
11470 if (result != 0) {
11471 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
11472 0, self->path);
11473 }
11474#else /* POSIX */
11475 PyObject *bytes;
11476 char *path;
11477
11478 if (!PyUnicode_FSConverter(self->path, &bytes))
11479 return NULL;
11480 path = PyBytes_AS_STRING(bytes);
11481
11482 if (follow_symlinks)
11483 result = STAT(path, &st);
11484 else
11485 result = LSTAT(path, &st);
11486 Py_DECREF(bytes);
11487
11488 if (result != 0)
11489 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, self->path);
11490#endif
11491
11492 return _pystat_fromstructstat(&st);
11493}
11494
11495static PyObject *
11496DirEntry_get_lstat(DirEntry *self)
11497{
11498 if (!self->lstat) {
11499#ifdef MS_WINDOWS
11500 self->lstat = _pystat_fromstructstat(&self->win32_lstat);
11501#else /* POSIX */
11502 self->lstat = DirEntry_fetch_stat(self, 0);
11503#endif
11504 }
11505 Py_XINCREF(self->lstat);
11506 return self->lstat;
11507}
11508
11509static PyObject *
11510DirEntry_get_stat(DirEntry *self, int follow_symlinks)
11511{
11512 if (!follow_symlinks)
11513 return DirEntry_get_lstat(self);
11514
11515 if (!self->stat) {
11516 int result = DirEntry_is_symlink(self);
11517 if (result == -1)
11518 return NULL;
11519 else if (result)
11520 self->stat = DirEntry_fetch_stat(self, 1);
11521 else
11522 self->stat = DirEntry_get_lstat(self);
11523 }
11524
11525 Py_XINCREF(self->stat);
11526 return self->stat;
11527}
11528
11529static PyObject *
11530DirEntry_stat(DirEntry *self, PyObject *args, PyObject *kwargs)
11531{
11532 int follow_symlinks = 1;
11533
11534 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.stat",
11535 follow_symlinks_keywords, &follow_symlinks))
11536 return NULL;
11537
11538 return DirEntry_get_stat(self, follow_symlinks);
11539}
11540
11541/* Set exception and return -1 on error, 0 for False, 1 for True */
11542static int
11543DirEntry_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits)
11544{
11545 PyObject *stat = NULL;
11546 PyObject *st_mode = NULL;
11547 long mode;
11548 int result;
Victor Stinner35a97c02015-03-08 02:59:09 +010011549#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011550 int is_symlink;
11551 int need_stat;
Victor Stinner35a97c02015-03-08 02:59:09 +010011552#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011553#ifdef MS_WINDOWS
11554 unsigned long dir_bits;
11555#endif
Victor Stinner35a97c02015-03-08 02:59:09 +010011556 _Py_IDENTIFIER(st_mode);
Victor Stinner6036e442015-03-08 01:58:04 +010011557
11558#ifdef MS_WINDOWS
11559 is_symlink = (self->win32_lstat.st_mode & S_IFMT) == S_IFLNK;
11560 need_stat = follow_symlinks && is_symlink;
Victor Stinner35a97c02015-03-08 02:59:09 +010011561#elif defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011562 is_symlink = self->d_type == DT_LNK;
11563 need_stat = self->d_type == DT_UNKNOWN || (follow_symlinks && is_symlink);
11564#endif
11565
Victor Stinner35a97c02015-03-08 02:59:09 +010011566#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011567 if (need_stat) {
Victor Stinner35a97c02015-03-08 02:59:09 +010011568#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011569 stat = DirEntry_get_stat(self, follow_symlinks);
11570 if (!stat) {
11571 if (PyErr_ExceptionMatches(PyExc_FileNotFoundError)) {
11572 /* If file doesn't exist (anymore), then return False
11573 (i.e., say it's not a file/directory) */
11574 PyErr_Clear();
11575 return 0;
11576 }
11577 goto error;
11578 }
11579 st_mode = _PyObject_GetAttrId(stat, &PyId_st_mode);
11580 if (!st_mode)
11581 goto error;
11582
11583 mode = PyLong_AsLong(st_mode);
11584 if (mode == -1 && PyErr_Occurred())
11585 goto error;
11586 Py_CLEAR(st_mode);
11587 Py_CLEAR(stat);
11588 result = (mode & S_IFMT) == mode_bits;
Victor Stinner35a97c02015-03-08 02:59:09 +010011589#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011590 }
11591 else if (is_symlink) {
11592 assert(mode_bits != S_IFLNK);
11593 result = 0;
11594 }
11595 else {
11596 assert(mode_bits == S_IFDIR || mode_bits == S_IFREG);
11597#ifdef MS_WINDOWS
11598 dir_bits = self->win32_lstat.st_file_attributes & FILE_ATTRIBUTE_DIRECTORY;
11599 if (mode_bits == S_IFDIR)
11600 result = dir_bits != 0;
11601 else
11602 result = dir_bits == 0;
11603#else /* POSIX */
11604 if (mode_bits == S_IFDIR)
11605 result = self->d_type == DT_DIR;
11606 else
11607 result = self->d_type == DT_REG;
11608#endif
11609 }
Victor Stinner35a97c02015-03-08 02:59:09 +010011610#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011611
11612 return result;
11613
11614error:
11615 Py_XDECREF(st_mode);
11616 Py_XDECREF(stat);
11617 return -1;
11618}
11619
11620static PyObject *
11621DirEntry_py_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits)
11622{
11623 int result;
11624
11625 result = DirEntry_test_mode(self, follow_symlinks, mode_bits);
11626 if (result == -1)
11627 return NULL;
11628 return PyBool_FromLong(result);
11629}
11630
11631static PyObject *
11632DirEntry_is_dir(DirEntry *self, PyObject *args, PyObject *kwargs)
11633{
11634 int follow_symlinks = 1;
11635
11636 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.is_dir",
11637 follow_symlinks_keywords, &follow_symlinks))
11638 return NULL;
11639
11640 return DirEntry_py_test_mode(self, follow_symlinks, S_IFDIR);
11641}
11642
11643static PyObject *
11644DirEntry_is_file(DirEntry *self, PyObject *args, PyObject *kwargs)
11645{
11646 int follow_symlinks = 1;
11647
11648 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.is_file",
11649 follow_symlinks_keywords, &follow_symlinks))
11650 return NULL;
11651
11652 return DirEntry_py_test_mode(self, follow_symlinks, S_IFREG);
11653}
11654
11655static PyObject *
11656DirEntry_inode(DirEntry *self)
11657{
11658#ifdef MS_WINDOWS
11659 if (!self->got_file_index) {
11660 wchar_t *path;
11661 struct _Py_stat_struct stat;
11662
11663 path = PyUnicode_AsUnicode(self->path);
11664 if (!path)
11665 return NULL;
11666
11667 if (win32_lstat_w(path, &stat) != 0) {
11668 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
11669 0, self->path);
11670 }
11671
11672 self->win32_file_index = stat.st_ino;
11673 self->got_file_index = 1;
11674 }
11675 return PyLong_FromLongLong((PY_LONG_LONG)self->win32_file_index);
11676#else /* POSIX */
11677#ifdef HAVE_LARGEFILE_SUPPORT
11678 return PyLong_FromLongLong((PY_LONG_LONG)self->d_ino);
11679#else
11680 return PyLong_FromLong((long)self->d_ino);
11681#endif
11682#endif
11683}
11684
11685static PyObject *
11686DirEntry_repr(DirEntry *self)
11687{
11688 return PyUnicode_FromFormat("<DirEntry %R>", self->name);
11689}
11690
11691static PyMemberDef DirEntry_members[] = {
11692 {"name", T_OBJECT_EX, offsetof(DirEntry, name), READONLY,
11693 "the entry's base filename, relative to scandir() \"path\" argument"},
11694 {"path", T_OBJECT_EX, offsetof(DirEntry, path), READONLY,
11695 "the entry's full path name; equivalent to os.path.join(scandir_path, entry.name)"},
11696 {NULL}
11697};
11698
11699static PyMethodDef DirEntry_methods[] = {
11700 {"is_dir", (PyCFunction)DirEntry_is_dir, METH_VARARGS | METH_KEYWORDS,
11701 "return True if the entry is a directory; cached per entry"
11702 },
11703 {"is_file", (PyCFunction)DirEntry_is_file, METH_VARARGS | METH_KEYWORDS,
11704 "return True if the entry is a file; cached per entry"
11705 },
11706 {"is_symlink", (PyCFunction)DirEntry_py_is_symlink, METH_NOARGS,
11707 "return True if the entry is a symbolic link; cached per entry"
11708 },
11709 {"stat", (PyCFunction)DirEntry_stat, METH_VARARGS | METH_KEYWORDS,
11710 "return stat_result object for the entry; cached per entry"
11711 },
11712 {"inode", (PyCFunction)DirEntry_inode, METH_NOARGS,
11713 "return inode of the entry; cached per entry",
11714 },
11715 {NULL}
11716};
11717
Benjamin Peterson5646de42015-04-12 17:56:34 -040011718static PyTypeObject DirEntryType = {
Victor Stinner6036e442015-03-08 01:58:04 +010011719 PyVarObject_HEAD_INIT(NULL, 0)
11720 MODNAME ".DirEntry", /* tp_name */
11721 sizeof(DirEntry), /* tp_basicsize */
11722 0, /* tp_itemsize */
11723 /* methods */
11724 (destructor)DirEntry_dealloc, /* tp_dealloc */
11725 0, /* tp_print */
11726 0, /* tp_getattr */
11727 0, /* tp_setattr */
11728 0, /* tp_compare */
11729 (reprfunc)DirEntry_repr, /* tp_repr */
11730 0, /* tp_as_number */
11731 0, /* tp_as_sequence */
11732 0, /* tp_as_mapping */
11733 0, /* tp_hash */
11734 0, /* tp_call */
11735 0, /* tp_str */
11736 0, /* tp_getattro */
11737 0, /* tp_setattro */
11738 0, /* tp_as_buffer */
11739 Py_TPFLAGS_DEFAULT, /* tp_flags */
11740 0, /* tp_doc */
11741 0, /* tp_traverse */
11742 0, /* tp_clear */
11743 0, /* tp_richcompare */
11744 0, /* tp_weaklistoffset */
11745 0, /* tp_iter */
11746 0, /* tp_iternext */
11747 DirEntry_methods, /* tp_methods */
11748 DirEntry_members, /* tp_members */
11749};
11750
11751#ifdef MS_WINDOWS
11752
11753static wchar_t *
11754join_path_filenameW(wchar_t *path_wide, wchar_t* filename)
11755{
11756 Py_ssize_t path_len;
11757 Py_ssize_t size;
11758 wchar_t *result;
11759 wchar_t ch;
11760
11761 if (!path_wide) { /* Default arg: "." */
11762 path_wide = L".";
11763 path_len = 1;
11764 }
11765 else {
11766 path_len = wcslen(path_wide);
11767 }
11768
11769 /* The +1's are for the path separator and the NUL */
11770 size = path_len + 1 + wcslen(filename) + 1;
11771 result = PyMem_New(wchar_t, size);
11772 if (!result) {
11773 PyErr_NoMemory();
11774 return NULL;
11775 }
11776 wcscpy(result, path_wide);
11777 if (path_len > 0) {
11778 ch = result[path_len - 1];
11779 if (ch != SEP && ch != ALTSEP && ch != L':')
11780 result[path_len++] = SEP;
11781 wcscpy(result + path_len, filename);
11782 }
11783 return result;
11784}
11785
11786static PyObject *
11787DirEntry_from_find_data(path_t *path, WIN32_FIND_DATAW *dataW)
11788{
11789 DirEntry *entry;
11790 BY_HANDLE_FILE_INFORMATION file_info;
11791 ULONG reparse_tag;
11792 wchar_t *joined_path;
11793
11794 entry = PyObject_New(DirEntry, &DirEntryType);
11795 if (!entry)
11796 return NULL;
11797 entry->name = NULL;
11798 entry->path = NULL;
11799 entry->stat = NULL;
11800 entry->lstat = NULL;
11801 entry->got_file_index = 0;
11802
11803 entry->name = PyUnicode_FromWideChar(dataW->cFileName, -1);
11804 if (!entry->name)
11805 goto error;
11806
11807 joined_path = join_path_filenameW(path->wide, dataW->cFileName);
11808 if (!joined_path)
11809 goto error;
11810
11811 entry->path = PyUnicode_FromWideChar(joined_path, -1);
11812 PyMem_Free(joined_path);
11813 if (!entry->path)
11814 goto error;
11815
11816 find_data_to_file_info_w(dataW, &file_info, &reparse_tag);
11817 _Py_attribute_data_to_stat(&file_info, reparse_tag, &entry->win32_lstat);
11818
11819 return (PyObject *)entry;
11820
11821error:
11822 Py_DECREF(entry);
11823 return NULL;
11824}
11825
11826#else /* POSIX */
11827
11828static char *
11829join_path_filename(char *path_narrow, char* filename, Py_ssize_t filename_len)
11830{
11831 Py_ssize_t path_len;
11832 Py_ssize_t size;
11833 char *result;
11834
11835 if (!path_narrow) { /* Default arg: "." */
11836 path_narrow = ".";
11837 path_len = 1;
11838 }
11839 else {
11840 path_len = strlen(path_narrow);
11841 }
11842
11843 if (filename_len == -1)
11844 filename_len = strlen(filename);
11845
11846 /* The +1's are for the path separator and the NUL */
11847 size = path_len + 1 + filename_len + 1;
11848 result = PyMem_New(char, size);
11849 if (!result) {
11850 PyErr_NoMemory();
11851 return NULL;
11852 }
11853 strcpy(result, path_narrow);
11854 if (path_len > 0 && result[path_len - 1] != '/')
11855 result[path_len++] = '/';
11856 strcpy(result + path_len, filename);
11857 return result;
11858}
11859
11860static PyObject *
11861DirEntry_from_posix_info(path_t *path, char *name, Py_ssize_t name_len,
Victor Stinner35a97c02015-03-08 02:59:09 +010011862 ino_t d_ino
11863#ifdef HAVE_DIRENT_D_TYPE
11864 , unsigned char d_type
11865#endif
11866 )
Victor Stinner6036e442015-03-08 01:58:04 +010011867{
11868 DirEntry *entry;
11869 char *joined_path;
11870
11871 entry = PyObject_New(DirEntry, &DirEntryType);
11872 if (!entry)
11873 return NULL;
11874 entry->name = NULL;
11875 entry->path = NULL;
11876 entry->stat = NULL;
11877 entry->lstat = NULL;
11878
11879 joined_path = join_path_filename(path->narrow, name, name_len);
11880 if (!joined_path)
11881 goto error;
11882
11883 if (!path->narrow || !PyBytes_Check(path->object)) {
11884 entry->name = PyUnicode_DecodeFSDefaultAndSize(name, name_len);
11885 entry->path = PyUnicode_DecodeFSDefault(joined_path);
11886 }
11887 else {
11888 entry->name = PyBytes_FromStringAndSize(name, name_len);
11889 entry->path = PyBytes_FromString(joined_path);
11890 }
11891 PyMem_Free(joined_path);
11892 if (!entry->name || !entry->path)
11893 goto error;
11894
Victor Stinner35a97c02015-03-08 02:59:09 +010011895#ifdef HAVE_DIRENT_D_TYPE
Victor Stinner6036e442015-03-08 01:58:04 +010011896 entry->d_type = d_type;
Victor Stinner35a97c02015-03-08 02:59:09 +010011897#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011898 entry->d_ino = d_ino;
11899
11900 return (PyObject *)entry;
11901
11902error:
11903 Py_XDECREF(entry);
11904 return NULL;
11905}
11906
11907#endif
11908
11909
11910typedef struct {
11911 PyObject_HEAD
11912 path_t path;
11913#ifdef MS_WINDOWS
11914 HANDLE handle;
11915 WIN32_FIND_DATAW file_data;
11916 int first_time;
11917#else /* POSIX */
11918 DIR *dirp;
11919#endif
11920} ScandirIterator;
11921
11922#ifdef MS_WINDOWS
11923
11924static void
11925ScandirIterator_close(ScandirIterator *iterator)
11926{
11927 if (iterator->handle == INVALID_HANDLE_VALUE)
11928 return;
11929
11930 Py_BEGIN_ALLOW_THREADS
11931 FindClose(iterator->handle);
11932 Py_END_ALLOW_THREADS
11933 iterator->handle = INVALID_HANDLE_VALUE;
11934}
11935
11936static PyObject *
11937ScandirIterator_iternext(ScandirIterator *iterator)
11938{
11939 WIN32_FIND_DATAW *file_data = &iterator->file_data;
11940 BOOL success;
11941
11942 /* Happens if the iterator is iterated twice */
11943 if (iterator->handle == INVALID_HANDLE_VALUE) {
11944 PyErr_SetNone(PyExc_StopIteration);
11945 return NULL;
11946 }
11947
11948 while (1) {
11949 if (!iterator->first_time) {
11950 Py_BEGIN_ALLOW_THREADS
11951 success = FindNextFileW(iterator->handle, file_data);
11952 Py_END_ALLOW_THREADS
11953 if (!success) {
11954 if (GetLastError() != ERROR_NO_MORE_FILES)
11955 return path_error(&iterator->path);
11956 /* No more files found in directory, stop iterating */
11957 break;
11958 }
11959 }
11960 iterator->first_time = 0;
11961
11962 /* Skip over . and .. */
11963 if (wcscmp(file_data->cFileName, L".") != 0 &&
11964 wcscmp(file_data->cFileName, L"..") != 0)
11965 return DirEntry_from_find_data(&iterator->path, file_data);
11966
11967 /* Loop till we get a non-dot directory or finish iterating */
11968 }
11969
11970 ScandirIterator_close(iterator);
11971
11972 PyErr_SetNone(PyExc_StopIteration);
11973 return NULL;
11974}
11975
11976#else /* POSIX */
11977
11978static void
11979ScandirIterator_close(ScandirIterator *iterator)
11980{
11981 if (!iterator->dirp)
11982 return;
11983
11984 Py_BEGIN_ALLOW_THREADS
11985 closedir(iterator->dirp);
11986 Py_END_ALLOW_THREADS
11987 iterator->dirp = NULL;
11988 return;
11989}
11990
11991static PyObject *
11992ScandirIterator_iternext(ScandirIterator *iterator)
11993{
11994 struct dirent *direntp;
11995 Py_ssize_t name_len;
11996 int is_dot;
Victor Stinner6036e442015-03-08 01:58:04 +010011997
11998 /* Happens if the iterator is iterated twice */
11999 if (!iterator->dirp) {
12000 PyErr_SetNone(PyExc_StopIteration);
12001 return NULL;
12002 }
12003
12004 while (1) {
12005 errno = 0;
12006 Py_BEGIN_ALLOW_THREADS
12007 direntp = readdir(iterator->dirp);
12008 Py_END_ALLOW_THREADS
12009
12010 if (!direntp) {
12011 if (errno != 0)
12012 return path_error(&iterator->path);
12013 /* No more files found in directory, stop iterating */
12014 break;
12015 }
12016
12017 /* Skip over . and .. */
12018 name_len = NAMLEN(direntp);
12019 is_dot = direntp->d_name[0] == '.' &&
12020 (name_len == 1 || (direntp->d_name[1] == '.' && name_len == 2));
12021 if (!is_dot) {
Victor Stinner6036e442015-03-08 01:58:04 +010012022 return DirEntry_from_posix_info(&iterator->path, direntp->d_name,
Victor Stinner35a97c02015-03-08 02:59:09 +010012023 name_len, direntp->d_ino
12024#ifdef HAVE_DIRENT_D_TYPE
12025 , direntp->d_type
12026#endif
12027 );
Victor Stinner6036e442015-03-08 01:58:04 +010012028 }
12029
12030 /* Loop till we get a non-dot directory or finish iterating */
12031 }
12032
12033 ScandirIterator_close(iterator);
12034
12035 PyErr_SetNone(PyExc_StopIteration);
12036 return NULL;
12037}
12038
12039#endif
12040
12041static void
12042ScandirIterator_dealloc(ScandirIterator *iterator)
12043{
12044 ScandirIterator_close(iterator);
12045 Py_XDECREF(iterator->path.object);
12046 path_cleanup(&iterator->path);
12047 Py_TYPE(iterator)->tp_free((PyObject *)iterator);
12048}
12049
Benjamin Peterson5646de42015-04-12 17:56:34 -040012050static PyTypeObject ScandirIteratorType = {
Victor Stinner6036e442015-03-08 01:58:04 +010012051 PyVarObject_HEAD_INIT(NULL, 0)
12052 MODNAME ".ScandirIterator", /* tp_name */
12053 sizeof(ScandirIterator), /* tp_basicsize */
12054 0, /* tp_itemsize */
12055 /* methods */
12056 (destructor)ScandirIterator_dealloc, /* tp_dealloc */
12057 0, /* tp_print */
12058 0, /* tp_getattr */
12059 0, /* tp_setattr */
12060 0, /* tp_compare */
12061 0, /* tp_repr */
12062 0, /* tp_as_number */
12063 0, /* tp_as_sequence */
12064 0, /* tp_as_mapping */
12065 0, /* tp_hash */
12066 0, /* tp_call */
12067 0, /* tp_str */
12068 0, /* tp_getattro */
12069 0, /* tp_setattro */
12070 0, /* tp_as_buffer */
12071 Py_TPFLAGS_DEFAULT, /* tp_flags */
12072 0, /* tp_doc */
12073 0, /* tp_traverse */
12074 0, /* tp_clear */
12075 0, /* tp_richcompare */
12076 0, /* tp_weaklistoffset */
12077 PyObject_SelfIter, /* tp_iter */
12078 (iternextfunc)ScandirIterator_iternext, /* tp_iternext */
12079};
12080
12081static PyObject *
12082posix_scandir(PyObject *self, PyObject *args, PyObject *kwargs)
12083{
12084 ScandirIterator *iterator;
12085 static char *keywords[] = {"path", NULL};
12086#ifdef MS_WINDOWS
12087 wchar_t *path_strW;
12088#else
12089 char *path;
12090#endif
12091
12092 iterator = PyObject_New(ScandirIterator, &ScandirIteratorType);
12093 if (!iterator)
12094 return NULL;
12095 memset(&iterator->path, 0, sizeof(path_t));
12096 iterator->path.function_name = "scandir";
12097 iterator->path.nullable = 1;
12098
12099#ifdef MS_WINDOWS
12100 iterator->handle = INVALID_HANDLE_VALUE;
12101#else
12102 iterator->dirp = NULL;
12103#endif
12104
12105 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O&:scandir", keywords,
12106 path_converter, &iterator->path))
12107 goto error;
12108
12109 /* path_converter doesn't keep path.object around, so do it
12110 manually for the lifetime of the iterator here (the refcount
12111 is decremented in ScandirIterator_dealloc)
12112 */
12113 Py_XINCREF(iterator->path.object);
12114
12115#ifdef MS_WINDOWS
12116 if (iterator->path.narrow) {
12117 PyErr_SetString(PyExc_TypeError,
12118 "os.scandir() doesn't support bytes path on Windows, use Unicode instead");
12119 goto error;
12120 }
12121 iterator->first_time = 1;
12122
12123 path_strW = join_path_filenameW(iterator->path.wide, L"*.*");
12124 if (!path_strW)
12125 goto error;
12126
12127 Py_BEGIN_ALLOW_THREADS
12128 iterator->handle = FindFirstFileW(path_strW, &iterator->file_data);
12129 Py_END_ALLOW_THREADS
12130
12131 PyMem_Free(path_strW);
12132
12133 if (iterator->handle == INVALID_HANDLE_VALUE) {
12134 path_error(&iterator->path);
12135 goto error;
12136 }
12137#else /* POSIX */
12138 if (iterator->path.narrow)
12139 path = iterator->path.narrow;
12140 else
12141 path = ".";
12142
12143 errno = 0;
12144 Py_BEGIN_ALLOW_THREADS
12145 iterator->dirp = opendir(path);
12146 Py_END_ALLOW_THREADS
12147
12148 if (!iterator->dirp) {
12149 path_error(&iterator->path);
12150 goto error;
12151 }
12152#endif
12153
12154 return (PyObject *)iterator;
12155
12156error:
12157 Py_DECREF(iterator);
12158 return NULL;
12159}
12160
12161
Serhiy Storchakaa4c6bad2015-04-04 23:35:52 +030012162#include "clinic/posixmodule.c.h"
12163
Larry Hastings7726ac92014-01-31 22:03:12 -080012164/*[clinic input]
12165dump buffer
12166[clinic start generated code]*/
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030012167/*[clinic end generated code: output=da39a3ee5e6b4b0d input=524ce2e021e4eba6]*/
Larry Hastings7726ac92014-01-31 22:03:12 -080012168
Larry Hastings31826802013-10-19 00:09:25 -070012169
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012170static PyMethodDef posix_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -070012171
12172 OS_STAT_METHODDEF
12173 OS_ACCESS_METHODDEF
12174 OS_TTYNAME_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100012175 OS_CHDIR_METHODDEF
12176 OS_CHFLAGS_METHODDEF
12177 OS_CHMOD_METHODDEF
12178 OS_FCHMOD_METHODDEF
12179 OS_LCHMOD_METHODDEF
12180 OS_CHOWN_METHODDEF
12181 OS_FCHOWN_METHODDEF
12182 OS_LCHOWN_METHODDEF
12183 OS_LCHFLAGS_METHODDEF
12184 OS_CHROOT_METHODDEF
12185 OS_CTERMID_METHODDEF
12186 OS_GETCWD_METHODDEF
12187 OS_GETCWDB_METHODDEF
12188 OS_LINK_METHODDEF
12189 OS_LISTDIR_METHODDEF
12190 OS_LSTAT_METHODDEF
12191 OS_MKDIR_METHODDEF
12192 OS_NICE_METHODDEF
12193 OS_GETPRIORITY_METHODDEF
12194 OS_SETPRIORITY_METHODDEF
Guido van Rossumb6775db1994-08-01 11:34:53 +000012195#ifdef HAVE_READLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070012196 {"readlink", (PyCFunction)posix_readlink,
12197 METH_VARARGS | METH_KEYWORDS,
12198 readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000012199#endif /* HAVE_READLINK */
Brian Curtind40e6f72010-07-08 21:39:08 +000012200#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
Larry Hastings9cf065c2012-06-22 16:30:09 -070012201 {"readlink", (PyCFunction)win_readlink,
12202 METH_VARARGS | METH_KEYWORDS,
12203 readlink__doc__},
Brian Curtind40e6f72010-07-08 21:39:08 +000012204#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
Larry Hastings2f936352014-08-05 14:04:04 +100012205 OS_RENAME_METHODDEF
12206 OS_REPLACE_METHODDEF
12207 OS_RMDIR_METHODDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000012208 {"stat_float_times", stat_float_times, METH_VARARGS, stat_float_times__doc__},
Larry Hastings2f936352014-08-05 14:04:04 +100012209 OS_SYMLINK_METHODDEF
12210 OS_SYSTEM_METHODDEF
12211 OS_UMASK_METHODDEF
12212 OS_UNAME_METHODDEF
12213 OS_UNLINK_METHODDEF
12214 OS_REMOVE_METHODDEF
12215 OS_UTIME_METHODDEF
12216 OS_TIMES_METHODDEF
12217 OS__EXIT_METHODDEF
12218 OS_EXECV_METHODDEF
12219 OS_EXECVE_METHODDEF
12220 OS_SPAWNV_METHODDEF
12221 OS_SPAWNVE_METHODDEF
12222 OS_FORK1_METHODDEF
12223 OS_FORK_METHODDEF
12224 OS_SCHED_GET_PRIORITY_MAX_METHODDEF
12225 OS_SCHED_GET_PRIORITY_MIN_METHODDEF
12226 OS_SCHED_GETPARAM_METHODDEF
12227 OS_SCHED_GETSCHEDULER_METHODDEF
12228 OS_SCHED_RR_GET_INTERVAL_METHODDEF
12229 OS_SCHED_SETPARAM_METHODDEF
12230 OS_SCHED_SETSCHEDULER_METHODDEF
12231 OS_SCHED_YIELD_METHODDEF
12232 OS_SCHED_SETAFFINITY_METHODDEF
12233 OS_SCHED_GETAFFINITY_METHODDEF
12234 OS_OPENPTY_METHODDEF
12235 OS_FORKPTY_METHODDEF
12236 OS_GETEGID_METHODDEF
12237 OS_GETEUID_METHODDEF
12238 OS_GETGID_METHODDEF
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +020012239#ifdef HAVE_GETGROUPLIST
12240 {"getgrouplist", posix_getgrouplist, METH_VARARGS, posix_getgrouplist__doc__},
12241#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012242 OS_GETGROUPS_METHODDEF
12243 OS_GETPID_METHODDEF
12244 OS_GETPGRP_METHODDEF
12245 OS_GETPPID_METHODDEF
12246 OS_GETUID_METHODDEF
12247 OS_GETLOGIN_METHODDEF
12248 OS_KILL_METHODDEF
12249 OS_KILLPG_METHODDEF
12250 OS_PLOCK_METHODDEF
Thomas Heller8b7a9572007-08-31 06:44:36 +000012251#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000012252 {"startfile", win32_startfile, METH_VARARGS, win32_startfile__doc__},
Thomas Heller8b7a9572007-08-31 06:44:36 +000012253#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012254 OS_SETUID_METHODDEF
12255 OS_SETEUID_METHODDEF
12256 OS_SETREUID_METHODDEF
12257 OS_SETGID_METHODDEF
12258 OS_SETEGID_METHODDEF
12259 OS_SETREGID_METHODDEF
12260 OS_SETGROUPS_METHODDEF
Antoine Pitroub7572f02009-12-02 20:46:48 +000012261#ifdef HAVE_INITGROUPS
Victor Stinner8c62be82010-05-06 00:08:46 +000012262 {"initgroups", posix_initgroups, METH_VARARGS, posix_initgroups__doc__},
Antoine Pitroub7572f02009-12-02 20:46:48 +000012263#endif /* HAVE_INITGROUPS */
Larry Hastings2f936352014-08-05 14:04:04 +100012264 OS_GETPGID_METHODDEF
12265 OS_SETPGRP_METHODDEF
12266 OS_WAIT_METHODDEF
12267 OS_WAIT3_METHODDEF
12268 OS_WAIT4_METHODDEF
12269 OS_WAITID_METHODDEF
12270 OS_WAITPID_METHODDEF
12271 OS_GETSID_METHODDEF
12272 OS_SETSID_METHODDEF
12273 OS_SETPGID_METHODDEF
12274 OS_TCGETPGRP_METHODDEF
12275 OS_TCSETPGRP_METHODDEF
12276 OS_OPEN_METHODDEF
12277 OS_CLOSE_METHODDEF
12278 OS_CLOSERANGE_METHODDEF
12279 OS_DEVICE_ENCODING_METHODDEF
12280 OS_DUP_METHODDEF
12281 OS_DUP2_METHODDEF
12282 OS_LOCKF_METHODDEF
12283 OS_LSEEK_METHODDEF
12284 OS_READ_METHODDEF
12285 OS_READV_METHODDEF
12286 OS_PREAD_METHODDEF
12287 OS_WRITE_METHODDEF
12288 OS_WRITEV_METHODDEF
12289 OS_PWRITE_METHODDEF
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012290#ifdef HAVE_SENDFILE
12291 {"sendfile", (PyCFunction)posix_sendfile, METH_VARARGS | METH_KEYWORDS,
12292 posix_sendfile__doc__},
12293#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012294 OS_FSTAT_METHODDEF
12295 OS_ISATTY_METHODDEF
12296 OS_PIPE_METHODDEF
12297 OS_PIPE2_METHODDEF
12298 OS_MKFIFO_METHODDEF
12299 OS_MKNOD_METHODDEF
12300 OS_MAJOR_METHODDEF
12301 OS_MINOR_METHODDEF
12302 OS_MAKEDEV_METHODDEF
12303 OS_FTRUNCATE_METHODDEF
12304 OS_TRUNCATE_METHODDEF
12305 OS_POSIX_FALLOCATE_METHODDEF
12306 OS_POSIX_FADVISE_METHODDEF
12307 OS_PUTENV_METHODDEF
12308 OS_UNSETENV_METHODDEF
12309 OS_STRERROR_METHODDEF
12310 OS_FCHDIR_METHODDEF
12311 OS_FSYNC_METHODDEF
12312 OS_SYNC_METHODDEF
12313 OS_FDATASYNC_METHODDEF
12314 OS_WCOREDUMP_METHODDEF
12315 OS_WIFCONTINUED_METHODDEF
12316 OS_WIFSTOPPED_METHODDEF
12317 OS_WIFSIGNALED_METHODDEF
12318 OS_WIFEXITED_METHODDEF
12319 OS_WEXITSTATUS_METHODDEF
12320 OS_WTERMSIG_METHODDEF
12321 OS_WSTOPSIG_METHODDEF
12322 OS_FSTATVFS_METHODDEF
12323 OS_STATVFS_METHODDEF
12324 OS_CONFSTR_METHODDEF
12325 OS_SYSCONF_METHODDEF
12326 OS_FPATHCONF_METHODDEF
12327 OS_PATHCONF_METHODDEF
12328 OS_ABORT_METHODDEF
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000012329#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000012330 {"_getfullpathname", posix__getfullpathname, METH_VARARGS, NULL},
Brian Curtin95d028f2011-06-09 09:10:38 -050012331 {"_isdir", posix__isdir, METH_VARARGS, posix__isdir__doc__},
Mark Hammondef8b6542001-05-13 08:04:26 +000012332#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012333 OS__GETDISKUSAGE_METHODDEF
12334 OS__GETFINALPATHNAME_METHODDEF
12335 OS__GETVOLUMEPATHNAME_METHODDEF
12336 OS_GETLOADAVG_METHODDEF
12337 OS_URANDOM_METHODDEF
12338 OS_SETRESUID_METHODDEF
12339 OS_SETRESGID_METHODDEF
12340 OS_GETRESUID_METHODDEF
12341 OS_GETRESGID_METHODDEF
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000012342
Larry Hastings2f936352014-08-05 14:04:04 +100012343 OS_GETXATTR_METHODDEF
12344 OS_SETXATTR_METHODDEF
12345 OS_REMOVEXATTR_METHODDEF
12346 OS_LISTXATTR_METHODDEF
12347
Antoine Pitroubcf2b592012-02-08 23:28:36 +010012348#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
12349 {"get_terminal_size", get_terminal_size, METH_VARARGS, termsize__doc__},
12350#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012351 OS_CPU_COUNT_METHODDEF
12352 OS_GET_INHERITABLE_METHODDEF
12353 OS_SET_INHERITABLE_METHODDEF
12354 OS_GET_HANDLE_INHERITABLE_METHODDEF
12355 OS_SET_HANDLE_INHERITABLE_METHODDEF
Victor Stinner1db9e7b2014-07-29 22:32:47 +020012356#ifndef MS_WINDOWS
12357 {"get_blocking", posix_get_blocking, METH_VARARGS, get_blocking__doc__},
12358 {"set_blocking", posix_set_blocking, METH_VARARGS, set_blocking__doc__},
12359#endif
Victor Stinner6036e442015-03-08 01:58:04 +010012360 {"scandir", (PyCFunction)posix_scandir,
12361 METH_VARARGS | METH_KEYWORDS,
12362 posix_scandir__doc__},
Victor Stinner8c62be82010-05-06 00:08:46 +000012363 {NULL, NULL} /* Sentinel */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000012364};
12365
12366
Brian Curtin52173d42010-12-02 18:29:18 +000012367#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000012368static int
Brian Curtin52173d42010-12-02 18:29:18 +000012369enable_symlink()
12370{
12371 HANDLE tok;
12372 TOKEN_PRIVILEGES tok_priv;
12373 LUID luid;
12374 int meth_idx = 0;
12375
12376 if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &tok))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012377 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012378
12379 if (!LookupPrivilegeValue(NULL, SE_CREATE_SYMBOLIC_LINK_NAME, &luid))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012380 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012381
12382 tok_priv.PrivilegeCount = 1;
12383 tok_priv.Privileges[0].Luid = luid;
12384 tok_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
12385
12386 if (!AdjustTokenPrivileges(tok, FALSE, &tok_priv,
12387 sizeof(TOKEN_PRIVILEGES),
12388 (PTOKEN_PRIVILEGES) NULL, (PDWORD) NULL))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012389 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012390
Brian Curtin3b4499c2010-12-28 14:31:47 +000012391 /* ERROR_NOT_ALL_ASSIGNED returned when the privilege can't be assigned. */
12392 return GetLastError() == ERROR_NOT_ALL_ASSIGNED ? 0 : 1;
Brian Curtin52173d42010-12-02 18:29:18 +000012393}
12394#endif /* defined(HAVE_SYMLINK) && defined(MS_WINDOWS) */
12395
Barry Warsaw4a342091996-12-19 23:50:02 +000012396static int
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012397all_ins(PyObject *m)
Barry Warsaw4a342091996-12-19 23:50:02 +000012398{
Guido van Rossum94f6f721999-01-06 18:42:14 +000012399#ifdef F_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012400 if (PyModule_AddIntMacro(m, F_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012401#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012402#ifdef R_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012403 if (PyModule_AddIntMacro(m, R_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012404#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012405#ifdef W_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012406 if (PyModule_AddIntMacro(m, W_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012407#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012408#ifdef X_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012409 if (PyModule_AddIntMacro(m, X_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012410#endif
Fred Drakec9680921999-12-13 16:37:25 +000012411#ifdef NGROUPS_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012412 if (PyModule_AddIntMacro(m, NGROUPS_MAX)) return -1;
Fred Drakec9680921999-12-13 16:37:25 +000012413#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012414#ifdef TMP_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012415 if (PyModule_AddIntMacro(m, TMP_MAX)) return -1;
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012416#endif
Fred Drake106c1a02002-04-23 15:58:02 +000012417#ifdef WCONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012418 if (PyModule_AddIntMacro(m, WCONTINUED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000012419#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000012420#ifdef WNOHANG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012421 if (PyModule_AddIntMacro(m, WNOHANG)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012422#endif
Fred Drake106c1a02002-04-23 15:58:02 +000012423#ifdef WUNTRACED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012424 if (PyModule_AddIntMacro(m, WUNTRACED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000012425#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000012426#ifdef O_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012427 if (PyModule_AddIntMacro(m, O_RDONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012428#endif
12429#ifdef O_WRONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012430 if (PyModule_AddIntMacro(m, O_WRONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012431#endif
12432#ifdef O_RDWR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012433 if (PyModule_AddIntMacro(m, O_RDWR)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012434#endif
12435#ifdef O_NDELAY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012436 if (PyModule_AddIntMacro(m, O_NDELAY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012437#endif
12438#ifdef O_NONBLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012439 if (PyModule_AddIntMacro(m, O_NONBLOCK)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012440#endif
12441#ifdef O_APPEND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012442 if (PyModule_AddIntMacro(m, O_APPEND)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012443#endif
12444#ifdef O_DSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012445 if (PyModule_AddIntMacro(m, O_DSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012446#endif
12447#ifdef O_RSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012448 if (PyModule_AddIntMacro(m, O_RSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012449#endif
12450#ifdef O_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012451 if (PyModule_AddIntMacro(m, O_SYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012452#endif
12453#ifdef O_NOCTTY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012454 if (PyModule_AddIntMacro(m, O_NOCTTY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012455#endif
12456#ifdef O_CREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012457 if (PyModule_AddIntMacro(m, O_CREAT)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012458#endif
12459#ifdef O_EXCL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012460 if (PyModule_AddIntMacro(m, O_EXCL)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012461#endif
12462#ifdef O_TRUNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012463 if (PyModule_AddIntMacro(m, O_TRUNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012464#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +000012465#ifdef O_BINARY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012466 if (PyModule_AddIntMacro(m, O_BINARY)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000012467#endif
12468#ifdef O_TEXT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012469 if (PyModule_AddIntMacro(m, O_TEXT)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000012470#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012471#ifdef O_XATTR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012472 if (PyModule_AddIntMacro(m, O_XATTR)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012473#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012474#ifdef O_LARGEFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012475 if (PyModule_AddIntMacro(m, O_LARGEFILE)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012476#endif
Skip Montanaro5ff14922005-05-16 02:42:22 +000012477#ifdef O_SHLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012478 if (PyModule_AddIntMacro(m, O_SHLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000012479#endif
12480#ifdef O_EXLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012481 if (PyModule_AddIntMacro(m, O_EXLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000012482#endif
Jesus Ceacf381202012-04-24 20:44:40 +020012483#ifdef O_EXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012484 if (PyModule_AddIntMacro(m, O_EXEC)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012485#endif
12486#ifdef O_SEARCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012487 if (PyModule_AddIntMacro(m, O_SEARCH)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012488#endif
Benjamin Peterson3b965a22013-03-13 10:27:41 -050012489#ifdef O_PATH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012490 if (PyModule_AddIntMacro(m, O_PATH)) return -1;
Benjamin Peterson3b965a22013-03-13 10:27:41 -050012491#endif
Jesus Ceacf381202012-04-24 20:44:40 +020012492#ifdef O_TTY_INIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012493 if (PyModule_AddIntMacro(m, O_TTY_INIT)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012494#endif
Christian Heimes177b3f92013-08-16 14:35:09 +020012495#ifdef O_TMPFILE
12496 if (PyModule_AddIntMacro(m, O_TMPFILE)) return -1;
12497#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012498#ifdef PRIO_PROCESS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012499 if (PyModule_AddIntMacro(m, PRIO_PROCESS)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012500#endif
12501#ifdef PRIO_PGRP
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012502 if (PyModule_AddIntMacro(m, PRIO_PGRP)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012503#endif
12504#ifdef PRIO_USER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012505 if (PyModule_AddIntMacro(m, PRIO_USER)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012506#endif
Charles-François Natali1e045b12011-05-22 20:42:32 +020012507#ifdef O_CLOEXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012508 if (PyModule_AddIntMacro(m, O_CLOEXEC)) return -1;
Charles-François Natali1e045b12011-05-22 20:42:32 +020012509#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012510#ifdef O_ACCMODE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012511 if (PyModule_AddIntMacro(m, O_ACCMODE)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012512#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012513
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012514
Jesus Cea94363612012-06-22 18:32:07 +020012515#ifdef SEEK_HOLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012516 if (PyModule_AddIntMacro(m, SEEK_HOLE)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020012517#endif
12518#ifdef SEEK_DATA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012519 if (PyModule_AddIntMacro(m, SEEK_DATA)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020012520#endif
12521
Tim Peters5aa91602002-01-30 05:46:57 +000012522/* MS Windows */
12523#ifdef O_NOINHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000012524 /* Don't inherit in child processes. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012525 if (PyModule_AddIntMacro(m, O_NOINHERIT)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012526#endif
12527#ifdef _O_SHORT_LIVED
Victor Stinner8c62be82010-05-06 00:08:46 +000012528 /* Optimize for short life (keep in memory). */
12529 /* MS forgot to define this one with a non-underscore form too. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012530 if (PyModule_AddIntConstant(m, "O_SHORT_LIVED", _O_SHORT_LIVED)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012531#endif
12532#ifdef O_TEMPORARY
Victor Stinner8c62be82010-05-06 00:08:46 +000012533 /* Automatically delete when last handle is closed. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012534 if (PyModule_AddIntMacro(m, O_TEMPORARY)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012535#endif
12536#ifdef O_RANDOM
Victor Stinner8c62be82010-05-06 00:08:46 +000012537 /* Optimize for random access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012538 if (PyModule_AddIntMacro(m, O_RANDOM)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012539#endif
12540#ifdef O_SEQUENTIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000012541 /* Optimize for sequential access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012542 if (PyModule_AddIntMacro(m, O_SEQUENTIAL)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012543#endif
12544
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012545/* GNU extensions. */
Alexandre Vassalottibee32532008-05-16 18:15:12 +000012546#ifdef O_ASYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000012547 /* Send a SIGIO signal whenever input or output
12548 becomes available on file descriptor */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012549 if (PyModule_AddIntMacro(m, O_ASYNC)) return -1;
Alexandre Vassalottibee32532008-05-16 18:15:12 +000012550#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012551#ifdef O_DIRECT
Victor Stinner8c62be82010-05-06 00:08:46 +000012552 /* Direct disk access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012553 if (PyModule_AddIntMacro(m, O_DIRECT)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012554#endif
12555#ifdef O_DIRECTORY
Victor Stinner8c62be82010-05-06 00:08:46 +000012556 /* Must be a directory. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012557 if (PyModule_AddIntMacro(m, O_DIRECTORY)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012558#endif
12559#ifdef O_NOFOLLOW
Victor Stinner8c62be82010-05-06 00:08:46 +000012560 /* Do not follow links. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012561 if (PyModule_AddIntMacro(m, O_NOFOLLOW)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012562#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012563#ifdef O_NOLINKS
12564 /* Fails if link count of the named file is greater than 1 */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012565 if (PyModule_AddIntMacro(m, O_NOLINKS)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012566#endif
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000012567#ifdef O_NOATIME
Victor Stinner8c62be82010-05-06 00:08:46 +000012568 /* Do not update the access time. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012569 if (PyModule_AddIntMacro(m, O_NOATIME)) return -1;
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000012570#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +000012571
Victor Stinner8c62be82010-05-06 00:08:46 +000012572 /* These come from sysexits.h */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012573#ifdef EX_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012574 if (PyModule_AddIntMacro(m, EX_OK)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012575#endif /* EX_OK */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012576#ifdef EX_USAGE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012577 if (PyModule_AddIntMacro(m, EX_USAGE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012578#endif /* EX_USAGE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012579#ifdef EX_DATAERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012580 if (PyModule_AddIntMacro(m, EX_DATAERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012581#endif /* EX_DATAERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012582#ifdef EX_NOINPUT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012583 if (PyModule_AddIntMacro(m, EX_NOINPUT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012584#endif /* EX_NOINPUT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012585#ifdef EX_NOUSER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012586 if (PyModule_AddIntMacro(m, EX_NOUSER)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012587#endif /* EX_NOUSER */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012588#ifdef EX_NOHOST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012589 if (PyModule_AddIntMacro(m, EX_NOHOST)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012590#endif /* EX_NOHOST */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012591#ifdef EX_UNAVAILABLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012592 if (PyModule_AddIntMacro(m, EX_UNAVAILABLE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012593#endif /* EX_UNAVAILABLE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012594#ifdef EX_SOFTWARE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012595 if (PyModule_AddIntMacro(m, EX_SOFTWARE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012596#endif /* EX_SOFTWARE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012597#ifdef EX_OSERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012598 if (PyModule_AddIntMacro(m, EX_OSERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012599#endif /* EX_OSERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012600#ifdef EX_OSFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012601 if (PyModule_AddIntMacro(m, EX_OSFILE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012602#endif /* EX_OSFILE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012603#ifdef EX_CANTCREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012604 if (PyModule_AddIntMacro(m, EX_CANTCREAT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012605#endif /* EX_CANTCREAT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012606#ifdef EX_IOERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012607 if (PyModule_AddIntMacro(m, EX_IOERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012608#endif /* EX_IOERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012609#ifdef EX_TEMPFAIL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012610 if (PyModule_AddIntMacro(m, EX_TEMPFAIL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012611#endif /* EX_TEMPFAIL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012612#ifdef EX_PROTOCOL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012613 if (PyModule_AddIntMacro(m, EX_PROTOCOL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012614#endif /* EX_PROTOCOL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012615#ifdef EX_NOPERM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012616 if (PyModule_AddIntMacro(m, EX_NOPERM)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012617#endif /* EX_NOPERM */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012618#ifdef EX_CONFIG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012619 if (PyModule_AddIntMacro(m, EX_CONFIG)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012620#endif /* EX_CONFIG */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012621#ifdef EX_NOTFOUND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012622 if (PyModule_AddIntMacro(m, EX_NOTFOUND)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012623#endif /* EX_NOTFOUND */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012624
Amaury Forgeot d'Arc66d00ad2010-09-10 18:11:45 +000012625 /* statvfs */
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012626#ifdef ST_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012627 if (PyModule_AddIntMacro(m, ST_RDONLY)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012628#endif /* ST_RDONLY */
12629#ifdef ST_NOSUID
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012630 if (PyModule_AddIntMacro(m, ST_NOSUID)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012631#endif /* ST_NOSUID */
12632
doko@ubuntu.comca616a22013-12-08 15:23:07 +010012633 /* GNU extensions */
12634#ifdef ST_NODEV
12635 if (PyModule_AddIntMacro(m, ST_NODEV)) return -1;
12636#endif /* ST_NODEV */
12637#ifdef ST_NOEXEC
12638 if (PyModule_AddIntMacro(m, ST_NOEXEC)) return -1;
12639#endif /* ST_NOEXEC */
12640#ifdef ST_SYNCHRONOUS
12641 if (PyModule_AddIntMacro(m, ST_SYNCHRONOUS)) return -1;
12642#endif /* ST_SYNCHRONOUS */
12643#ifdef ST_MANDLOCK
12644 if (PyModule_AddIntMacro(m, ST_MANDLOCK)) return -1;
12645#endif /* ST_MANDLOCK */
12646#ifdef ST_WRITE
12647 if (PyModule_AddIntMacro(m, ST_WRITE)) return -1;
12648#endif /* ST_WRITE */
12649#ifdef ST_APPEND
12650 if (PyModule_AddIntMacro(m, ST_APPEND)) return -1;
12651#endif /* ST_APPEND */
12652#ifdef ST_NOATIME
12653 if (PyModule_AddIntMacro(m, ST_NOATIME)) return -1;
12654#endif /* ST_NOATIME */
12655#ifdef ST_NODIRATIME
12656 if (PyModule_AddIntMacro(m, ST_NODIRATIME)) return -1;
12657#endif /* ST_NODIRATIME */
12658#ifdef ST_RELATIME
12659 if (PyModule_AddIntMacro(m, ST_RELATIME)) return -1;
12660#endif /* ST_RELATIME */
12661
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012662 /* FreeBSD sendfile() constants */
12663#ifdef SF_NODISKIO
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012664 if (PyModule_AddIntMacro(m, SF_NODISKIO)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012665#endif
12666#ifdef SF_MNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012667 if (PyModule_AddIntMacro(m, SF_MNOWAIT)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012668#endif
12669#ifdef SF_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012670 if (PyModule_AddIntMacro(m, SF_SYNC)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012671#endif
12672
Ross Lagerwall7807c352011-03-17 20:20:30 +020012673 /* constants for posix_fadvise */
12674#ifdef POSIX_FADV_NORMAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012675 if (PyModule_AddIntMacro(m, POSIX_FADV_NORMAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012676#endif
12677#ifdef POSIX_FADV_SEQUENTIAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012678 if (PyModule_AddIntMacro(m, POSIX_FADV_SEQUENTIAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012679#endif
12680#ifdef POSIX_FADV_RANDOM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012681 if (PyModule_AddIntMacro(m, POSIX_FADV_RANDOM)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012682#endif
12683#ifdef POSIX_FADV_NOREUSE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012684 if (PyModule_AddIntMacro(m, POSIX_FADV_NOREUSE)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012685#endif
12686#ifdef POSIX_FADV_WILLNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012687 if (PyModule_AddIntMacro(m, POSIX_FADV_WILLNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012688#endif
12689#ifdef POSIX_FADV_DONTNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012690 if (PyModule_AddIntMacro(m, POSIX_FADV_DONTNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012691#endif
12692
12693 /* constants for waitid */
12694#if defined(HAVE_SYS_WAIT_H) && defined(HAVE_WAITID)
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012695 if (PyModule_AddIntMacro(m, P_PID)) return -1;
12696 if (PyModule_AddIntMacro(m, P_PGID)) return -1;
12697 if (PyModule_AddIntMacro(m, P_ALL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012698#endif
12699#ifdef WEXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012700 if (PyModule_AddIntMacro(m, WEXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012701#endif
12702#ifdef WNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012703 if (PyModule_AddIntMacro(m, WNOWAIT)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012704#endif
12705#ifdef WSTOPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012706 if (PyModule_AddIntMacro(m, WSTOPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012707#endif
12708#ifdef CLD_EXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012709 if (PyModule_AddIntMacro(m, CLD_EXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012710#endif
12711#ifdef CLD_DUMPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012712 if (PyModule_AddIntMacro(m, CLD_DUMPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012713#endif
12714#ifdef CLD_TRAPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012715 if (PyModule_AddIntMacro(m, CLD_TRAPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012716#endif
12717#ifdef CLD_CONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012718 if (PyModule_AddIntMacro(m, CLD_CONTINUED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012719#endif
12720
12721 /* constants for lockf */
12722#ifdef F_LOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012723 if (PyModule_AddIntMacro(m, F_LOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012724#endif
12725#ifdef F_TLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012726 if (PyModule_AddIntMacro(m, F_TLOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012727#endif
12728#ifdef F_ULOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012729 if (PyModule_AddIntMacro(m, F_ULOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012730#endif
12731#ifdef F_TEST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012732 if (PyModule_AddIntMacro(m, F_TEST)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012733#endif
12734
Guido van Rossum246bc171999-02-01 23:54:31 +000012735#ifdef HAVE_SPAWNV
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012736 if (PyModule_AddIntConstant(m, "P_WAIT", _P_WAIT)) return -1;
12737 if (PyModule_AddIntConstant(m, "P_NOWAIT", _P_NOWAIT)) return -1;
12738 if (PyModule_AddIntConstant(m, "P_OVERLAY", _OLD_P_OVERLAY)) return -1;
12739 if (PyModule_AddIntConstant(m, "P_NOWAITO", _P_NOWAITO)) return -1;
12740 if (PyModule_AddIntConstant(m, "P_DETACH", _P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +000012741#endif
12742
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012743#ifdef HAVE_SCHED_H
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012744 if (PyModule_AddIntMacro(m, SCHED_OTHER)) return -1;
12745 if (PyModule_AddIntMacro(m, SCHED_FIFO)) return -1;
12746 if (PyModule_AddIntMacro(m, SCHED_RR)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012747#ifdef SCHED_SPORADIC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012748 if (PyModule_AddIntMacro(m, SCHED_SPORADIC) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012749#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012750#ifdef SCHED_BATCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012751 if (PyModule_AddIntMacro(m, SCHED_BATCH)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012752#endif
12753#ifdef SCHED_IDLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012754 if (PyModule_AddIntMacro(m, SCHED_IDLE)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012755#endif
12756#ifdef SCHED_RESET_ON_FORK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012757 if (PyModule_AddIntMacro(m, SCHED_RESET_ON_FORK)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012758#endif
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012759#ifdef SCHED_SYS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012760 if (PyModule_AddIntMacro(m, SCHED_SYS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012761#endif
12762#ifdef SCHED_IA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012763 if (PyModule_AddIntMacro(m, SCHED_IA)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012764#endif
12765#ifdef SCHED_FSS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012766 if (PyModule_AddIntMacro(m, SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012767#endif
12768#ifdef SCHED_FX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012769 if (PyModule_AddIntConstant(m, "SCHED_FX", SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012770#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012771#endif
12772
Benjamin Peterson9428d532011-09-14 11:45:52 -040012773#ifdef USE_XATTRS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012774 if (PyModule_AddIntMacro(m, XATTR_CREATE)) return -1;
12775 if (PyModule_AddIntMacro(m, XATTR_REPLACE)) return -1;
12776 if (PyModule_AddIntMacro(m, XATTR_SIZE_MAX)) return -1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040012777#endif
12778
Victor Stinner8b905bd2011-10-25 13:34:04 +020012779#ifdef RTLD_LAZY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012780 if (PyModule_AddIntMacro(m, RTLD_LAZY)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012781#endif
12782#ifdef RTLD_NOW
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012783 if (PyModule_AddIntMacro(m, RTLD_NOW)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012784#endif
12785#ifdef RTLD_GLOBAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012786 if (PyModule_AddIntMacro(m, RTLD_GLOBAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012787#endif
12788#ifdef RTLD_LOCAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012789 if (PyModule_AddIntMacro(m, RTLD_LOCAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012790#endif
12791#ifdef RTLD_NODELETE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012792 if (PyModule_AddIntMacro(m, RTLD_NODELETE)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012793#endif
12794#ifdef RTLD_NOLOAD
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012795 if (PyModule_AddIntMacro(m, RTLD_NOLOAD)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012796#endif
12797#ifdef RTLD_DEEPBIND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012798 if (PyModule_AddIntMacro(m, RTLD_DEEPBIND)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012799#endif
12800
Victor Stinner8c62be82010-05-06 00:08:46 +000012801 return 0;
Barry Warsaw4a342091996-12-19 23:50:02 +000012802}
12803
12804
Martin v. Löwis1a214512008-06-11 05:26:20 +000012805static struct PyModuleDef posixmodule = {
Victor Stinner8c62be82010-05-06 00:08:46 +000012806 PyModuleDef_HEAD_INIT,
12807 MODNAME,
12808 posix__doc__,
12809 -1,
12810 posix_methods,
12811 NULL,
12812 NULL,
12813 NULL,
12814 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +000012815};
12816
12817
Larry Hastings9cf065c2012-06-22 16:30:09 -070012818static char *have_functions[] = {
12819
12820#ifdef HAVE_FACCESSAT
12821 "HAVE_FACCESSAT",
12822#endif
12823
12824#ifdef HAVE_FCHDIR
12825 "HAVE_FCHDIR",
12826#endif
12827
12828#ifdef HAVE_FCHMOD
12829 "HAVE_FCHMOD",
12830#endif
12831
12832#ifdef HAVE_FCHMODAT
12833 "HAVE_FCHMODAT",
12834#endif
12835
12836#ifdef HAVE_FCHOWN
12837 "HAVE_FCHOWN",
12838#endif
12839
Larry Hastings00964ed2013-08-12 13:49:30 -040012840#ifdef HAVE_FCHOWNAT
12841 "HAVE_FCHOWNAT",
12842#endif
12843
Larry Hastings9cf065c2012-06-22 16:30:09 -070012844#ifdef HAVE_FEXECVE
12845 "HAVE_FEXECVE",
12846#endif
12847
12848#ifdef HAVE_FDOPENDIR
12849 "HAVE_FDOPENDIR",
12850#endif
12851
Georg Brandl306336b2012-06-24 12:55:33 +020012852#ifdef HAVE_FPATHCONF
12853 "HAVE_FPATHCONF",
12854#endif
12855
Larry Hastings9cf065c2012-06-22 16:30:09 -070012856#ifdef HAVE_FSTATAT
12857 "HAVE_FSTATAT",
12858#endif
12859
12860#ifdef HAVE_FSTATVFS
12861 "HAVE_FSTATVFS",
12862#endif
12863
Steve Dowerfe0a41a2015-03-20 19:50:46 -070012864#if defined HAVE_FTRUNCATE || defined MS_WINDOWS
Georg Brandl306336b2012-06-24 12:55:33 +020012865 "HAVE_FTRUNCATE",
12866#endif
12867
Larry Hastings9cf065c2012-06-22 16:30:09 -070012868#ifdef HAVE_FUTIMENS
12869 "HAVE_FUTIMENS",
12870#endif
12871
12872#ifdef HAVE_FUTIMES
12873 "HAVE_FUTIMES",
12874#endif
12875
12876#ifdef HAVE_FUTIMESAT
12877 "HAVE_FUTIMESAT",
12878#endif
12879
12880#ifdef HAVE_LINKAT
12881 "HAVE_LINKAT",
12882#endif
12883
12884#ifdef HAVE_LCHFLAGS
12885 "HAVE_LCHFLAGS",
12886#endif
12887
12888#ifdef HAVE_LCHMOD
12889 "HAVE_LCHMOD",
12890#endif
12891
12892#ifdef HAVE_LCHOWN
12893 "HAVE_LCHOWN",
12894#endif
12895
12896#ifdef HAVE_LSTAT
12897 "HAVE_LSTAT",
12898#endif
12899
12900#ifdef HAVE_LUTIMES
12901 "HAVE_LUTIMES",
12902#endif
12903
12904#ifdef HAVE_MKDIRAT
12905 "HAVE_MKDIRAT",
12906#endif
12907
12908#ifdef HAVE_MKFIFOAT
12909 "HAVE_MKFIFOAT",
12910#endif
12911
12912#ifdef HAVE_MKNODAT
12913 "HAVE_MKNODAT",
12914#endif
12915
12916#ifdef HAVE_OPENAT
12917 "HAVE_OPENAT",
12918#endif
12919
12920#ifdef HAVE_READLINKAT
12921 "HAVE_READLINKAT",
12922#endif
12923
12924#ifdef HAVE_RENAMEAT
12925 "HAVE_RENAMEAT",
12926#endif
12927
12928#ifdef HAVE_SYMLINKAT
12929 "HAVE_SYMLINKAT",
12930#endif
12931
12932#ifdef HAVE_UNLINKAT
12933 "HAVE_UNLINKAT",
12934#endif
12935
12936#ifdef HAVE_UTIMENSAT
12937 "HAVE_UTIMENSAT",
12938#endif
12939
12940#ifdef MS_WINDOWS
12941 "MS_WINDOWS",
12942#endif
12943
12944 NULL
12945};
12946
12947
Mark Hammondfe51c6d2002-08-02 02:27:13 +000012948PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +000012949INITFUNC(void)
Guido van Rossumb6775db1994-08-01 11:34:53 +000012950{
Victor Stinner8c62be82010-05-06 00:08:46 +000012951 PyObject *m, *v;
Larry Hastings9cf065c2012-06-22 16:30:09 -070012952 PyObject *list;
12953 char **trace;
Tim Peters5aa91602002-01-30 05:46:57 +000012954
Brian Curtin52173d42010-12-02 18:29:18 +000012955#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000012956 win32_can_symlink = enable_symlink();
Brian Curtin52173d42010-12-02 18:29:18 +000012957#endif
12958
Victor Stinner8c62be82010-05-06 00:08:46 +000012959 m = PyModule_Create(&posixmodule);
12960 if (m == NULL)
12961 return NULL;
Tim Peters5aa91602002-01-30 05:46:57 +000012962
Victor Stinner8c62be82010-05-06 00:08:46 +000012963 /* Initialize environ dictionary */
12964 v = convertenviron();
12965 Py_XINCREF(v);
12966 if (v == NULL || PyModule_AddObject(m, "environ", v) != 0)
12967 return NULL;
12968 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +000012969
Victor Stinner8c62be82010-05-06 00:08:46 +000012970 if (all_ins(m))
12971 return NULL;
Barry Warsaw4a342091996-12-19 23:50:02 +000012972
Victor Stinner8c62be82010-05-06 00:08:46 +000012973 if (setup_confname_tables(m))
12974 return NULL;
Fred Drakebec628d1999-12-15 18:31:10 +000012975
Victor Stinner8c62be82010-05-06 00:08:46 +000012976 Py_INCREF(PyExc_OSError);
12977 PyModule_AddObject(m, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +000012978
Guido van Rossumb3d39562000-01-31 18:41:26 +000012979#ifdef HAVE_PUTENV
Victor Stinner8c62be82010-05-06 00:08:46 +000012980 if (posix_putenv_garbage == NULL)
12981 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +000012982#endif
Guido van Rossum98bf58f2001-10-18 20:34:25 +000012983
Victor Stinner8c62be82010-05-06 00:08:46 +000012984 if (!initialized) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020012985#if defined(HAVE_WAITID) && !defined(__APPLE__)
12986 waitid_result_desc.name = MODNAME ".waitid_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020012987 if (PyStructSequence_InitType2(&WaitidResultType, &waitid_result_desc) < 0)
12988 return NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012989#endif
12990
Christian Heimes25827622013-10-12 01:27:08 +020012991 stat_result_desc.name = "os.stat_result"; /* see issue #19209 */
Victor Stinner8c62be82010-05-06 00:08:46 +000012992 stat_result_desc.fields[7].name = PyStructSequence_UnnamedField;
12993 stat_result_desc.fields[8].name = PyStructSequence_UnnamedField;
12994 stat_result_desc.fields[9].name = PyStructSequence_UnnamedField;
Victor Stinner1c8f0592013-07-22 22:24:54 +020012995 if (PyStructSequence_InitType2(&StatResultType, &stat_result_desc) < 0)
12996 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000012997 structseq_new = StatResultType.tp_new;
12998 StatResultType.tp_new = statresult_new;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000012999
Christian Heimes25827622013-10-12 01:27:08 +020013000 statvfs_result_desc.name = "os.statvfs_result"; /* see issue #19209 */
Victor Stinner1c8f0592013-07-22 22:24:54 +020013001 if (PyStructSequence_InitType2(&StatVFSResultType,
13002 &statvfs_result_desc) < 0)
13003 return NULL;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013004#ifdef NEED_TICKS_PER_SECOND
13005# if defined(HAVE_SYSCONF) && defined(_SC_CLK_TCK)
Victor Stinner8c62be82010-05-06 00:08:46 +000013006 ticks_per_second = sysconf(_SC_CLK_TCK);
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013007# elif defined(HZ)
Victor Stinner8c62be82010-05-06 00:08:46 +000013008 ticks_per_second = HZ;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013009# else
Victor Stinner8c62be82010-05-06 00:08:46 +000013010 ticks_per_second = 60; /* magic fallback value; may be bogus */
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013011# endif
13012#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013013
Benjamin Peterson0163c9a2011-08-02 18:11:38 -050013014#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013015 sched_param_desc.name = MODNAME ".sched_param";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013016 if (PyStructSequence_InitType2(&SchedParamType, &sched_param_desc) < 0)
13017 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100013018 SchedParamType.tp_new = os_sched_param;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013019#endif
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013020
13021 /* initialize TerminalSize_info */
Victor Stinner1c8f0592013-07-22 22:24:54 +020013022 if (PyStructSequence_InitType2(&TerminalSizeType,
13023 &TerminalSize_desc) < 0)
13024 return NULL;
Victor Stinner6036e442015-03-08 01:58:04 +010013025
13026 /* initialize scandir types */
13027 if (PyType_Ready(&ScandirIteratorType) < 0)
13028 return NULL;
13029 if (PyType_Ready(&DirEntryType) < 0)
13030 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013031 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020013032#if defined(HAVE_WAITID) && !defined(__APPLE__)
13033 Py_INCREF((PyObject*) &WaitidResultType);
13034 PyModule_AddObject(m, "waitid_result", (PyObject*) &WaitidResultType);
13035#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000013036 Py_INCREF((PyObject*) &StatResultType);
13037 PyModule_AddObject(m, "stat_result", (PyObject*) &StatResultType);
13038 Py_INCREF((PyObject*) &StatVFSResultType);
13039 PyModule_AddObject(m, "statvfs_result",
13040 (PyObject*) &StatVFSResultType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050013041
13042#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013043 Py_INCREF(&SchedParamType);
13044 PyModule_AddObject(m, "sched_param", (PyObject *)&SchedParamType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050013045#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +000013046
Larry Hastings605a62d2012-06-24 04:33:36 -070013047 times_result_desc.name = MODNAME ".times_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013048 if (PyStructSequence_InitType2(&TimesResultType, &times_result_desc) < 0)
13049 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070013050 PyModule_AddObject(m, "times_result", (PyObject *)&TimesResultType);
13051
13052 uname_result_desc.name = MODNAME ".uname_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013053 if (PyStructSequence_InitType2(&UnameResultType, &uname_result_desc) < 0)
13054 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070013055 PyModule_AddObject(m, "uname_result", (PyObject *)&UnameResultType);
13056
Thomas Wouters477c8d52006-05-27 19:21:47 +000013057#ifdef __APPLE__
Victor Stinner8c62be82010-05-06 00:08:46 +000013058 /*
13059 * Step 2 of weak-linking support on Mac OS X.
13060 *
13061 * The code below removes functions that are not available on the
13062 * currently active platform.
13063 *
13064 * This block allow one to use a python binary that was build on
Larry Hastings9cf065c2012-06-22 16:30:09 -070013065 * OSX 10.4 on OSX 10.3, without losing access to new APIs on
Victor Stinner8c62be82010-05-06 00:08:46 +000013066 * OSX 10.4.
13067 */
Thomas Wouters477c8d52006-05-27 19:21:47 +000013068#ifdef HAVE_FSTATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000013069 if (fstatvfs == NULL) {
13070 if (PyObject_DelAttrString(m, "fstatvfs") == -1) {
13071 return NULL;
13072 }
13073 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013074#endif /* HAVE_FSTATVFS */
13075
13076#ifdef HAVE_STATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000013077 if (statvfs == NULL) {
13078 if (PyObject_DelAttrString(m, "statvfs") == -1) {
13079 return NULL;
13080 }
13081 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013082#endif /* HAVE_STATVFS */
13083
13084# ifdef HAVE_LCHOWN
Victor Stinner8c62be82010-05-06 00:08:46 +000013085 if (lchown == NULL) {
13086 if (PyObject_DelAttrString(m, "lchown") == -1) {
13087 return NULL;
13088 }
13089 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013090#endif /* HAVE_LCHOWN */
13091
13092
13093#endif /* __APPLE__ */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013094
Antoine Pitrou9d20e0e2012-09-12 18:01:36 +020013095 Py_INCREF(&TerminalSizeType);
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013096 PyModule_AddObject(m, "terminal_size", (PyObject*) &TerminalSizeType);
13097
Larry Hastings6fe20b32012-04-19 15:07:49 -070013098 billion = PyLong_FromLong(1000000000);
13099 if (!billion)
13100 return NULL;
13101
Larry Hastings9cf065c2012-06-22 16:30:09 -070013102 /* suppress "function not used" warnings */
13103 {
13104 int ignored;
13105 fd_specified("", -1);
13106 follow_symlinks_specified("", 1);
13107 dir_fd_and_follow_symlinks_invalid("chmod", DEFAULT_DIR_FD, 1);
13108 dir_fd_converter(Py_None, &ignored);
13109 dir_fd_unavailable(Py_None, &ignored);
13110 }
13111
13112 /*
13113 * provide list of locally available functions
13114 * so os.py can populate support_* lists
13115 */
13116 list = PyList_New(0);
13117 if (!list)
13118 return NULL;
13119 for (trace = have_functions; *trace; trace++) {
13120 PyObject *unicode = PyUnicode_DecodeASCII(*trace, strlen(*trace), NULL);
13121 if (!unicode)
13122 return NULL;
13123 if (PyList_Append(list, unicode))
13124 return NULL;
13125 Py_DECREF(unicode);
13126 }
13127 PyModule_AddObject(m, "_have_functions", list);
13128
13129 initialized = 1;
13130
Victor Stinner8c62be82010-05-06 00:08:46 +000013131 return m;
Guido van Rossumb6775db1994-08-01 11:34:53 +000013132}
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000013133
13134#ifdef __cplusplus
13135}
13136#endif