blob: a87bbbd6b400c290eb7baf662ffe87f35e0340fa [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 Storchaka819399b2016-04-06 22:17:52 +0300672_fd_converter(PyObject *o, int *p)
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200673{
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) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700679 return 0;
680 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700681
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300682 assert(PyLong_Check(index));
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700683 long_value = PyLong_AsLongAndOverflow(index, &overflow);
684 Py_DECREF(index);
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300685 assert(!PyErr_Occurred());
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200686 if (overflow > 0 || long_value > INT_MAX) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700687 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700688 "fd is greater than maximum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700689 return 0;
690 }
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200691 if (overflow < 0 || long_value < INT_MIN) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700692 PyErr_SetString(PyExc_OverflowError,
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700693 "fd is less than minimum");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700694 return 0;
695 }
Larry Hastingsa27b83a2013-08-08 00:19:50 -0700696
Larry Hastings9cf065c2012-06-22 16:30:09 -0700697 *p = (int)long_value;
698 return 1;
699}
700
701static int
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200702dir_fd_converter(PyObject *o, void *p)
703{
704 if (o == Py_None) {
705 *(int *)p = DEFAULT_DIR_FD;
706 return 1;
707 }
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300708 else if (PyIndex_Check(o)) {
709 return _fd_converter(o, (int *)p);
710 }
711 else {
712 PyErr_Format(PyExc_TypeError,
713 "argument should be integer or None, not %.200s",
714 Py_TYPE(o)->tp_name);
715 return 0;
716 }
Larry Hastings9cf065c2012-06-22 16:30:09 -0700717}
718
719
Larry Hastings9cf065c2012-06-22 16:30:09 -0700720/*
721 * A PyArg_ParseTuple "converter" function
722 * that handles filesystem paths in the manner
723 * preferred by the os module.
724 *
725 * path_converter accepts (Unicode) strings and their
726 * subclasses, and bytes and their subclasses. What
727 * it does with the argument depends on the platform:
728 *
729 * * On Windows, if we get a (Unicode) string we
730 * extract the wchar_t * and return it; if we get
731 * bytes we extract the char * and return that.
732 *
733 * * On all other platforms, strings are encoded
734 * to bytes using PyUnicode_FSConverter, then we
735 * extract the char * from the bytes object and
736 * return that.
737 *
738 * path_converter also optionally accepts signed
739 * integers (representing open file descriptors) instead
740 * of path strings.
741 *
742 * Input fields:
743 * path.nullable
744 * If nonzero, the path is permitted to be None.
745 * path.allow_fd
746 * If nonzero, the path is permitted to be a file handle
747 * (a signed int) instead of a string.
748 * path.function_name
749 * If non-NULL, path_converter will use that as the name
750 * of the function in error messages.
Larry Hastings31826802013-10-19 00:09:25 -0700751 * (If path.function_name is NULL it omits the function name.)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700752 * path.argument_name
753 * If non-NULL, path_converter will use that as the name
754 * of the parameter in error messages.
755 * (If path.argument_name is NULL it uses "path".)
756 *
757 * Output fields:
758 * path.wide
759 * Points to the path if it was expressed as Unicode
760 * and was not encoded. (Only used on Windows.)
761 * path.narrow
762 * Points to the path if it was expressed as bytes,
763 * or it was Unicode and was encoded to bytes.
764 * path.fd
765 * Contains a file descriptor if path.accept_fd was true
766 * and the caller provided a signed integer instead of any
767 * sort of string.
768 *
769 * WARNING: if your "path" parameter is optional, and is
770 * unspecified, path_converter will never get called.
771 * So if you set allow_fd, you *MUST* initialize path.fd = -1
772 * yourself!
773 * path.length
774 * The length of the path in characters, if specified as
775 * a string.
776 * path.object
777 * The original object passed in.
778 * path.cleanup
779 * For internal use only. May point to a temporary object.
780 * (Pay no attention to the man behind the curtain.)
781 *
782 * At most one of path.wide or path.narrow will be non-NULL.
783 * If path was None and path.nullable was set,
784 * or if path was an integer and path.allow_fd was set,
785 * both path.wide and path.narrow will be NULL
786 * and path.length will be 0.
Georg Brandlf7875592012-06-24 13:58:31 +0200787 *
Larry Hastings9cf065c2012-06-22 16:30:09 -0700788 * path_converter takes care to not write to the path_t
789 * unless it's successful. However it must reset the
790 * "cleanup" field each time it's called.
791 *
792 * Use as follows:
793 * path_t path;
794 * memset(&path, 0, sizeof(path));
795 * PyArg_ParseTuple(args, "O&", path_converter, &path);
796 * // ... use values from path ...
797 * path_cleanup(&path);
798 *
799 * (Note that if PyArg_Parse fails you don't need to call
800 * path_cleanup(). However it is safe to do so.)
801 */
802typedef struct {
Victor Stinner292c8352012-10-30 02:17:38 +0100803 const char *function_name;
804 const char *argument_name;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700805 int nullable;
806 int allow_fd;
807 wchar_t *wide;
808 char *narrow;
809 int fd;
810 Py_ssize_t length;
811 PyObject *object;
812 PyObject *cleanup;
813} path_t;
814
Larry Hastings2f936352014-08-05 14:04:04 +1000815#define PATH_T_INITIALIZE(function_name, argument_name, nullable, allow_fd) \
816 {function_name, argument_name, nullable, allow_fd, NULL, NULL, -1, 0, NULL, NULL}
Larry Hastings31826802013-10-19 00:09:25 -0700817
Larry Hastings9cf065c2012-06-22 16:30:09 -0700818static void
819path_cleanup(path_t *path) {
820 if (path->cleanup) {
Serhiy Storchaka505ff752014-02-09 13:33:53 +0200821 Py_CLEAR(path->cleanup);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700822 }
823}
824
825static int
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300826path_converter(PyObject *o, void *p)
827{
Larry Hastings9cf065c2012-06-22 16:30:09 -0700828 path_t *path = (path_t *)p;
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300829 PyObject *bytes;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700830 Py_ssize_t length;
831 char *narrow;
832
833#define FORMAT_EXCEPTION(exc, fmt) \
834 PyErr_Format(exc, "%s%s" fmt, \
835 path->function_name ? path->function_name : "", \
836 path->function_name ? ": " : "", \
837 path->argument_name ? path->argument_name : "path")
838
839 /* Py_CLEANUP_SUPPORTED support */
840 if (o == NULL) {
841 path_cleanup(path);
842 return 1;
843 }
844
845 /* ensure it's always safe to call path_cleanup() */
846 path->cleanup = NULL;
847
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300848 if ((o == Py_None) && path->nullable) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700849 path->wide = NULL;
850 path->narrow = NULL;
851 path->length = 0;
852 path->object = o;
853 path->fd = -1;
854 return 1;
855 }
856
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300857 if (PyUnicode_Check(o)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700858#ifdef MS_WINDOWS
859 wchar_t *wide;
Victor Stinner59799a82013-11-13 14:17:30 +0100860
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300861 wide = PyUnicode_AsUnicodeAndSize(o, &length);
Victor Stinner59799a82013-11-13 14:17:30 +0100862 if (!wide) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700863 return 0;
864 }
Victor Stinner59799a82013-11-13 14:17:30 +0100865 if (length > 32767) {
866 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700867 return 0;
868 }
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +0300869 if (wcslen(wide) != length) {
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300870 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +0300871 return 0;
872 }
Larry Hastings9cf065c2012-06-22 16:30:09 -0700873
874 path->wide = wide;
875 path->narrow = NULL;
876 path->length = length;
877 path->object = o;
878 path->fd = -1;
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300879 return 1;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700880#else
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300881 if (!PyUnicode_FSConverter(o, &bytes)) {
882 return 0;
883 }
Larry Hastings9cf065c2012-06-22 16:30:09 -0700884#endif
885 }
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300886 else if (PyObject_CheckBuffer(o)) {
Serhiy Storchaka3291d852016-04-06 23:02:46 +0300887#ifdef MS_WINDOWS
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300888 if (win32_warn_bytes_api()) {
889 return 0;
890 }
Serhiy Storchaka3291d852016-04-06 23:02:46 +0300891#endif
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300892 bytes = PyBytes_FromObject(o);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700893 if (!bytes) {
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300894 return 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -0700895 }
896 }
Serhiy Storchaka819399b2016-04-06 22:17:52 +0300897 else if (path->allow_fd && PyIndex_Check(o)) {
898 if (!_fd_converter(o, &path->fd)) {
899 return 0;
900 }
901 path->wide = NULL;
902 path->narrow = NULL;
903 path->length = 0;
904 path->object = o;
905 return 1;
906 }
907 else {
908 PyErr_Format(PyExc_TypeError, "%s%s%s should be %s, not %.200s",
909 path->function_name ? path->function_name : "",
910 path->function_name ? ": " : "",
911 path->argument_name ? path->argument_name : "path",
912 path->allow_fd && path->nullable ? "string, bytes, integer or None" :
913 path->allow_fd ? "string, bytes or integer" :
914 path->nullable ? "string, bytes or None" :
915 "string or bytes",
916 Py_TYPE(o)->tp_name);
Larry Hastings9cf065c2012-06-22 16:30:09 -0700917 return 0;
918 }
919
Larry Hastings9cf065c2012-06-22 16:30:09 -0700920 length = PyBytes_GET_SIZE(bytes);
921#ifdef MS_WINDOWS
Victor Stinner75875072013-11-24 19:23:25 +0100922 if (length > MAX_PATH-1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -0700923 FORMAT_EXCEPTION(PyExc_ValueError, "%s too long for Windows");
924 Py_DECREF(bytes);
925 return 0;
926 }
927#endif
928
929 narrow = PyBytes_AS_STRING(bytes);
Victor Stinner706768c2014-08-16 01:03:39 +0200930 if ((size_t)length != strlen(narrow)) {
Serhiy Storchakad8a14472014-09-06 20:07:17 +0300931 FORMAT_EXCEPTION(PyExc_ValueError, "embedded null character in %s");
Larry Hastings9cf065c2012-06-22 16:30:09 -0700932 Py_DECREF(bytes);
933 return 0;
934 }
935
936 path->wide = NULL;
937 path->narrow = narrow;
938 path->length = length;
939 path->object = o;
940 path->fd = -1;
941 path->cleanup = bytes;
942 return Py_CLEANUP_SUPPORTED;
943}
944
945static void
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200946argument_unavailable_error(const char *function_name, const char *argument_name)
947{
Larry Hastings9cf065c2012-06-22 16:30:09 -0700948 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
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200970fd_specified(const char *function_name, int fd)
971{
Larry Hastings9cf065c2012-06-22 16:30:09 -0700972 if (fd == -1)
973 return 0;
974
975 argument_unavailable_error(function_name, "fd");
976 return 1;
977}
978
979static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200980follow_symlinks_specified(const char *function_name, int follow_symlinks)
981{
Larry Hastings9cf065c2012-06-22 16:30:09 -0700982 if (follow_symlinks)
983 return 0;
984
985 argument_unavailable_error(function_name, "follow_symlinks");
986 return 1;
987}
988
989static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +0200990path_and_dir_fd_invalid(const char *function_name, path_t *path, int dir_fd)
991{
Larry Hastings9cf065c2012-06-22 16:30:09 -0700992 if (!path->narrow && !path->wide && (dir_fd != DEFAULT_DIR_FD)) {
993 PyErr_Format(PyExc_ValueError,
994 "%s: can't specify dir_fd without matching path",
995 function_name);
996 return 1;
997 }
998 return 0;
999}
1000
1001static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02001002dir_fd_and_fd_invalid(const char *function_name, int dir_fd, int fd)
1003{
Larry Hastings9cf065c2012-06-22 16:30:09 -07001004 if ((dir_fd != DEFAULT_DIR_FD) && (fd != -1)) {
1005 PyErr_Format(PyExc_ValueError,
1006 "%s: can't specify both dir_fd and fd",
1007 function_name);
1008 return 1;
1009 }
1010 return 0;
1011}
1012
1013static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02001014fd_and_follow_symlinks_invalid(const char *function_name, int fd,
1015 int follow_symlinks)
1016{
Larry Hastings9cf065c2012-06-22 16:30:09 -07001017 if ((fd > 0) && (!follow_symlinks)) {
1018 PyErr_Format(PyExc_ValueError,
1019 "%s: cannot use fd and follow_symlinks together",
1020 function_name);
1021 return 1;
1022 }
1023 return 0;
1024}
1025
1026static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02001027dir_fd_and_follow_symlinks_invalid(const char *function_name, int dir_fd,
1028 int follow_symlinks)
1029{
Larry Hastings9cf065c2012-06-22 16:30:09 -07001030 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
1031 PyErr_Format(PyExc_ValueError,
1032 "%s: cannot use dir_fd and follow_symlinks together",
1033 function_name);
1034 return 1;
1035 }
1036 return 0;
1037}
1038
Larry Hastings2f936352014-08-05 14:04:04 +10001039#ifdef MS_WINDOWS
1040 typedef PY_LONG_LONG Py_off_t;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001041#else
Larry Hastings2f936352014-08-05 14:04:04 +10001042 typedef off_t Py_off_t;
1043#endif
1044
1045static int
1046Py_off_t_converter(PyObject *arg, void *addr)
1047{
1048#ifdef HAVE_LARGEFILE_SUPPORT
1049 *((Py_off_t *)addr) = PyLong_AsLongLong(arg);
1050#else
1051 *((Py_off_t *)addr) = PyLong_AsLong(arg);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001052#endif
1053 if (PyErr_Occurred())
1054 return 0;
1055 return 1;
1056}
Larry Hastings2f936352014-08-05 14:04:04 +10001057
1058static PyObject *
1059PyLong_FromPy_off_t(Py_off_t offset)
1060{
1061#ifdef HAVE_LARGEFILE_SUPPORT
1062 return PyLong_FromLongLong(offset);
1063#else
1064 return PyLong_FromLong(offset);
Ross Lagerwallb1e5d592011-09-19 08:30:43 +02001065#endif
Larry Hastings2f936352014-08-05 14:04:04 +10001066}
1067
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001068
Steve Dowerd81431f2015-03-06 14:47:02 -08001069#if defined _MSC_VER && _MSC_VER >= 1400 && _MSC_VER < 1900
1070/* Legacy implementation of _PyVerify_fd_dup2 while transitioning to
1071 * MSVC 14.0. This should eventually be removed. (issue23524)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001072 */
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001073#define IOINFO_L2E 5
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001074#define IOINFO_ARRAYS 64
Steve Dower65e4cb12014-11-22 12:54:57 -08001075#define IOINFO_ARRAY_ELTS (1 << IOINFO_L2E)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001076#define _NHANDLE_ (IOINFO_ARRAYS * IOINFO_ARRAY_ELTS)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001077#define _NO_CONSOLE_FILENO (intptr_t)-2
1078
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001079/* the special case of checking dup2. The target fd must be in a sensible range */
1080static int
1081_PyVerify_fd_dup2(int fd1, int fd2)
1082{
Victor Stinner8c62be82010-05-06 00:08:46 +00001083 if (!_PyVerify_fd(fd1))
1084 return 0;
1085 if (fd2 == _NO_CONSOLE_FILENO)
1086 return 0;
1087 if ((unsigned)fd2 < _NHANDLE_)
1088 return 1;
1089 else
1090 return 0;
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001091}
1092#else
Steve Dowerd81431f2015-03-06 14:47:02 -08001093#define _PyVerify_fd_dup2(fd1, fd2) (_PyVerify_fd(fd1) && (fd2) >= 0)
Amaury Forgeot d'Arc2fc224f2009-02-19 23:23:47 +00001094#endif
1095
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001096#ifdef MS_WINDOWS
Brian Curtinf5e76d02010-11-24 13:14:05 +00001097
1098static int
Brian Curtind25aef52011-06-13 15:16:04 -05001099win32_get_reparse_tag(HANDLE reparse_point_handle, ULONG *reparse_tag)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001100{
1101 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
1102 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
1103 DWORD n_bytes_returned;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001104
1105 if (0 == DeviceIoControl(
1106 reparse_point_handle,
1107 FSCTL_GET_REPARSE_POINT,
1108 NULL, 0, /* in buffer */
1109 target_buffer, sizeof(target_buffer),
1110 &n_bytes_returned,
1111 NULL)) /* we're not using OVERLAPPED_IO */
Brian Curtind25aef52011-06-13 15:16:04 -05001112 return FALSE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001113
1114 if (reparse_tag)
1115 *reparse_tag = rdb->ReparseTag;
1116
Brian Curtind25aef52011-06-13 15:16:04 -05001117 return TRUE;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001118}
Victor Stinner1ab6c2d2011-11-15 22:27:41 +01001119
Brian Curtinfc1be6d2010-11-24 13:23:18 +00001120#endif /* MS_WINDOWS */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001121
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001122/* Return a dictionary corresponding to the POSIX environment table */
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001123#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Jack Jansenea0c3822002-08-01 21:57:49 +00001124/* On Darwin/MacOSX a shared library or framework has no access to
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001125** environ directly, we must obtain it with _NSGetEnviron(). See also
1126** man environ(7).
Jack Jansenea0c3822002-08-01 21:57:49 +00001127*/
1128#include <crt_externs.h>
1129static char **environ;
1130#elif !defined(_MSC_VER) && ( !defined(__WATCOMC__) || defined(__QNX__) )
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001131extern char **environ;
Guido van Rossuma4916fa1996-05-23 22:58:55 +00001132#endif /* !_MSC_VER */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001133
Barry Warsaw53699e91996-12-10 23:23:01 +00001134static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001135convertenviron(void)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001136{
Victor Stinner8c62be82010-05-06 00:08:46 +00001137 PyObject *d;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001138#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00001139 wchar_t **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001140#else
Victor Stinner8c62be82010-05-06 00:08:46 +00001141 char **e;
Thomas Hellerf78f12a2007-11-08 19:33:05 +00001142#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +00001143
Victor Stinner8c62be82010-05-06 00:08:46 +00001144 d = PyDict_New();
1145 if (d == NULL)
1146 return NULL;
Ronald Oussoren697e56d2013-01-25 17:57:13 +01001147#if defined(WITH_NEXT_FRAMEWORK) || (defined(__APPLE__) && defined(Py_ENABLE_SHARED))
Victor Stinner8c62be82010-05-06 00:08:46 +00001148 if (environ == NULL)
1149 environ = *_NSGetEnviron();
1150#endif
1151#ifdef MS_WINDOWS
1152 /* _wenviron must be initialized in this way if the program is started
1153 through main() instead of wmain(). */
1154 _wgetenv(L"");
1155 if (_wenviron == NULL)
1156 return d;
1157 /* This part ignores errors */
1158 for (e = _wenviron; *e != NULL; e++) {
1159 PyObject *k;
1160 PyObject *v;
1161 wchar_t *p = wcschr(*e, L'=');
1162 if (p == NULL)
1163 continue;
1164 k = PyUnicode_FromWideChar(*e, (Py_ssize_t)(p-*e));
1165 if (k == NULL) {
1166 PyErr_Clear();
1167 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001168 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001169 v = PyUnicode_FromWideChar(p+1, wcslen(p+1));
1170 if (v == NULL) {
1171 PyErr_Clear();
1172 Py_DECREF(k);
1173 continue;
Guido van Rossumd48f2521997-12-05 22:19:34 +00001174 }
Victor Stinner8c62be82010-05-06 00:08:46 +00001175 if (PyDict_GetItem(d, k) == NULL) {
1176 if (PyDict_SetItem(d, k, v) != 0)
1177 PyErr_Clear();
1178 }
1179 Py_DECREF(k);
1180 Py_DECREF(v);
1181 }
1182#else
1183 if (environ == NULL)
1184 return d;
1185 /* This part ignores errors */
1186 for (e = environ; *e != NULL; e++) {
1187 PyObject *k;
1188 PyObject *v;
1189 char *p = strchr(*e, '=');
1190 if (p == NULL)
1191 continue;
Victor Stinner84ae1182010-05-06 22:05:07 +00001192 k = PyBytes_FromStringAndSize(*e, (int)(p-*e));
Victor Stinner8c62be82010-05-06 00:08:46 +00001193 if (k == NULL) {
1194 PyErr_Clear();
1195 continue;
1196 }
Victor Stinner84ae1182010-05-06 22:05:07 +00001197 v = PyBytes_FromStringAndSize(p+1, strlen(p+1));
Victor Stinner8c62be82010-05-06 00:08:46 +00001198 if (v == NULL) {
1199 PyErr_Clear();
1200 Py_DECREF(k);
1201 continue;
1202 }
1203 if (PyDict_GetItem(d, k) == NULL) {
1204 if (PyDict_SetItem(d, k, v) != 0)
1205 PyErr_Clear();
1206 }
1207 Py_DECREF(k);
1208 Py_DECREF(v);
Guido van Rossumd48f2521997-12-05 22:19:34 +00001209 }
1210#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001211 return d;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001212}
1213
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001214/* Set a POSIX-specific error from errno, and return NULL */
1215
Barry Warsawd58d7641998-07-23 16:14:40 +00001216static PyObject *
Thomas Woutersf3f33dc2000-07-21 06:00:07 +00001217posix_error(void)
Guido van Rossumad0ee831995-03-01 10:34:45 +00001218{
Victor Stinner8c62be82010-05-06 00:08:46 +00001219 return PyErr_SetFromErrno(PyExc_OSError);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001220}
Mark Hammondef8b6542001-05-13 08:04:26 +00001221
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00001222#ifdef MS_WINDOWS
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001223static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02001224win32_error(const char* function, const char* filename)
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001225{
Victor Stinner8c62be82010-05-06 00:08:46 +00001226 /* XXX We should pass the function name along in the future.
1227 (winreg.c also wants to pass the function name.)
1228 This would however require an additional param to the
1229 Windows error object, which is non-trivial.
1230 */
1231 errno = GetLastError();
1232 if (filename)
1233 return PyErr_SetFromWindowsErrWithFilename(errno, filename);
1234 else
1235 return PyErr_SetFromWindowsErr(errno);
Fredrik Lundhffb9c772000-07-09 14:49:51 +00001236}
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001237
Mark Hammondc2e85bd2002-10-03 05:10:39 +00001238static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02001239win32_error_object(const char* function, PyObject* filename)
Victor Stinnereb5657a2011-09-30 01:44:27 +02001240{
1241 /* XXX - see win32_error for comments on 'function' */
1242 errno = GetLastError();
1243 if (filename)
1244 return PyErr_SetExcFromWindowsErrWithFilenameObject(
Andrew Svetlov2606a6f2012-12-19 14:33:35 +02001245 PyExc_OSError,
Victor Stinnereb5657a2011-09-30 01:44:27 +02001246 errno,
1247 filename);
1248 else
1249 return PyErr_SetFromWindowsErr(errno);
1250}
1251
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001252#endif /* MS_WINDOWS */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001253
Larry Hastings9cf065c2012-06-22 16:30:09 -07001254static PyObject *
Victor Stinner292c8352012-10-30 02:17:38 +01001255path_error(path_t *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001256{
1257#ifdef MS_WINDOWS
Victor Stinner292c8352012-10-30 02:17:38 +01001258 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
1259 0, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001260#else
Victor Stinner292c8352012-10-30 02:17:38 +01001261 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings9cf065c2012-06-22 16:30:09 -07001262#endif
1263}
1264
Larry Hastings31826802013-10-19 00:09:25 -07001265
Larry Hastingsb0827312014-02-09 22:05:19 -08001266static PyObject *
1267path_error2(path_t *path, path_t *path2)
1268{
1269#ifdef MS_WINDOWS
1270 return PyErr_SetExcFromWindowsErrWithFilenameObjects(PyExc_OSError,
1271 0, path->object, path2->object);
1272#else
1273 return PyErr_SetFromErrnoWithFilenameObjects(PyExc_OSError,
1274 path->object, path2->object);
1275#endif
1276}
1277
1278
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001279/* POSIX generic methods */
1280
Larry Hastings2f936352014-08-05 14:04:04 +10001281static int
1282fildes_converter(PyObject *o, void *p)
Fred Drake4d1e64b2002-04-15 19:40:07 +00001283{
Victor Stinner8c62be82010-05-06 00:08:46 +00001284 int fd;
Larry Hastings2f936352014-08-05 14:04:04 +10001285 int *pointer = (int *)p;
1286 fd = PyObject_AsFileDescriptor(o);
Victor Stinner8c62be82010-05-06 00:08:46 +00001287 if (fd < 0)
Larry Hastings2f936352014-08-05 14:04:04 +10001288 return 0;
Larry Hastings2f936352014-08-05 14:04:04 +10001289 *pointer = fd;
1290 return 1;
1291}
1292
1293static PyObject *
1294posix_fildes_fd(int fd, int (*func)(int))
1295{
1296 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001297 int async_err = 0;
1298
Steve Dower8fc89802015-04-12 00:26:27 -04001299 if (!_PyVerify_fd(fd))
1300 return posix_error();
1301
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001302 do {
1303 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04001304 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001305 res = (*func)(fd);
Steve Dower8fc89802015-04-12 00:26:27 -04001306 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00001307 Py_END_ALLOW_THREADS
1308 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
1309 if (res != 0)
1310 return (!async_err) ? posix_error() : NULL;
1311 Py_RETURN_NONE;
Fred Drake4d1e64b2002-04-15 19:40:07 +00001312}
Guido van Rossum21142a01999-01-08 21:05:37 +00001313
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00001314
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00001315#ifdef MS_WINDOWS
Thomas Wouters477c8d52006-05-27 19:21:47 +00001316/* This is a reimplementation of the C library's chdir function,
1317 but one that produces Win32 errors instead of DOS error codes.
1318 chdir is essentially a wrapper around SetCurrentDirectory; however,
1319 it also needs to set "magic" environment variables indicating
1320 the per-drive current directory, which are of the form =<drive>: */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001321static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001322win32_chdir(LPCSTR path)
1323{
Victor Stinner75875072013-11-24 19:23:25 +01001324 char new_path[MAX_PATH];
Victor Stinner8c62be82010-05-06 00:08:46 +00001325 int result;
1326 char env[4] = "=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001327
Victor Stinner8c62be82010-05-06 00:08:46 +00001328 if(!SetCurrentDirectoryA(path))
1329 return FALSE;
Victor Stinner75875072013-11-24 19:23:25 +01001330 result = GetCurrentDirectoryA(Py_ARRAY_LENGTH(new_path), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001331 if (!result)
1332 return FALSE;
1333 /* In the ANSI API, there should not be any paths longer
Victor Stinner75875072013-11-24 19:23:25 +01001334 than MAX_PATH-1 (not including the final null character). */
1335 assert(result < Py_ARRAY_LENGTH(new_path));
Victor Stinner8c62be82010-05-06 00:08:46 +00001336 if (strncmp(new_path, "\\\\", 2) == 0 ||
1337 strncmp(new_path, "//", 2) == 0)
1338 /* UNC path, nothing to do. */
1339 return TRUE;
1340 env[1] = new_path[0];
1341 return SetEnvironmentVariableA(env, new_path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00001342}
1343
1344/* The Unicode version differs from the ANSI version
1345 since the current directory might exceed MAX_PATH characters */
Benjamin Peterson206e3072008-10-19 14:07:49 +00001346static BOOL __stdcall
Thomas Wouters477c8d52006-05-27 19:21:47 +00001347win32_wchdir(LPCWSTR path)
1348{
Victor Stinnered537822015-12-13 21:40:26 +01001349 wchar_t path_buf[MAX_PATH], *new_path = path_buf;
Victor Stinner8c62be82010-05-06 00:08:46 +00001350 int result;
1351 wchar_t env[4] = L"=x:";
Thomas Wouters477c8d52006-05-27 19:21:47 +00001352
Victor Stinner8c62be82010-05-06 00:08:46 +00001353 if(!SetCurrentDirectoryW(path))
1354 return FALSE;
Victor Stinnered537822015-12-13 21:40:26 +01001355 result = GetCurrentDirectoryW(Py_ARRAY_LENGTH(path_buf), new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001356 if (!result)
1357 return FALSE;
Victor Stinnere847d712015-12-14 00:21:50 +01001358 if (result > Py_ARRAY_LENGTH(path_buf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001359 new_path = PyMem_RawMalloc(result * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00001360 if (!new_path) {
1361 SetLastError(ERROR_OUTOFMEMORY);
1362 return FALSE;
1363 }
1364 result = GetCurrentDirectoryW(result, new_path);
1365 if (!result) {
Victor Stinnerb6404912013-07-07 16:21:41 +02001366 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001367 return FALSE;
1368 }
1369 }
1370 if (wcsncmp(new_path, L"\\\\", 2) == 0 ||
1371 wcsncmp(new_path, L"//", 2) == 0)
1372 /* UNC path, nothing to do. */
1373 return TRUE;
1374 env[1] = new_path[0];
1375 result = SetEnvironmentVariableW(env, new_path);
Victor Stinnered537822015-12-13 21:40:26 +01001376 if (new_path != path_buf)
Victor Stinnerb6404912013-07-07 16:21:41 +02001377 PyMem_RawFree(new_path);
Victor Stinner8c62be82010-05-06 00:08:46 +00001378 return result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00001379}
1380#endif
1381
Martin v. Löwis14694662006-02-03 12:54:16 +00001382#ifdef MS_WINDOWS
1383/* The CRT of Windows has a number of flaws wrt. its stat() implementation:
1384 - time stamps are restricted to second resolution
1385 - file modification times suffer from forth-and-back conversions between
1386 UTC and local time
1387 Therefore, we implement our own stat, based on the Win32 API directly.
1388*/
Victor Stinner8c62be82010-05-06 00:08:46 +00001389#define HAVE_STAT_NSEC 1
Zachary Ware63f277b2014-06-19 09:46:37 -05001390#define HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES 1
Martin v. Löwis14694662006-02-03 12:54:16 +00001391
Guido van Rossumd8faa362007-04-27 19:54:29 +00001392static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001393attributes_from_dir(LPCSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001394{
Victor Stinner8c62be82010-05-06 00:08:46 +00001395 HANDLE hFindFile;
1396 WIN32_FIND_DATAA FileData;
1397 hFindFile = FindFirstFileA(pszFile, &FileData);
1398 if (hFindFile == INVALID_HANDLE_VALUE)
1399 return FALSE;
1400 FindClose(hFindFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001401 memset(info, 0, sizeof(*info));
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001402 *reparse_tag = 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001403 info->dwFileAttributes = FileData.dwFileAttributes;
1404 info->ftCreationTime = FileData.ftCreationTime;
1405 info->ftLastAccessTime = FileData.ftLastAccessTime;
1406 info->ftLastWriteTime = FileData.ftLastWriteTime;
1407 info->nFileSizeHigh = FileData.nFileSizeHigh;
1408 info->nFileSizeLow = FileData.nFileSizeLow;
1409/* info->nNumberOfLinks = 1; */
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001410 if (FileData.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1411 *reparse_tag = FileData.dwReserved0;
Victor Stinner8c62be82010-05-06 00:08:46 +00001412 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001413}
1414
Victor Stinner6036e442015-03-08 01:58:04 +01001415static void
1416find_data_to_file_info_w(WIN32_FIND_DATAW *pFileData,
1417 BY_HANDLE_FILE_INFORMATION *info,
1418 ULONG *reparse_tag)
1419{
1420 memset(info, 0, sizeof(*info));
1421 info->dwFileAttributes = pFileData->dwFileAttributes;
1422 info->ftCreationTime = pFileData->ftCreationTime;
1423 info->ftLastAccessTime = pFileData->ftLastAccessTime;
1424 info->ftLastWriteTime = pFileData->ftLastWriteTime;
1425 info->nFileSizeHigh = pFileData->nFileSizeHigh;
1426 info->nFileSizeLow = pFileData->nFileSizeLow;
1427/* info->nNumberOfLinks = 1; */
1428 if (pFileData->dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT)
1429 *reparse_tag = pFileData->dwReserved0;
1430 else
1431 *reparse_tag = 0;
1432}
1433
Guido van Rossumd8faa362007-04-27 19:54:29 +00001434static BOOL
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001435attributes_from_dir_w(LPCWSTR pszFile, BY_HANDLE_FILE_INFORMATION *info, ULONG *reparse_tag)
Guido van Rossumd8faa362007-04-27 19:54:29 +00001436{
Victor Stinner8c62be82010-05-06 00:08:46 +00001437 HANDLE hFindFile;
1438 WIN32_FIND_DATAW FileData;
1439 hFindFile = FindFirstFileW(pszFile, &FileData);
1440 if (hFindFile == INVALID_HANDLE_VALUE)
1441 return FALSE;
1442 FindClose(hFindFile);
Victor Stinner6036e442015-03-08 01:58:04 +01001443 find_data_to_file_info_w(&FileData, info, reparse_tag);
Victor Stinner8c62be82010-05-06 00:08:46 +00001444 return TRUE;
Guido van Rossumd8faa362007-04-27 19:54:29 +00001445}
1446
Brian Curtind25aef52011-06-13 15:16:04 -05001447static BOOL
1448get_target_path(HANDLE hdl, wchar_t **target_path)
1449{
1450 int buf_size, result_length;
1451 wchar_t *buf;
1452
1453 /* We have a good handle to the target, use it to determine
1454 the target path name (then we'll call lstat on it). */
Steve Dower2ea51c92015-03-20 21:49:12 -07001455 buf_size = GetFinalPathNameByHandleW(hdl, 0, 0,
1456 VOLUME_NAME_DOS);
Brian Curtind25aef52011-06-13 15:16:04 -05001457 if(!buf_size)
1458 return FALSE;
1459
Victor Stinnerc36674a2016-03-16 14:30:16 +01001460 buf = (wchar_t *)PyMem_RawMalloc((buf_size + 1) * sizeof(wchar_t));
Brian Curtinc8be8402011-06-14 09:52:50 -05001461 if (!buf) {
1462 SetLastError(ERROR_OUTOFMEMORY);
1463 return FALSE;
1464 }
1465
Steve Dower2ea51c92015-03-20 21:49:12 -07001466 result_length = GetFinalPathNameByHandleW(hdl,
Brian Curtind25aef52011-06-13 15:16:04 -05001467 buf, buf_size, VOLUME_NAME_DOS);
1468
1469 if(!result_length) {
Victor Stinnerc36674a2016-03-16 14:30:16 +01001470 PyMem_RawFree(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001471 return FALSE;
1472 }
1473
1474 if(!CloseHandle(hdl)) {
Victor Stinnerc36674a2016-03-16 14:30:16 +01001475 PyMem_RawFree(buf);
Brian Curtind25aef52011-06-13 15:16:04 -05001476 return FALSE;
1477 }
1478
1479 buf[result_length] = 0;
1480
1481 *target_path = buf;
1482 return TRUE;
1483}
1484
1485static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001486win32_xstat_impl_w(const wchar_t *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001487 BOOL traverse);
1488static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001489win32_xstat_impl(const char *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001490 BOOL traverse)
1491{
Victor Stinner26de69d2011-06-17 15:15:38 +02001492 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001493 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001494 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001495 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001496 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001497 const char *dot;
1498
1499 hFile = CreateFileA(
1500 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001501 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001502 0, /* share mode */
1503 NULL, /* security attributes */
1504 OPEN_EXISTING,
1505 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001506 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1507 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001508 the symlink path again and not the actual final path. */
Brian Curtind25aef52011-06-13 15:16:04 -05001509 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
1510 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001511 NULL);
1512
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001513 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001514 /* Either the target doesn't exist, or we don't have access to
1515 get a handle to it. If the former, we need to return an error.
1516 If the latter, we can use attributes_from_dir. */
1517 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001518 return -1;
1519 /* Could not get attributes on open file. Fall back to
1520 reading the directory. */
1521 if (!attributes_from_dir(path, &info, &reparse_tag))
1522 /* Very strange. This should not fail now */
1523 return -1;
1524 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1525 if (traverse) {
1526 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001527 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001528 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001529 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001530 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001531 } else {
1532 if (!GetFileInformationByHandle(hFile, &info)) {
1533 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001534 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001535 }
1536 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001537 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1538 return -1;
1539
1540 /* Close the outer open file handle now that we're about to
1541 reopen it with different flags. */
1542 if (!CloseHandle(hFile))
1543 return -1;
1544
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001545 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001546 /* In order to call GetFinalPathNameByHandle we need to open
1547 the file without the reparse handling flag set. */
1548 hFile2 = CreateFileA(
1549 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1550 NULL, OPEN_EXISTING,
1551 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1552 NULL);
1553 if (hFile2 == INVALID_HANDLE_VALUE)
1554 return -1;
1555
1556 if (!get_target_path(hFile2, &target_path))
1557 return -1;
1558
1559 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerc36674a2016-03-16 14:30:16 +01001560 PyMem_RawFree(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001561 return code;
1562 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001563 } else
1564 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001565 }
Steve Dowera2af1a52015-02-21 10:04:10 -08001566 _Py_attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001567
1568 /* Set S_IEXEC if it is an .exe, .bat, ... */
1569 dot = strrchr(path, '.');
1570 if (dot) {
1571 if (stricmp(dot, ".bat") == 0 || stricmp(dot, ".cmd") == 0 ||
1572 stricmp(dot, ".exe") == 0 || stricmp(dot, ".com") == 0)
1573 result->st_mode |= 0111;
1574 }
1575 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001576}
1577
1578static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001579win32_xstat_impl_w(const wchar_t *path, struct _Py_stat_struct *result,
Brian Curtind25aef52011-06-13 15:16:04 -05001580 BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001581{
1582 int code;
Brian Curtind25aef52011-06-13 15:16:04 -05001583 HANDLE hFile, hFile2;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001584 BY_HANDLE_FILE_INFORMATION info;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001585 ULONG reparse_tag = 0;
Victor Stinner26de69d2011-06-17 15:15:38 +02001586 wchar_t *target_path;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001587 const wchar_t *dot;
1588
1589 hFile = CreateFileW(
1590 path,
Brian Curtind25aef52011-06-13 15:16:04 -05001591 FILE_READ_ATTRIBUTES, /* desired access */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001592 0, /* share mode */
1593 NULL, /* security attributes */
1594 OPEN_EXISTING,
1595 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
Brian Curtind25aef52011-06-13 15:16:04 -05001596 /* FILE_FLAG_OPEN_REPARSE_POINT does not follow the symlink.
1597 Because of this, calls like GetFinalPathNameByHandle will return
R David Murrayfc069992013-12-13 20:52:19 -05001598 the symlink path again and not the actual final path. */
Victor Stinner26de69d2011-06-17 15:15:38 +02001599 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS|
Brian Curtind25aef52011-06-13 15:16:04 -05001600 FILE_FLAG_OPEN_REPARSE_POINT,
Brian Curtinf5e76d02010-11-24 13:14:05 +00001601 NULL);
1602
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001603 if (hFile == INVALID_HANDLE_VALUE) {
Brian Curtinf5e76d02010-11-24 13:14:05 +00001604 /* Either the target doesn't exist, or we don't have access to
1605 get a handle to it. If the former, we need to return an error.
1606 If the latter, we can use attributes_from_dir. */
1607 if (GetLastError() != ERROR_SHARING_VIOLATION)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001608 return -1;
1609 /* Could not get attributes on open file. Fall back to
1610 reading the directory. */
1611 if (!attributes_from_dir_w(path, &info, &reparse_tag))
1612 /* Very strange. This should not fail now */
1613 return -1;
1614 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
1615 if (traverse) {
1616 /* Should traverse, but could not open reparse point handle */
Brian Curtinf5e76d02010-11-24 13:14:05 +00001617 SetLastError(ERROR_SHARING_VIOLATION);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001618 return -1;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001619 }
Brian Curtinf5e76d02010-11-24 13:14:05 +00001620 }
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001621 } else {
1622 if (!GetFileInformationByHandle(hFile, &info)) {
1623 CloseHandle(hFile);
Brian Curtind25aef52011-06-13 15:16:04 -05001624 return -1;
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001625 }
1626 if (info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
Brian Curtind25aef52011-06-13 15:16:04 -05001627 if (!win32_get_reparse_tag(hFile, &reparse_tag))
1628 return -1;
1629
1630 /* Close the outer open file handle now that we're about to
1631 reopen it with different flags. */
1632 if (!CloseHandle(hFile))
1633 return -1;
1634
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001635 if (traverse) {
Brian Curtind25aef52011-06-13 15:16:04 -05001636 /* In order to call GetFinalPathNameByHandle we need to open
1637 the file without the reparse handling flag set. */
1638 hFile2 = CreateFileW(
1639 path, FILE_READ_ATTRIBUTES, FILE_SHARE_READ,
1640 NULL, OPEN_EXISTING,
1641 FILE_ATTRIBUTE_NORMAL|FILE_FLAG_BACKUP_SEMANTICS,
1642 NULL);
1643 if (hFile2 == INVALID_HANDLE_VALUE)
1644 return -1;
1645
1646 if (!get_target_path(hFile2, &target_path))
1647 return -1;
1648
1649 code = win32_xstat_impl_w(target_path, result, FALSE);
Victor Stinnerc36674a2016-03-16 14:30:16 +01001650 PyMem_RawFree(target_path);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001651 return code;
1652 }
Hirokazu Yamamoto7ed117a2010-12-07 10:24:37 +00001653 } else
1654 CloseHandle(hFile);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001655 }
Steve Dowera2af1a52015-02-21 10:04:10 -08001656 _Py_attribute_data_to_stat(&info, reparse_tag, result);
Brian Curtinf5e76d02010-11-24 13:14:05 +00001657
1658 /* Set S_IEXEC if it is an .exe, .bat, ... */
1659 dot = wcsrchr(path, '.');
1660 if (dot) {
1661 if (_wcsicmp(dot, L".bat") == 0 || _wcsicmp(dot, L".cmd") == 0 ||
1662 _wcsicmp(dot, L".exe") == 0 || _wcsicmp(dot, L".com") == 0)
1663 result->st_mode |= 0111;
1664 }
1665 return 0;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001666}
1667
1668static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001669win32_xstat(const char *path, struct _Py_stat_struct *result, BOOL traverse)
Brian Curtinf5e76d02010-11-24 13:14:05 +00001670{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001671 /* Protocol violation: we explicitly clear errno, instead of
1672 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001673 int code = win32_xstat_impl(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001674 errno = 0;
1675 return code;
1676}
Brian Curtinf5e76d02010-11-24 13:14:05 +00001677
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001678static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001679win32_xstat_w(const wchar_t *path, struct _Py_stat_struct *result, BOOL traverse)
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001680{
1681 /* Protocol violation: we explicitly clear errno, instead of
1682 setting it to a POSIX error. Callers should use GetLastError. */
Brian Curtind25aef52011-06-13 15:16:04 -05001683 int code = win32_xstat_impl_w(path, result, traverse);
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001684 errno = 0;
1685 return code;
Brian Curtinf5e76d02010-11-24 13:14:05 +00001686}
Brian Curtind25aef52011-06-13 15:16:04 -05001687/* About the following functions: win32_lstat_w, win32_stat, win32_stat_w
Brian Curtind40e6f72010-07-08 21:39:08 +00001688
1689 In Posix, stat automatically traverses symlinks and returns the stat
1690 structure for the target. In Windows, the equivalent GetFileAttributes by
1691 default does not traverse symlinks and instead returns attributes for
1692 the symlink.
1693
1694 Therefore, win32_lstat will get the attributes traditionally, and
1695 win32_stat will first explicitly resolve the symlink target and then will
1696 call win32_lstat on that result.
1697
Ezio Melotti4969f702011-03-15 05:59:46 +02001698 The _w represent Unicode equivalents of the aforementioned ANSI functions. */
Brian Curtind40e6f72010-07-08 21:39:08 +00001699
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001700static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001701win32_lstat(const char* 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(path, result, FALSE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001704}
1705
Victor Stinner8c62be82010-05-06 00:08:46 +00001706static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001707win32_lstat_w(const wchar_t* path, struct _Py_stat_struct *result)
Martin v. Löwis14694662006-02-03 12:54:16 +00001708{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001709 return win32_xstat_w(path, result, FALSE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001710}
1711
1712static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001713win32_stat(const char* 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(path, result, TRUE);
Brian Curtind40e6f72010-07-08 21:39:08 +00001716}
1717
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00001718static int
Steve Dowerf2f373f2015-02-21 08:44:05 -08001719win32_stat_w(const wchar_t* path, struct _Py_stat_struct *result)
Brian Curtind40e6f72010-07-08 21:39:08 +00001720{
Hirokazu Yamamoto427d3142010-12-04 10:16:05 +00001721 return win32_xstat_w(path, result, TRUE);
Martin v. Löwis14694662006-02-03 12:54:16 +00001722}
1723
Martin v. Löwis14694662006-02-03 12:54:16 +00001724#endif /* MS_WINDOWS */
1725
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001726PyDoc_STRVAR(stat_result__doc__,
Larry Hastings9cf065c2012-06-22 16:30:09 -07001727"stat_result: Result from stat, fstat, or lstat.\n\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001728This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001729 (mode, ino, dev, nlink, uid, gid, size, atime, mtime, ctime)\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001730or via the attributes st_mode, st_ino, st_dev, st_nlink, st_uid, and so on.\n\
1731\n\
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001732Posix/windows: If your platform supports st_blksize, st_blocks, st_rdev,\n\
1733or st_flags, they are available as attributes only.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001734\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001735See os.stat for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001736
1737static PyStructSequence_Field stat_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001738 {"st_mode", "protection bits"},
1739 {"st_ino", "inode"},
1740 {"st_dev", "device"},
1741 {"st_nlink", "number of hard links"},
1742 {"st_uid", "user ID of owner"},
1743 {"st_gid", "group ID of owner"},
1744 {"st_size", "total size, in bytes"},
1745 /* The NULL is replaced with PyStructSequence_UnnamedField later. */
1746 {NULL, "integer time of last access"},
1747 {NULL, "integer time of last modification"},
1748 {NULL, "integer time of last change"},
1749 {"st_atime", "time of last access"},
1750 {"st_mtime", "time of last modification"},
1751 {"st_ctime", "time of last change"},
Larry Hastings6fe20b32012-04-19 15:07:49 -07001752 {"st_atime_ns", "time of last access in nanoseconds"},
1753 {"st_mtime_ns", "time of last modification in nanoseconds"},
1754 {"st_ctime_ns", "time of last change in nanoseconds"},
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001755#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00001756 {"st_blksize", "blocksize for filesystem I/O"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001757#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001758#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00001759 {"st_blocks", "number of blocks allocated"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001760#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001761#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00001762 {"st_rdev", "device type (if inode device)"},
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001763#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001764#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00001765 {"st_flags", "user defined flags for file"},
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001766#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001767#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00001768 {"st_gen", "generation number"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001769#endif
1770#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00001771 {"st_birthtime", "time of creation"},
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001772#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05001773#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1774 {"st_file_attributes", "Windows file attribute bits"},
1775#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00001776 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001777};
1778
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001779#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Larry Hastings6fe20b32012-04-19 15:07:49 -07001780#define ST_BLKSIZE_IDX 16
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001781#else
Larry Hastings6fe20b32012-04-19 15:07:49 -07001782#define ST_BLKSIZE_IDX 15
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001783#endif
1784
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001785#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001786#define ST_BLOCKS_IDX (ST_BLKSIZE_IDX+1)
1787#else
1788#define ST_BLOCKS_IDX ST_BLKSIZE_IDX
1789#endif
1790
Martin v. Löwis60a5d722002-10-16 20:28:25 +00001791#ifdef HAVE_STRUCT_STAT_ST_RDEV
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001792#define ST_RDEV_IDX (ST_BLOCKS_IDX+1)
1793#else
1794#define ST_RDEV_IDX ST_BLOCKS_IDX
1795#endif
1796
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00001797#ifdef HAVE_STRUCT_STAT_ST_FLAGS
1798#define ST_FLAGS_IDX (ST_RDEV_IDX+1)
1799#else
1800#define ST_FLAGS_IDX ST_RDEV_IDX
1801#endif
1802
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001803#ifdef HAVE_STRUCT_STAT_ST_GEN
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001804#define ST_GEN_IDX (ST_FLAGS_IDX+1)
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001805#else
Martin v. Löwisf09582e2005-08-14 21:42:34 +00001806#define ST_GEN_IDX ST_FLAGS_IDX
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00001807#endif
1808
1809#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
1810#define ST_BIRTHTIME_IDX (ST_GEN_IDX+1)
1811#else
1812#define ST_BIRTHTIME_IDX ST_GEN_IDX
1813#endif
1814
Zachary Ware63f277b2014-06-19 09:46:37 -05001815#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
1816#define ST_FILE_ATTRIBUTES_IDX (ST_BIRTHTIME_IDX+1)
1817#else
1818#define ST_FILE_ATTRIBUTES_IDX ST_BIRTHTIME_IDX
1819#endif
1820
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001821static PyStructSequence_Desc stat_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001822 "stat_result", /* name */
1823 stat_result__doc__, /* doc */
1824 stat_result_fields,
1825 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001826};
1827
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001828PyDoc_STRVAR(statvfs_result__doc__,
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001829"statvfs_result: Result from statvfs or fstatvfs.\n\n\
1830This object may be accessed either as a tuple of\n\
Fred Drakef7ce04d2002-06-20 18:31:21 +00001831 (bsize, frsize, blocks, bfree, bavail, files, ffree, favail, flag, namemax),\n\
Guido van Rossuma4dc73e2001-10-18 20:53:15 +00001832or via the attributes f_bsize, f_frsize, f_blocks, f_bfree, and so on.\n\
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001833\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00001834See os.statvfs for more information.");
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001835
1836static PyStructSequence_Field statvfs_result_fields[] = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001837 {"f_bsize", },
1838 {"f_frsize", },
1839 {"f_blocks", },
1840 {"f_bfree", },
1841 {"f_bavail", },
1842 {"f_files", },
1843 {"f_ffree", },
1844 {"f_favail", },
1845 {"f_flag", },
1846 {"f_namemax",},
1847 {0}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001848};
1849
1850static PyStructSequence_Desc statvfs_result_desc = {
Victor Stinner8c62be82010-05-06 00:08:46 +00001851 "statvfs_result", /* name */
1852 statvfs_result__doc__, /* doc */
1853 statvfs_result_fields,
1854 10
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001855};
1856
Ross Lagerwall7807c352011-03-17 20:20:30 +02001857#if defined(HAVE_WAITID) && !defined(__APPLE__)
1858PyDoc_STRVAR(waitid_result__doc__,
1859"waitid_result: Result from waitid.\n\n\
1860This object may be accessed either as a tuple of\n\
1861 (si_pid, si_uid, si_signo, si_status, si_code),\n\
1862or via the attributes si_pid, si_uid, and so on.\n\
1863\n\
1864See os.waitid for more information.");
1865
1866static PyStructSequence_Field waitid_result_fields[] = {
1867 {"si_pid", },
1868 {"si_uid", },
1869 {"si_signo", },
1870 {"si_status", },
1871 {"si_code", },
1872 {0}
1873};
1874
1875static PyStructSequence_Desc waitid_result_desc = {
1876 "waitid_result", /* name */
1877 waitid_result__doc__, /* doc */
1878 waitid_result_fields,
1879 5
1880};
1881static PyTypeObject WaitidResultType;
1882#endif
1883
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00001884static int initialized;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001885static PyTypeObject StatResultType;
1886static PyTypeObject StatVFSResultType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05001887#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001888static PyTypeObject SchedParamType;
Benjamin Petersonbad9c2f2011-08-02 18:42:14 -05001889#endif
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001890static newfunc structseq_new;
1891
1892static PyObject *
1893statresult_new(PyTypeObject *type, PyObject *args, PyObject *kwds)
1894{
Victor Stinner8c62be82010-05-06 00:08:46 +00001895 PyStructSequence *result;
1896 int i;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001897
Victor Stinner8c62be82010-05-06 00:08:46 +00001898 result = (PyStructSequence*)structseq_new(type, args, kwds);
1899 if (!result)
1900 return NULL;
1901 /* If we have been initialized from a tuple,
1902 st_?time might be set to None. Initialize it
1903 from the int slots. */
1904 for (i = 7; i <= 9; i++) {
1905 if (result->ob_item[i+3] == Py_None) {
1906 Py_DECREF(Py_None);
1907 Py_INCREF(result->ob_item[i]);
1908 result->ob_item[i+3] = result->ob_item[i];
1909 }
1910 }
1911 return (PyObject*)result;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001912}
1913
1914
1915
1916/* If true, st_?time is float. */
Martin v. Löwisfe33d0b2005-01-16 08:57:39 +00001917static int _stat_float_times = 1;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001918
1919PyDoc_STRVAR(stat_float_times__doc__,
1920"stat_float_times([newval]) -> oldval\n\n\
1921Determine whether os.[lf]stat represents time stamps as float objects.\n\
Larry Hastings2f936352014-08-05 14:04:04 +10001922\n\
1923If value is True, future calls to stat() return floats; if it is False,\n\
1924future calls return ints.\n\
1925If value is omitted, return the current setting.\n");
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001926
Larry Hastings2f936352014-08-05 14:04:04 +10001927/* AC 3.5: the public default value should be None, not ready for that yet */
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001928static PyObject*
1929stat_float_times(PyObject* self, PyObject *args)
1930{
Victor Stinner8c62be82010-05-06 00:08:46 +00001931 int newval = -1;
1932 if (!PyArg_ParseTuple(args, "|i:stat_float_times", &newval))
1933 return NULL;
Victor Stinner034d0aa2012-06-05 01:22:15 +02001934 if (PyErr_WarnEx(PyExc_DeprecationWarning,
1935 "stat_float_times() is deprecated",
1936 1))
1937 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00001938 if (newval == -1)
1939 /* Return old value */
1940 return PyBool_FromLong(_stat_float_times);
1941 _stat_float_times = newval;
1942 Py_INCREF(Py_None);
1943 return Py_None;
Martin v. Löwisf607bda2002-10-16 18:27:39 +00001944}
Guido van Rossum98bf58f2001-10-18 20:34:25 +00001945
Larry Hastings6fe20b32012-04-19 15:07:49 -07001946static PyObject *billion = NULL;
1947
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001948static void
Victor Stinner4195b5c2012-02-08 23:03:19 +01001949fill_time(PyObject *v, int index, time_t sec, unsigned long nsec)
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001950{
Larry Hastings6fe20b32012-04-19 15:07:49 -07001951 PyObject *s = _PyLong_FromTime_t(sec);
1952 PyObject *ns_fractional = PyLong_FromUnsignedLong(nsec);
1953 PyObject *s_in_ns = NULL;
1954 PyObject *ns_total = NULL;
1955 PyObject *float_s = NULL;
1956
1957 if (!(s && ns_fractional))
1958 goto exit;
1959
1960 s_in_ns = PyNumber_Multiply(s, billion);
1961 if (!s_in_ns)
1962 goto exit;
1963
1964 ns_total = PyNumber_Add(s_in_ns, ns_fractional);
1965 if (!ns_total)
1966 goto exit;
1967
Victor Stinner4195b5c2012-02-08 23:03:19 +01001968 if (_stat_float_times) {
Larry Hastings6fe20b32012-04-19 15:07:49 -07001969 float_s = PyFloat_FromDouble(sec + 1e-9*nsec);
1970 if (!float_s)
1971 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00001972 }
Larry Hastings6fe20b32012-04-19 15:07:49 -07001973 else {
1974 float_s = s;
1975 Py_INCREF(float_s);
1976 }
1977
1978 PyStructSequence_SET_ITEM(v, index, s);
1979 PyStructSequence_SET_ITEM(v, index+3, float_s);
1980 PyStructSequence_SET_ITEM(v, index+6, ns_total);
1981 s = NULL;
1982 float_s = NULL;
1983 ns_total = NULL;
1984exit:
1985 Py_XDECREF(s);
1986 Py_XDECREF(ns_fractional);
1987 Py_XDECREF(s_in_ns);
1988 Py_XDECREF(ns_total);
1989 Py_XDECREF(float_s);
Martin v. Löwis94717ed2002-09-09 14:24:16 +00001990}
1991
Tim Peters5aa91602002-01-30 05:46:57 +00001992/* pack a system stat C structure into the Python stat tuple
Fred Drake699f3522000-06-29 21:12:41 +00001993 (used by posix_stat() and posix_fstat()) */
1994static PyObject*
Victor Stinner4195b5c2012-02-08 23:03:19 +01001995_pystat_fromstructstat(STRUCT_STAT *st)
Fred Drake699f3522000-06-29 21:12:41 +00001996{
Victor Stinner8c62be82010-05-06 00:08:46 +00001997 unsigned long ansec, mnsec, cnsec;
1998 PyObject *v = PyStructSequence_New(&StatResultType);
1999 if (v == NULL)
2000 return NULL;
Fred Drake699f3522000-06-29 21:12:41 +00002001
Victor Stinner8c62be82010-05-06 00:08:46 +00002002 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long)st->st_mode));
Fred Drake699f3522000-06-29 21:12:41 +00002003#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002004 PyStructSequence_SET_ITEM(v, 1,
2005 PyLong_FromLongLong((PY_LONG_LONG)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002006#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002007 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long)st->st_ino));
Fred Drake699f3522000-06-29 21:12:41 +00002008#endif
Serhiy Storchaka404fa922013-01-02 18:22:23 +02002009#ifdef MS_WINDOWS
2010 PyStructSequence_SET_ITEM(v, 2, PyLong_FromUnsignedLong(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002011#else
Serhiy Storchakab2653b32015-01-18 11:12:11 +02002012 PyStructSequence_SET_ITEM(v, 2, _PyLong_FromDev(st->st_dev));
Fred Drake699f3522000-06-29 21:12:41 +00002013#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002014 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long)st->st_nlink));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02002015#if defined(MS_WINDOWS)
2016 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong(0));
2017 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong(0));
2018#else
2019 PyStructSequence_SET_ITEM(v, 4, _PyLong_FromUid(st->st_uid));
2020 PyStructSequence_SET_ITEM(v, 5, _PyLong_FromGid(st->st_gid));
2021#endif
Fred Drake699f3522000-06-29 21:12:41 +00002022#ifdef HAVE_LARGEFILE_SUPPORT
Victor Stinner8c62be82010-05-06 00:08:46 +00002023 PyStructSequence_SET_ITEM(v, 6,
2024 PyLong_FromLongLong((PY_LONG_LONG)st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002025#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002026 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong(st->st_size));
Fred Drake699f3522000-06-29 21:12:41 +00002027#endif
Martin v. Löwis94717ed2002-09-09 14:24:16 +00002028
Martin v. Löwis14694662006-02-03 12:54:16 +00002029#if defined(HAVE_STAT_TV_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002030 ansec = st->st_atim.tv_nsec;
2031 mnsec = st->st_mtim.tv_nsec;
2032 cnsec = st->st_ctim.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002033#elif defined(HAVE_STAT_TV_NSEC2)
Victor Stinner8c62be82010-05-06 00:08:46 +00002034 ansec = st->st_atimespec.tv_nsec;
2035 mnsec = st->st_mtimespec.tv_nsec;
2036 cnsec = st->st_ctimespec.tv_nsec;
Martin v. Löwis14694662006-02-03 12:54:16 +00002037#elif defined(HAVE_STAT_NSEC)
Victor Stinner8c62be82010-05-06 00:08:46 +00002038 ansec = st->st_atime_nsec;
2039 mnsec = st->st_mtime_nsec;
2040 cnsec = st->st_ctime_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002041#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002042 ansec = mnsec = cnsec = 0;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002043#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002044 fill_time(v, 7, st->st_atime, ansec);
2045 fill_time(v, 8, st->st_mtime, mnsec);
2046 fill_time(v, 9, st->st_ctime, cnsec);
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002047
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002048#ifdef HAVE_STRUCT_STAT_ST_BLKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +00002049 PyStructSequence_SET_ITEM(v, ST_BLKSIZE_IDX,
2050 PyLong_FromLong((long)st->st_blksize));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002051#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002052#ifdef HAVE_STRUCT_STAT_ST_BLOCKS
Victor Stinner8c62be82010-05-06 00:08:46 +00002053 PyStructSequence_SET_ITEM(v, ST_BLOCKS_IDX,
2054 PyLong_FromLong((long)st->st_blocks));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00002055#endif
Martin v. Löwis60a5d722002-10-16 20:28:25 +00002056#ifdef HAVE_STRUCT_STAT_ST_RDEV
Victor Stinner8c62be82010-05-06 00:08:46 +00002057 PyStructSequence_SET_ITEM(v, ST_RDEV_IDX,
2058 PyLong_FromLong((long)st->st_rdev));
Fred Drake699f3522000-06-29 21:12:41 +00002059#endif
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002060#ifdef HAVE_STRUCT_STAT_ST_GEN
Victor Stinner8c62be82010-05-06 00:08:46 +00002061 PyStructSequence_SET_ITEM(v, ST_GEN_IDX,
2062 PyLong_FromLong((long)st->st_gen));
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002063#endif
2064#ifdef HAVE_STRUCT_STAT_ST_BIRTHTIME
Victor Stinner8c62be82010-05-06 00:08:46 +00002065 {
Victor Stinner4195b5c2012-02-08 23:03:19 +01002066 PyObject *val;
2067 unsigned long bsec,bnsec;
2068 bsec = (long)st->st_birthtime;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002069#ifdef HAVE_STAT_TV_NSEC2
Victor Stinner4195b5c2012-02-08 23:03:19 +01002070 bnsec = st->st_birthtimespec.tv_nsec;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002071#else
Victor Stinner4195b5c2012-02-08 23:03:19 +01002072 bnsec = 0;
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002073#endif
Victor Stinner4195b5c2012-02-08 23:03:19 +01002074 if (_stat_float_times) {
2075 val = PyFloat_FromDouble(bsec + 1e-9*bnsec);
2076 } else {
2077 val = PyLong_FromLong((long)bsec);
2078 }
2079 PyStructSequence_SET_ITEM(v, ST_BIRTHTIME_IDX,
2080 val);
Victor Stinner8c62be82010-05-06 00:08:46 +00002081 }
Martin v. Löwisebd9d5b2005-08-09 15:00:59 +00002082#endif
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002083#ifdef HAVE_STRUCT_STAT_ST_FLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00002084 PyStructSequence_SET_ITEM(v, ST_FLAGS_IDX,
2085 PyLong_FromLong((long)st->st_flags));
Hye-Shik Chang5f937a72005-06-02 13:09:30 +00002086#endif
Zachary Ware63f277b2014-06-19 09:46:37 -05002087#ifdef HAVE_STRUCT_STAT_ST_FILE_ATTRIBUTES
2088 PyStructSequence_SET_ITEM(v, ST_FILE_ATTRIBUTES_IDX,
2089 PyLong_FromUnsignedLong(st->st_file_attributes));
2090#endif
Fred Drake699f3522000-06-29 21:12:41 +00002091
Victor Stinner8c62be82010-05-06 00:08:46 +00002092 if (PyErr_Occurred()) {
2093 Py_DECREF(v);
2094 return NULL;
2095 }
Fred Drake699f3522000-06-29 21:12:41 +00002096
Victor Stinner8c62be82010-05-06 00:08:46 +00002097 return v;
Fred Drake699f3522000-06-29 21:12:41 +00002098}
2099
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002100/* POSIX methods */
2101
Guido van Rossum94f6f721999-01-06 18:42:14 +00002102
2103static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02002104posix_do_stat(const char *function_name, path_t *path,
Larry Hastings9cf065c2012-06-22 16:30:09 -07002105 int dir_fd, int follow_symlinks)
Guido van Rossum94f6f721999-01-06 18:42:14 +00002106{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002107 STRUCT_STAT st;
2108 int result;
2109
2110#if !defined(MS_WINDOWS) && !defined(HAVE_FSTATAT) && !defined(HAVE_LSTAT)
2111 if (follow_symlinks_specified(function_name, follow_symlinks))
2112 return NULL;
2113#endif
2114
2115 if (path_and_dir_fd_invalid("stat", path, dir_fd) ||
2116 dir_fd_and_fd_invalid("stat", dir_fd, path->fd) ||
2117 fd_and_follow_symlinks_invalid("stat", path->fd, follow_symlinks))
2118 return NULL;
2119
2120 Py_BEGIN_ALLOW_THREADS
2121 if (path->fd != -1)
2122 result = FSTAT(path->fd, &st);
2123 else
2124#ifdef MS_WINDOWS
2125 if (path->wide) {
2126 if (follow_symlinks)
2127 result = win32_stat_w(path->wide, &st);
2128 else
2129 result = win32_lstat_w(path->wide, &st);
2130 }
2131 else
2132#endif
2133#if defined(HAVE_LSTAT) || defined(MS_WINDOWS)
2134 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
2135 result = LSTAT(path->narrow, &st);
2136 else
2137#endif
2138#ifdef HAVE_FSTATAT
2139 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks)
2140 result = fstatat(dir_fd, path->narrow, &st,
2141 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2142 else
2143#endif
2144 result = STAT(path->narrow, &st);
2145 Py_END_ALLOW_THREADS
2146
Victor Stinner292c8352012-10-30 02:17:38 +01002147 if (result != 0) {
2148 return path_error(path);
2149 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07002150
2151 return _pystat_fromstructstat(&st);
2152}
2153
Larry Hastings2f936352014-08-05 14:04:04 +10002154/*[python input]
2155
2156for s in """
2157
2158FACCESSAT
2159FCHMODAT
2160FCHOWNAT
2161FSTATAT
2162LINKAT
2163MKDIRAT
2164MKFIFOAT
2165MKNODAT
2166OPENAT
2167READLINKAT
2168SYMLINKAT
2169UNLINKAT
2170
2171""".strip().split():
2172 s = s.strip()
2173 print("""
2174#ifdef HAVE_{s}
2175 #define {s}_DIR_FD_CONVERTER dir_fd_converter
Larry Hastings31826802013-10-19 00:09:25 -07002176#else
Larry Hastings2f936352014-08-05 14:04:04 +10002177 #define {s}_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings31826802013-10-19 00:09:25 -07002178#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002179""".rstrip().format(s=s))
2180
2181for s in """
2182
2183FCHDIR
2184FCHMOD
2185FCHOWN
2186FDOPENDIR
2187FEXECVE
2188FPATHCONF
2189FSTATVFS
2190FTRUNCATE
2191
2192""".strip().split():
2193 s = s.strip()
2194 print("""
2195#ifdef HAVE_{s}
2196 #define PATH_HAVE_{s} 1
2197#else
2198 #define PATH_HAVE_{s} 0
2199#endif
2200
2201""".rstrip().format(s=s))
2202[python start generated code]*/
2203
2204#ifdef HAVE_FACCESSAT
2205 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_converter
2206#else
2207 #define FACCESSAT_DIR_FD_CONVERTER dir_fd_unavailable
2208#endif
2209
2210#ifdef HAVE_FCHMODAT
2211 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_converter
2212#else
2213 #define FCHMODAT_DIR_FD_CONVERTER dir_fd_unavailable
2214#endif
2215
2216#ifdef HAVE_FCHOWNAT
2217 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_converter
2218#else
2219 #define FCHOWNAT_DIR_FD_CONVERTER dir_fd_unavailable
2220#endif
2221
2222#ifdef HAVE_FSTATAT
2223 #define FSTATAT_DIR_FD_CONVERTER dir_fd_converter
2224#else
2225 #define FSTATAT_DIR_FD_CONVERTER dir_fd_unavailable
2226#endif
2227
2228#ifdef HAVE_LINKAT
2229 #define LINKAT_DIR_FD_CONVERTER dir_fd_converter
2230#else
2231 #define LINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2232#endif
2233
2234#ifdef HAVE_MKDIRAT
2235 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_converter
2236#else
2237 #define MKDIRAT_DIR_FD_CONVERTER dir_fd_unavailable
2238#endif
2239
2240#ifdef HAVE_MKFIFOAT
2241 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_converter
2242#else
2243 #define MKFIFOAT_DIR_FD_CONVERTER dir_fd_unavailable
2244#endif
2245
2246#ifdef HAVE_MKNODAT
2247 #define MKNODAT_DIR_FD_CONVERTER dir_fd_converter
2248#else
2249 #define MKNODAT_DIR_FD_CONVERTER dir_fd_unavailable
2250#endif
2251
2252#ifdef HAVE_OPENAT
2253 #define OPENAT_DIR_FD_CONVERTER dir_fd_converter
2254#else
2255 #define OPENAT_DIR_FD_CONVERTER dir_fd_unavailable
2256#endif
2257
2258#ifdef HAVE_READLINKAT
2259 #define READLINKAT_DIR_FD_CONVERTER dir_fd_converter
2260#else
2261 #define READLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2262#endif
2263
2264#ifdef HAVE_SYMLINKAT
2265 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_converter
2266#else
2267 #define SYMLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2268#endif
2269
2270#ifdef HAVE_UNLINKAT
2271 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_converter
2272#else
2273 #define UNLINKAT_DIR_FD_CONVERTER dir_fd_unavailable
2274#endif
2275
2276#ifdef HAVE_FCHDIR
2277 #define PATH_HAVE_FCHDIR 1
2278#else
2279 #define PATH_HAVE_FCHDIR 0
2280#endif
2281
2282#ifdef HAVE_FCHMOD
2283 #define PATH_HAVE_FCHMOD 1
2284#else
2285 #define PATH_HAVE_FCHMOD 0
2286#endif
2287
2288#ifdef HAVE_FCHOWN
2289 #define PATH_HAVE_FCHOWN 1
2290#else
2291 #define PATH_HAVE_FCHOWN 0
2292#endif
2293
2294#ifdef HAVE_FDOPENDIR
2295 #define PATH_HAVE_FDOPENDIR 1
2296#else
2297 #define PATH_HAVE_FDOPENDIR 0
2298#endif
2299
2300#ifdef HAVE_FEXECVE
2301 #define PATH_HAVE_FEXECVE 1
2302#else
2303 #define PATH_HAVE_FEXECVE 0
2304#endif
2305
2306#ifdef HAVE_FPATHCONF
2307 #define PATH_HAVE_FPATHCONF 1
2308#else
2309 #define PATH_HAVE_FPATHCONF 0
2310#endif
2311
2312#ifdef HAVE_FSTATVFS
2313 #define PATH_HAVE_FSTATVFS 1
2314#else
2315 #define PATH_HAVE_FSTATVFS 0
2316#endif
2317
2318#ifdef HAVE_FTRUNCATE
2319 #define PATH_HAVE_FTRUNCATE 1
2320#else
2321 #define PATH_HAVE_FTRUNCATE 0
2322#endif
2323/*[python end generated code: output=4bd4f6f7d41267f1 input=80b4c890b6774ea5]*/
Larry Hastings31826802013-10-19 00:09:25 -07002324
Steve Dowerfe0a41a2015-03-20 19:50:46 -07002325#ifdef MS_WINDOWS
2326 #undef PATH_HAVE_FTRUNCATE
2327 #define PATH_HAVE_FTRUNCATE 1
2328#endif
Larry Hastings31826802013-10-19 00:09:25 -07002329
Larry Hastings61272b72014-01-07 12:41:53 -08002330/*[python input]
Larry Hastings31826802013-10-19 00:09:25 -07002331
2332class path_t_converter(CConverter):
2333
2334 type = "path_t"
2335 impl_by_reference = True
2336 parse_by_reference = True
2337
2338 converter = 'path_converter'
2339
2340 def converter_init(self, *, allow_fd=False, nullable=False):
Larry Hastings31826802013-10-19 00:09:25 -07002341 # right now path_t doesn't support default values.
2342 # to support a default value, you'll need to override initialize().
Larry Hastings2f936352014-08-05 14:04:04 +10002343 if self.default not in (unspecified, None):
Larry Hastings7726ac92014-01-31 22:03:12 -08002344 fail("Can't specify a default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002345
Larry Hastings2f936352014-08-05 14:04:04 +10002346 if self.c_default not in (None, 'Py_None'):
2347 raise RuntimeError("Can't specify a c_default to the path_t converter!")
Larry Hastings31826802013-10-19 00:09:25 -07002348
2349 self.nullable = nullable
2350 self.allow_fd = allow_fd
2351
Larry Hastings7726ac92014-01-31 22:03:12 -08002352 def pre_render(self):
2353 def strify(value):
Larry Hastings2f936352014-08-05 14:04:04 +10002354 if isinstance(value, str):
2355 return value
Larry Hastings7726ac92014-01-31 22:03:12 -08002356 return str(int(bool(value)))
2357
2358 # add self.py_name here when merging with posixmodule conversion
Larry Hastings2f936352014-08-05 14:04:04 +10002359 self.c_default = 'PATH_T_INITIALIZE("{}", "{}", {}, {})'.format(
Larry Hastings31826802013-10-19 00:09:25 -07002360 self.function.name,
Larry Hastings2f936352014-08-05 14:04:04 +10002361 self.name,
Larry Hastings7726ac92014-01-31 22:03:12 -08002362 strify(self.nullable),
2363 strify(self.allow_fd),
Larry Hastings31826802013-10-19 00:09:25 -07002364 )
2365
2366 def cleanup(self):
2367 return "path_cleanup(&" + self.name + ");\n"
2368
2369
2370class dir_fd_converter(CConverter):
2371 type = 'int'
Larry Hastings31826802013-10-19 00:09:25 -07002372
Larry Hastings2f936352014-08-05 14:04:04 +10002373 def converter_init(self, requires=None):
Larry Hastings31826802013-10-19 00:09:25 -07002374 if self.default in (unspecified, None):
2375 self.c_default = 'DEFAULT_DIR_FD'
Larry Hastings2f936352014-08-05 14:04:04 +10002376 if isinstance(requires, str):
2377 self.converter = requires.upper() + '_DIR_FD_CONVERTER'
2378 else:
2379 self.converter = 'dir_fd_converter'
Larry Hastings31826802013-10-19 00:09:25 -07002380
Larry Hastings2f936352014-08-05 14:04:04 +10002381class fildes_converter(CConverter):
2382 type = 'int'
2383 converter = 'fildes_converter'
2384
2385class uid_t_converter(CConverter):
2386 type = "uid_t"
2387 converter = '_Py_Uid_Converter'
2388
2389class gid_t_converter(CConverter):
2390 type = "gid_t"
2391 converter = '_Py_Gid_Converter'
2392
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002393class dev_t_converter(CConverter):
2394 type = 'dev_t'
2395 converter = '_Py_Dev_Converter'
2396
2397class dev_t_return_converter(unsigned_long_return_converter):
2398 type = 'dev_t'
2399 conversion_fn = '_PyLong_FromDev'
2400 unsigned_cast = '(dev_t)'
2401
Larry Hastings2f936352014-08-05 14:04:04 +10002402class FSConverter_converter(CConverter):
2403 type = 'PyObject *'
2404 converter = 'PyUnicode_FSConverter'
2405 def converter_init(self):
2406 if self.default is not unspecified:
2407 fail("FSConverter_converter does not support default values")
2408 self.c_default = 'NULL'
2409
2410 def cleanup(self):
2411 return "Py_XDECREF(" + self.name + ");\n"
2412
2413class pid_t_converter(CConverter):
2414 type = 'pid_t'
2415 format_unit = '" _Py_PARSE_PID "'
2416
2417class idtype_t_converter(int_converter):
2418 type = 'idtype_t'
2419
2420class id_t_converter(CConverter):
2421 type = 'id_t'
2422 format_unit = '" _Py_PARSE_PID "'
2423
2424class Py_intptr_t_converter(CConverter):
2425 type = 'Py_intptr_t'
2426 format_unit = '" _Py_PARSE_INTPTR "'
2427
2428class Py_off_t_converter(CConverter):
2429 type = 'Py_off_t'
2430 converter = 'Py_off_t_converter'
2431
2432class Py_off_t_return_converter(long_return_converter):
2433 type = 'Py_off_t'
2434 conversion_fn = 'PyLong_FromPy_off_t'
2435
2436class path_confname_converter(CConverter):
2437 type="int"
2438 converter="conv_path_confname"
2439
2440class confstr_confname_converter(path_confname_converter):
2441 converter='conv_confstr_confname'
2442
2443class sysconf_confname_converter(path_confname_converter):
2444 converter="conv_sysconf_confname"
2445
2446class sched_param_converter(CConverter):
2447 type = 'struct sched_param'
2448 converter = 'convert_sched_param'
2449 impl_by_reference = True;
Larry Hastings31826802013-10-19 00:09:25 -07002450
Larry Hastings61272b72014-01-07 12:41:53 -08002451[python start generated code]*/
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02002452/*[python end generated code: output=da39a3ee5e6b4b0d input=affe68316f160401]*/
Larry Hastings31826802013-10-19 00:09:25 -07002453
Larry Hastings61272b72014-01-07 12:41:53 -08002454/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002455
Larry Hastings2a727912014-01-16 11:32:01 -08002456os.stat
Larry Hastings31826802013-10-19 00:09:25 -07002457
2458 path : path_t(allow_fd=True)
2459 Path to be examined; can be string, bytes, or open-file-descriptor int.
2460
2461 *
2462
Larry Hastings2f936352014-08-05 14:04:04 +10002463 dir_fd : dir_fd(requires='fstatat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002464 If not None, it should be a file descriptor open to a directory,
2465 and path should be a relative string; path will then be relative to
2466 that directory.
2467
2468 follow_symlinks: bool = True
2469 If False, and the last element of the path is a symbolic link,
2470 stat will examine the symbolic link itself instead of the file
2471 the link points to.
2472
2473Perform a stat system call on the given path.
2474
2475dir_fd and follow_symlinks may not be implemented
2476 on your platform. If they are unavailable, using them will raise a
2477 NotImplementedError.
2478
2479It's an error to use dir_fd or follow_symlinks when specifying path as
2480 an open file descriptor.
2481
Larry Hastings61272b72014-01-07 12:41:53 -08002482[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002483
Larry Hastings31826802013-10-19 00:09:25 -07002484static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002485os_stat_impl(PyModuleDef *module, path_t *path, int dir_fd,
2486 int follow_symlinks)
2487/*[clinic end generated code: output=e4f7569f95d523ca input=099d356c306fa24a]*/
Larry Hastings31826802013-10-19 00:09:25 -07002488{
2489 return posix_do_stat("stat", path, dir_fd, follow_symlinks);
2490}
2491
Larry Hastings2f936352014-08-05 14:04:04 +10002492
2493/*[clinic input]
2494os.lstat
2495
2496 path : path_t
2497
2498 *
2499
2500 dir_fd : dir_fd(requires='fstatat') = None
2501
2502Perform a stat system call on the given path, without following symbolic links.
2503
2504Like stat(), but do not follow symbolic links.
2505Equivalent to stat(path, follow_symlinks=False).
2506[clinic start generated code]*/
2507
Larry Hastings2f936352014-08-05 14:04:04 +10002508static PyObject *
2509os_lstat_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002510/*[clinic end generated code: output=7a748e333fcb39bd input=0b7474765927b925]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002511{
2512 int follow_symlinks = 0;
2513 return posix_do_stat("lstat", path, dir_fd, follow_symlinks);
2514}
Larry Hastings31826802013-10-19 00:09:25 -07002515
Larry Hastings2f936352014-08-05 14:04:04 +10002516
Larry Hastings61272b72014-01-07 12:41:53 -08002517/*[clinic input]
Larry Hastings2f936352014-08-05 14:04:04 +10002518os.access -> bool
Larry Hastings31826802013-10-19 00:09:25 -07002519
2520 path: path_t(allow_fd=True)
2521 Path to be tested; can be string, bytes, or open-file-descriptor int.
2522
2523 mode: int
2524 Operating-system mode bitfield. Can be F_OK to test existence,
2525 or the inclusive-OR of R_OK, W_OK, and X_OK.
2526
2527 *
2528
Larry Hastings2f936352014-08-05 14:04:04 +10002529 dir_fd : dir_fd(requires='faccessat') = None
Larry Hastings31826802013-10-19 00:09:25 -07002530 If not None, it should be a file descriptor open to a directory,
2531 and path should be relative; path will then be relative to that
2532 directory.
2533
2534 effective_ids: bool = False
2535 If True, access will use the effective uid/gid instead of
2536 the real uid/gid.
2537
2538 follow_symlinks: bool = True
2539 If False, and the last element of the path is a symbolic link,
2540 access will examine the symbolic link itself instead of the file
2541 the link points to.
2542
2543Use the real uid/gid to test for access to a path.
2544
2545{parameters}
2546dir_fd, effective_ids, and follow_symlinks may not be implemented
2547 on your platform. If they are unavailable, using them will raise a
2548 NotImplementedError.
2549
2550Note that most operations will use the effective uid/gid, therefore this
2551 routine can be used in a suid/sgid environment to test if the invoking user
2552 has the specified access to the path.
2553
Larry Hastings61272b72014-01-07 12:41:53 -08002554[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002555
Larry Hastings2f936352014-08-05 14:04:04 +10002556static int
Larry Hastings89964c42015-04-14 18:07:59 -04002557os_access_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd,
2558 int effective_ids, int follow_symlinks)
2559/*[clinic end generated code: output=abaa53340210088d input=b75a756797af45ec]*/
Larry Hastings31826802013-10-19 00:09:25 -07002560{
Larry Hastings2f936352014-08-05 14:04:04 +10002561 int return_value;
Victor Stinner8c62be82010-05-06 00:08:46 +00002562
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002563#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002564 DWORD attr;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002565#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07002566 int result;
Thomas Wouters477c8d52006-05-27 19:21:47 +00002567#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07002568
Larry Hastings9cf065c2012-06-22 16:30:09 -07002569#ifndef HAVE_FACCESSAT
2570 if (follow_symlinks_specified("access", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002571 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002572
2573 if (effective_ids) {
2574 argument_unavailable_error("access", "effective_ids");
Larry Hastings2f936352014-08-05 14:04:04 +10002575 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002576 }
2577#endif
2578
2579#ifdef MS_WINDOWS
2580 Py_BEGIN_ALLOW_THREADS
Christian Heimesebe83f92013-10-19 22:36:17 +02002581 if (path->wide != NULL)
2582 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002583 else
Christian Heimesebe83f92013-10-19 22:36:17 +02002584 attr = GetFileAttributesA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002585 Py_END_ALLOW_THREADS
2586
2587 /*
Georg Brandlf7875592012-06-24 13:58:31 +02002588 * Access is possible if
Larry Hastings9cf065c2012-06-22 16:30:09 -07002589 * * we didn't get a -1, and
2590 * * write access wasn't requested,
2591 * * or the file isn't read-only,
2592 * * or it's a directory.
2593 * (Directories cannot be read-only on Windows.)
2594 */
Larry Hastings2f936352014-08-05 14:04:04 +10002595 return_value = (attr != INVALID_FILE_ATTRIBUTES) &&
Georg Brandl5bb7aa92012-06-23 12:48:40 +02002596 (!(mode & 2) ||
Larry Hastings9cf065c2012-06-22 16:30:09 -07002597 !(attr & FILE_ATTRIBUTE_READONLY) ||
Larry Hastings2f936352014-08-05 14:04:04 +10002598 (attr & FILE_ATTRIBUTE_DIRECTORY));
Larry Hastings9cf065c2012-06-22 16:30:09 -07002599#else
2600
2601 Py_BEGIN_ALLOW_THREADS
2602#ifdef HAVE_FACCESSAT
2603 if ((dir_fd != DEFAULT_DIR_FD) ||
2604 effective_ids ||
2605 !follow_symlinks) {
2606 int flags = 0;
2607 if (!follow_symlinks)
2608 flags |= AT_SYMLINK_NOFOLLOW;
2609 if (effective_ids)
2610 flags |= AT_EACCESS;
Larry Hastings31826802013-10-19 00:09:25 -07002611 result = faccessat(dir_fd, path->narrow, mode, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002612 }
2613 else
2614#endif
Larry Hastings31826802013-10-19 00:09:25 -07002615 result = access(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002616 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002617 return_value = !result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002618#endif
2619
Larry Hastings9cf065c2012-06-22 16:30:09 -07002620 return return_value;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002621}
2622
Guido van Rossumd371ff11999-01-25 16:12:23 +00002623#ifndef F_OK
2624#define F_OK 0
2625#endif
2626#ifndef R_OK
2627#define R_OK 4
2628#endif
2629#ifndef W_OK
2630#define W_OK 2
2631#endif
2632#ifndef X_OK
2633#define X_OK 1
2634#endif
2635
Larry Hastings31826802013-10-19 00:09:25 -07002636
Guido van Rossumd371ff11999-01-25 16:12:23 +00002637#ifdef HAVE_TTYNAME
Larry Hastings61272b72014-01-07 12:41:53 -08002638/*[clinic input]
Larry Hastings31826802013-10-19 00:09:25 -07002639os.ttyname -> DecodeFSDefault
2640
2641 fd: int
2642 Integer file descriptor handle.
2643
2644 /
2645
2646Return the name of the terminal device connected to 'fd'.
Larry Hastings61272b72014-01-07 12:41:53 -08002647[clinic start generated code]*/
Larry Hastings31826802013-10-19 00:09:25 -07002648
Larry Hastings31826802013-10-19 00:09:25 -07002649static char *
Larry Hastingsebdcb502013-11-23 14:54:00 -08002650os_ttyname_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002651/*[clinic end generated code: output=03ad3d5ccaef75c3 input=5f72ca83e76b3b45]*/
Larry Hastings31826802013-10-19 00:09:25 -07002652{
2653 char *ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002654
Larry Hastings31826802013-10-19 00:09:25 -07002655 ret = ttyname(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00002656 if (ret == NULL)
Larry Hastings31826802013-10-19 00:09:25 -07002657 posix_error();
2658 return ret;
Guido van Rossum94f6f721999-01-06 18:42:14 +00002659}
Guido van Rossumd371ff11999-01-25 16:12:23 +00002660#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00002661
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002662#ifdef HAVE_CTERMID
Larry Hastings2f936352014-08-05 14:04:04 +10002663/*[clinic input]
2664os.ctermid
2665
2666Return the name of the controlling terminal for this process.
2667[clinic start generated code]*/
2668
Larry Hastings2f936352014-08-05 14:04:04 +10002669static PyObject *
2670os_ctermid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002671/*[clinic end generated code: output=1b73788201e0aebd input=3b87fdd52556382d]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002672{
Victor Stinner8c62be82010-05-06 00:08:46 +00002673 char *ret;
2674 char buffer[L_ctermid];
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002675
Greg Wardb48bc172000-03-01 21:51:56 +00002676#ifdef USE_CTERMID_R
Victor Stinner8c62be82010-05-06 00:08:46 +00002677 ret = ctermid_r(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002678#else
Victor Stinner8c62be82010-05-06 00:08:46 +00002679 ret = ctermid(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002680#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00002681 if (ret == NULL)
2682 return posix_error();
Victor Stinner5fe6de82010-08-15 09:12:51 +00002683 return PyUnicode_DecodeFSDefault(buffer);
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002684}
Larry Hastings2f936352014-08-05 14:04:04 +10002685#endif /* HAVE_CTERMID */
Fred Drake5ab8eaf1999-12-09 21:13:07 +00002686
Larry Hastings2f936352014-08-05 14:04:04 +10002687
2688/*[clinic input]
2689os.chdir
2690
2691 path: path_t(allow_fd='PATH_HAVE_FCHDIR')
2692
2693Change the current working directory to the specified path.
2694
2695path may always be specified as a string.
2696On some platforms, path may also be specified as an open file descriptor.
2697 If this functionality is unavailable, using it raises an exception.
2698[clinic start generated code]*/
2699
Larry Hastings2f936352014-08-05 14:04:04 +10002700static PyObject *
2701os_chdir_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002702/*[clinic end generated code: output=7358e3a20fb5aa93 input=1a4a15b4d12cb15d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002703{
2704 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002705
2706 Py_BEGIN_ALLOW_THREADS
2707#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10002708 if (path->wide)
2709 result = win32_wchdir(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002710 else
Larry Hastings2f936352014-08-05 14:04:04 +10002711 result = win32_chdir(path->narrow);
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03002712 result = !result; /* on unix, success = 0, on windows, success = !0 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07002713#else
2714#ifdef HAVE_FCHDIR
Larry Hastings2f936352014-08-05 14:04:04 +10002715 if (path->fd != -1)
2716 result = fchdir(path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002717 else
2718#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002719 result = chdir(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002720#endif
2721 Py_END_ALLOW_THREADS
2722
2723 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10002724 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002725 }
2726
Larry Hastings2f936352014-08-05 14:04:04 +10002727 Py_RETURN_NONE;
2728}
2729
2730
2731#ifdef HAVE_FCHDIR
2732/*[clinic input]
2733os.fchdir
2734
2735 fd: fildes
2736
2737Change to the directory of the given file descriptor.
2738
2739fd must be opened on a directory, not a file.
2740Equivalent to os.chdir(fd).
2741
2742[clinic start generated code]*/
2743
Fred Drake4d1e64b2002-04-15 19:40:07 +00002744static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10002745os_fchdir_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002746/*[clinic end generated code: output=361d30df6b2d3418 input=18e816479a2fa985]*/
Fred Drake4d1e64b2002-04-15 19:40:07 +00002747{
Larry Hastings2f936352014-08-05 14:04:04 +10002748 return posix_fildes_fd(fd, fchdir);
Fred Drake4d1e64b2002-04-15 19:40:07 +00002749}
2750#endif /* HAVE_FCHDIR */
2751
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002752
Larry Hastings2f936352014-08-05 14:04:04 +10002753/*[clinic input]
2754os.chmod
2755
2756 path: path_t(allow_fd='PATH_HAVE_FCHMOD')
2757 Path to be modified. May always be specified as a str or bytes.
2758 On some platforms, path may also be specified as an open file descriptor.
2759 If this functionality is unavailable, using it raises an exception.
2760
2761 mode: int
2762 Operating-system mode bitfield.
2763
2764 *
2765
2766 dir_fd : dir_fd(requires='fchmodat') = None
2767 If not None, it should be a file descriptor open to a directory,
2768 and path should be relative; path will then be relative to that
2769 directory.
2770
2771 follow_symlinks: bool = True
2772 If False, and the last element of the path is a symbolic link,
2773 chmod will modify the symbolic link itself instead of the file
2774 the link points to.
2775
2776Change the access permissions of a file.
2777
2778It is an error to use dir_fd or follow_symlinks when specifying path as
2779 an open file descriptor.
2780dir_fd and follow_symlinks may not be implemented on your platform.
2781 If they are unavailable, using them will raise a NotImplementedError.
2782
2783[clinic start generated code]*/
2784
Larry Hastings2f936352014-08-05 14:04:04 +10002785static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002786os_chmod_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd,
2787 int follow_symlinks)
2788/*[clinic end generated code: output=05e7f73b1a843ba2 input=7f1618e5e15cc196]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002789{
Larry Hastings9cf065c2012-06-22 16:30:09 -07002790 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002791
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00002792#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002793 DWORD attr;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002794#endif
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00002795
Larry Hastings9cf065c2012-06-22 16:30:09 -07002796#ifdef HAVE_FCHMODAT
2797 int fchmodat_nofollow_unsupported = 0;
2798#endif
2799
Larry Hastings9cf065c2012-06-22 16:30:09 -07002800#if !(defined(HAVE_FCHMODAT) || defined(HAVE_LCHMOD))
2801 if (follow_symlinks_specified("chmod", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002802 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002803#endif
2804
2805#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00002806 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10002807 if (path->wide)
2808 attr = GetFileAttributesW(path->wide);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002809 else
Larry Hastings2f936352014-08-05 14:04:04 +10002810 attr = GetFileAttributesA(path->narrow);
Tim Golden23005082013-10-25 11:22:37 +01002811 if (attr == INVALID_FILE_ATTRIBUTES)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002812 result = 0;
2813 else {
2814 if (mode & _S_IWRITE)
Victor Stinner8c62be82010-05-06 00:08:46 +00002815 attr &= ~FILE_ATTRIBUTE_READONLY;
2816 else
2817 attr |= FILE_ATTRIBUTE_READONLY;
Larry Hastings2f936352014-08-05 14:04:04 +10002818 if (path->wide)
2819 result = SetFileAttributesW(path->wide, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002820 else
Larry Hastings2f936352014-08-05 14:04:04 +10002821 result = SetFileAttributesA(path->narrow, attr);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002822 }
2823 Py_END_ALLOW_THREADS
2824
2825 if (!result) {
Larry Hastings2f936352014-08-05 14:04:04 +10002826 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002827 }
2828#else /* MS_WINDOWS */
2829 Py_BEGIN_ALLOW_THREADS
2830#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002831 if (path->fd != -1)
2832 result = fchmod(path->fd, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002833 else
2834#endif
2835#ifdef HAVE_LCHMOD
2836 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10002837 result = lchmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002838 else
2839#endif
2840#ifdef HAVE_FCHMODAT
2841 if ((dir_fd != DEFAULT_DIR_FD) || !follow_symlinks) {
2842 /*
2843 * fchmodat() doesn't currently support AT_SYMLINK_NOFOLLOW!
2844 * The documentation specifically shows how to use it,
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07002845 * and then says it isn't implemented yet.
2846 * (true on linux with glibc 2.15, and openindiana 3.x)
Larry Hastings9cf065c2012-06-22 16:30:09 -07002847 *
2848 * Once it is supported, os.chmod will automatically
2849 * support dir_fd and follow_symlinks=False. (Hopefully.)
2850 * Until then, we need to be careful what exception we raise.
2851 */
Larry Hastings2f936352014-08-05 14:04:04 +10002852 result = fchmodat(dir_fd, path->narrow, mode,
Larry Hastings9cf065c2012-06-22 16:30:09 -07002853 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
2854 /*
2855 * But wait! We can't throw the exception without allowing threads,
2856 * and we can't do that in this nested scope. (Macro trickery, sigh.)
2857 */
2858 fchmodat_nofollow_unsupported =
Larry Hastingsdbbc0c82012-06-22 19:50:21 -07002859 result &&
2860 ((errno == ENOTSUP) || (errno == EOPNOTSUPP)) &&
2861 !follow_symlinks;
Victor Stinner8c62be82010-05-06 00:08:46 +00002862 }
2863 else
Thomas Wouters477c8d52006-05-27 19:21:47 +00002864#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002865 result = chmod(path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002866 Py_END_ALLOW_THREADS
2867
2868 if (result) {
2869#ifdef HAVE_FCHMODAT
2870 if (fchmodat_nofollow_unsupported) {
2871 if (dir_fd != DEFAULT_DIR_FD)
2872 dir_fd_and_follow_symlinks_invalid("chmod",
2873 dir_fd, follow_symlinks);
2874 else
2875 follow_symlinks_specified("chmod", follow_symlinks);
2876 }
2877 else
2878#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002879 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002880 }
2881#endif
2882
Larry Hastings2f936352014-08-05 14:04:04 +10002883 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00002884}
2885
Larry Hastings9cf065c2012-06-22 16:30:09 -07002886
Christian Heimes4e30a842007-11-30 22:12:06 +00002887#ifdef HAVE_FCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002888/*[clinic input]
2889os.fchmod
2890
2891 fd: int
2892 mode: int
2893
2894Change the access permissions of the file given by file descriptor fd.
2895
2896Equivalent to os.chmod(fd, mode).
2897[clinic start generated code]*/
2898
Larry Hastings2f936352014-08-05 14:04:04 +10002899static PyObject *
2900os_fchmod_impl(PyModuleDef *module, int fd, int mode)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002901/*[clinic end generated code: output=2ee31ca226d1ed33 input=8ab11975ca01ee5b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002902{
2903 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00002904 int async_err = 0;
2905
2906 do {
2907 Py_BEGIN_ALLOW_THREADS
2908 res = fchmod(fd, mode);
2909 Py_END_ALLOW_THREADS
2910 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
2911 if (res != 0)
2912 return (!async_err) ? posix_error() : NULL;
2913
Victor Stinner8c62be82010-05-06 00:08:46 +00002914 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00002915}
2916#endif /* HAVE_FCHMOD */
2917
Larry Hastings2f936352014-08-05 14:04:04 +10002918
Christian Heimes4e30a842007-11-30 22:12:06 +00002919#ifdef HAVE_LCHMOD
Larry Hastings2f936352014-08-05 14:04:04 +10002920/*[clinic input]
2921os.lchmod
2922
2923 path: path_t
2924 mode: int
2925
2926Change the access permissions of a file, without following symbolic links.
2927
2928If path is a symlink, this affects the link itself rather than the target.
2929Equivalent to chmod(path, mode, follow_symlinks=False)."
2930[clinic start generated code]*/
2931
Larry Hastings2f936352014-08-05 14:04:04 +10002932static PyObject *
2933os_lchmod_impl(PyModuleDef *module, path_t *path, int mode)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03002934/*[clinic end generated code: output=7c0cc46588d89e46 input=90c5663c7465d24f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002935{
Victor Stinner8c62be82010-05-06 00:08:46 +00002936 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00002937 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10002938 res = lchmod(path->narrow, mode);
Victor Stinner8c62be82010-05-06 00:08:46 +00002939 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01002940 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10002941 path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01002942 return NULL;
2943 }
Victor Stinner8c62be82010-05-06 00:08:46 +00002944 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00002945}
2946#endif /* HAVE_LCHMOD */
2947
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00002948
Thomas Wouterscf297e42007-02-23 15:07:44 +00002949#ifdef HAVE_CHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10002950/*[clinic input]
2951os.chflags
2952
2953 path: path_t
2954 flags: unsigned_long(bitwise=True)
2955 follow_symlinks: bool=True
2956
2957Set file flags.
2958
2959If follow_symlinks is False, and the last element of the path is a symbolic
2960 link, chflags will change flags on the symbolic link itself instead of the
2961 file the link points to.
2962follow_symlinks may not be implemented on your platform. If it is
2963unavailable, using it will raise a NotImplementedError.
2964
2965[clinic start generated code]*/
2966
Larry Hastings2f936352014-08-05 14:04:04 +10002967static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04002968os_chflags_impl(PyModuleDef *module, path_t *path, unsigned long flags,
2969 int follow_symlinks)
2970/*[clinic end generated code: output=ff2d6e73534a95b9 input=0327e29feb876236]*/
Larry Hastings2f936352014-08-05 14:04:04 +10002971{
2972 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002973
2974#ifndef HAVE_LCHFLAGS
2975 if (follow_symlinks_specified("chflags", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10002976 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07002977#endif
2978
Victor Stinner8c62be82010-05-06 00:08:46 +00002979 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07002980#ifdef HAVE_LCHFLAGS
2981 if (!follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +10002982 result = lchflags(path->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002983 else
2984#endif
Larry Hastings2f936352014-08-05 14:04:04 +10002985 result = chflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00002986 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07002987
Larry Hastings2f936352014-08-05 14:04:04 +10002988 if (result)
2989 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07002990
Larry Hastings2f936352014-08-05 14:04:04 +10002991 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00002992}
2993#endif /* HAVE_CHFLAGS */
2994
Larry Hastings2f936352014-08-05 14:04:04 +10002995
Thomas Wouterscf297e42007-02-23 15:07:44 +00002996#ifdef HAVE_LCHFLAGS
Larry Hastings2f936352014-08-05 14:04:04 +10002997/*[clinic input]
2998os.lchflags
2999
3000 path: path_t
3001 flags: unsigned_long(bitwise=True)
3002
3003Set file flags.
3004
3005This function will not follow symbolic links.
3006Equivalent to chflags(path, flags, follow_symlinks=False).
3007[clinic start generated code]*/
3008
Larry Hastings2f936352014-08-05 14:04:04 +10003009static PyObject *
3010os_lchflags_impl(PyModuleDef *module, path_t *path, unsigned long flags)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003011/*[clinic end generated code: output=6741322fb949661b input=f9f82ea8b585ca9d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003012{
Victor Stinner8c62be82010-05-06 00:08:46 +00003013 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003014 Py_BEGIN_ALLOW_THREADS
Larry Hastingsb1dc1122014-08-05 16:06:16 +10003015 res = lchflags(path->narrow, flags);
Victor Stinner8c62be82010-05-06 00:08:46 +00003016 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003017 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003018 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003019 }
Victor Stinner292c8352012-10-30 02:17:38 +01003020 Py_RETURN_NONE;
Thomas Wouterscf297e42007-02-23 15:07:44 +00003021}
3022#endif /* HAVE_LCHFLAGS */
3023
Larry Hastings2f936352014-08-05 14:04:04 +10003024
Martin v. Löwis244edc82001-10-04 22:44:26 +00003025#ifdef HAVE_CHROOT
Larry Hastings2f936352014-08-05 14:04:04 +10003026/*[clinic input]
3027os.chroot
3028 path: path_t
3029
3030Change root directory to path.
3031
3032[clinic start generated code]*/
3033
Larry Hastings2f936352014-08-05 14:04:04 +10003034static PyObject *
3035os_chroot_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003036/*[clinic end generated code: output=b6dbfabe74ecaa9d input=14822965652c3dc3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003037{
3038 int res;
3039 Py_BEGIN_ALLOW_THREADS
3040 res = chroot(path->narrow);
3041 Py_END_ALLOW_THREADS
3042 if (res < 0)
3043 return path_error(path);
3044 Py_RETURN_NONE;
3045}
3046#endif /* HAVE_CHROOT */
3047
Martin v. Löwis244edc82001-10-04 22:44:26 +00003048
Guido van Rossum21142a01999-01-08 21:05:37 +00003049#ifdef HAVE_FSYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003050/*[clinic input]
3051os.fsync
3052
3053 fd: fildes
3054
3055Force write of fd to disk.
3056[clinic start generated code]*/
3057
Larry Hastings2f936352014-08-05 14:04:04 +10003058static PyObject *
3059os_fsync_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003060/*[clinic end generated code: output=83a350851064aea7 input=21c3645c056967f2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003061{
3062 return posix_fildes_fd(fd, fsync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003063}
3064#endif /* HAVE_FSYNC */
3065
Larry Hastings2f936352014-08-05 14:04:04 +10003066
Ross Lagerwall7807c352011-03-17 20:20:30 +02003067#ifdef HAVE_SYNC
Larry Hastings2f936352014-08-05 14:04:04 +10003068/*[clinic input]
3069os.sync
3070
3071Force write of everything to disk.
3072[clinic start generated code]*/
3073
Larry Hastings2f936352014-08-05 14:04:04 +10003074static PyObject *
3075os_sync_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003076/*[clinic end generated code: output=ba524f656c201c40 input=84749fe5e9b404ff]*/
Ross Lagerwall7807c352011-03-17 20:20:30 +02003077{
3078 Py_BEGIN_ALLOW_THREADS
3079 sync();
3080 Py_END_ALLOW_THREADS
3081 Py_RETURN_NONE;
3082}
Larry Hastings2f936352014-08-05 14:04:04 +10003083#endif /* HAVE_SYNC */
3084
Ross Lagerwall7807c352011-03-17 20:20:30 +02003085
Guido van Rossum21142a01999-01-08 21:05:37 +00003086#ifdef HAVE_FDATASYNC
Guido van Rossum7f58e2e2000-09-22 17:26:14 +00003087#ifdef __hpux
Guido van Rossumecc23b02000-09-22 16:01:05 +00003088extern int fdatasync(int); /* On HP-UX, in libc but not in unistd.h */
3089#endif
3090
Larry Hastings2f936352014-08-05 14:04:04 +10003091/*[clinic input]
3092os.fdatasync
3093
3094 fd: fildes
3095
3096Force write of fd to disk without forcing update of metadata.
3097[clinic start generated code]*/
3098
Larry Hastings2f936352014-08-05 14:04:04 +10003099static PyObject *
3100os_fdatasync_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003101/*[clinic end generated code: output=e0f04a3aff515b75 input=bc74791ee54dd291]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003102{
3103 return posix_fildes_fd(fd, fdatasync);
Guido van Rossum21142a01999-01-08 21:05:37 +00003104}
3105#endif /* HAVE_FDATASYNC */
3106
3107
Fredrik Lundh10723342000-07-10 16:38:09 +00003108#ifdef HAVE_CHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003109/*[clinic input]
3110os.chown
3111
3112 path : path_t(allow_fd='PATH_HAVE_FCHOWN')
3113 Path to be examined; can be string, bytes, or open-file-descriptor int.
3114
3115 uid: uid_t
3116
3117 gid: gid_t
3118
3119 *
3120
3121 dir_fd : dir_fd(requires='fchownat') = None
3122 If not None, it should be a file descriptor open to a directory,
3123 and path should be relative; path will then be relative to that
3124 directory.
3125
3126 follow_symlinks: bool = True
3127 If False, and the last element of the path is a symbolic link,
3128 stat will examine the symbolic link itself instead of the file
3129 the link points to.
3130
3131Change the owner and group id of path to the numeric uid and gid.\
3132
3133path may always be specified as a string.
3134On some platforms, path may also be specified as an open file descriptor.
3135 If this functionality is unavailable, using it raises an exception.
3136If dir_fd is not None, it should be a file descriptor open to a directory,
3137 and path should be relative; path will then be relative to that directory.
3138If follow_symlinks is False, and the last element of the path is a symbolic
3139 link, chown will modify the symbolic link itself instead of the file the
3140 link points to.
3141It is an error to use dir_fd or follow_symlinks when specifying path as
3142 an open file descriptor.
3143dir_fd and follow_symlinks may not be implemented on your platform.
3144 If they are unavailable, using them will raise a NotImplementedError.
3145
3146[clinic start generated code]*/
3147
Larry Hastings2f936352014-08-05 14:04:04 +10003148static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04003149os_chown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid,
3150 int dir_fd, int follow_symlinks)
3151/*[clinic end generated code: output=e0a4559f394dbd91 input=a61cc35574814d5d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003152{
3153 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003154
3155#if !(defined(HAVE_LCHOWN) || defined(HAVE_FCHOWNAT))
3156 if (follow_symlinks_specified("chown", follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003157 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003158#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003159 if (dir_fd_and_fd_invalid("chown", dir_fd, path->fd) ||
3160 fd_and_follow_symlinks_invalid("chown", path->fd, follow_symlinks))
3161 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003162
3163#ifdef __APPLE__
3164 /*
3165 * This is for Mac OS X 10.3, which doesn't have lchown.
3166 * (But we still have an lchown symbol because of weak-linking.)
3167 * It doesn't have fchownat either. So there's no possibility
3168 * of a graceful failover.
Georg Brandlf7875592012-06-24 13:58:31 +02003169 */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003170 if ((!follow_symlinks) && (lchown == NULL)) {
3171 follow_symlinks_specified("chown", follow_symlinks);
Larry Hastings2f936352014-08-05 14:04:04 +10003172 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003173 }
3174#endif
3175
Victor Stinner8c62be82010-05-06 00:08:46 +00003176 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003177#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003178 if (path->fd != -1)
3179 result = fchown(path->fd, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003180 else
3181#endif
3182#ifdef HAVE_LCHOWN
3183 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10003184 result = lchown(path->narrow, uid, gid);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003185 else
3186#endif
3187#ifdef HAVE_FCHOWNAT
3188 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003189 result = fchownat(dir_fd, path->narrow, uid, gid,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003190 follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW);
3191 else
3192#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003193 result = chown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00003194 Py_END_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003195
Larry Hastings2f936352014-08-05 14:04:04 +10003196 if (result)
3197 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003198
Larry Hastings2f936352014-08-05 14:04:04 +10003199 Py_RETURN_NONE;
Guido van Rossumb6775db1994-08-01 11:34:53 +00003200}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00003201#endif /* HAVE_CHOWN */
Guido van Rossumb6775db1994-08-01 11:34:53 +00003202
Larry Hastings2f936352014-08-05 14:04:04 +10003203
Christian Heimes4e30a842007-11-30 22:12:06 +00003204#ifdef HAVE_FCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003205/*[clinic input]
3206os.fchown
3207
3208 fd: int
3209 uid: uid_t
3210 gid: gid_t
3211
3212Change the owner and group id of the file specified by file descriptor.
3213
3214Equivalent to os.chown(fd, uid, gid).
3215
3216[clinic start generated code]*/
3217
Larry Hastings2f936352014-08-05 14:04:04 +10003218static PyObject *
3219os_fchown_impl(PyModuleDef *module, int fd, uid_t uid, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003220/*[clinic end generated code: output=7545abf8f6086d76 input=3af544ba1b13a0d7]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003221{
Victor Stinner8c62be82010-05-06 00:08:46 +00003222 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00003223 int async_err = 0;
3224
3225 do {
3226 Py_BEGIN_ALLOW_THREADS
3227 res = fchown(fd, uid, gid);
3228 Py_END_ALLOW_THREADS
3229 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
3230 if (res != 0)
3231 return (!async_err) ? posix_error() : NULL;
3232
Victor Stinner8c62be82010-05-06 00:08:46 +00003233 Py_RETURN_NONE;
Christian Heimes4e30a842007-11-30 22:12:06 +00003234}
3235#endif /* HAVE_FCHOWN */
3236
Larry Hastings2f936352014-08-05 14:04:04 +10003237
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00003238#ifdef HAVE_LCHOWN
Larry Hastings2f936352014-08-05 14:04:04 +10003239/*[clinic input]
3240os.lchown
3241
3242 path : path_t
3243 uid: uid_t
3244 gid: gid_t
3245
3246Change the owner and group id of path to the numeric uid and gid.
3247
3248This function will not follow symbolic links.
3249Equivalent to os.chown(path, uid, gid, follow_symlinks=False).
3250[clinic start generated code]*/
3251
Larry Hastings2f936352014-08-05 14:04:04 +10003252static PyObject *
3253os_lchown_impl(PyModuleDef *module, path_t *path, uid_t uid, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003254/*[clinic end generated code: output=bb0d2da1579ac275 input=b1c6014d563a7161]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003255{
Victor Stinner8c62be82010-05-06 00:08:46 +00003256 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00003257 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003258 res = lchown(path->narrow, uid, gid);
Victor Stinner8c62be82010-05-06 00:08:46 +00003259 Py_END_ALLOW_THREADS
Victor Stinner292c8352012-10-30 02:17:38 +01003260 if (res < 0) {
Larry Hastings2f936352014-08-05 14:04:04 +10003261 return path_error(path);
Victor Stinner292c8352012-10-30 02:17:38 +01003262 }
Larry Hastings2f936352014-08-05 14:04:04 +10003263 Py_RETURN_NONE;
Martin v. Löwis0cec0ff2002-07-28 16:33:45 +00003264}
3265#endif /* HAVE_LCHOWN */
3266
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003267
Barry Warsaw53699e91996-12-10 23:23:01 +00003268static PyObject *
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003269posix_getcwd(int use_bytes)
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003270{
Victor Stinner4403d7d2015-04-25 00:16:10 +02003271 char *buf, *tmpbuf;
3272 char *cwd;
3273 const size_t chunk = 1024;
3274 size_t buflen = 0;
3275 PyObject *obj;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003276
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003277#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003278 if (!use_bytes) {
Victor Stinner4403d7d2015-04-25 00:16:10 +02003279 wchar_t wbuf[MAXPATHLEN];
Victor Stinner8c62be82010-05-06 00:08:46 +00003280 wchar_t *wbuf2 = wbuf;
3281 PyObject *resobj;
3282 DWORD len;
3283 Py_BEGIN_ALLOW_THREADS
Victor Stinner75875072013-11-24 19:23:25 +01003284 len = GetCurrentDirectoryW(Py_ARRAY_LENGTH(wbuf), wbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00003285 /* If the buffer is large enough, len does not include the
3286 terminating \0. If the buffer is too small, len includes
3287 the space needed for the terminator. */
Victor Stinner75875072013-11-24 19:23:25 +01003288 if (len >= Py_ARRAY_LENGTH(wbuf)) {
Victor Stinnerb6404912013-07-07 16:21:41 +02003289 wbuf2 = PyMem_RawMalloc(len * sizeof(wchar_t));
Victor Stinner8c62be82010-05-06 00:08:46 +00003290 if (wbuf2)
3291 len = GetCurrentDirectoryW(len, wbuf2);
3292 }
3293 Py_END_ALLOW_THREADS
3294 if (!wbuf2) {
3295 PyErr_NoMemory();
3296 return NULL;
3297 }
3298 if (!len) {
Victor Stinnerb024e842012-10-31 22:24:06 +01003299 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003300 PyMem_RawFree(wbuf2);
Victor Stinnerb024e842012-10-31 22:24:06 +01003301 return PyErr_SetFromWindowsErr(0);
Victor Stinner8c62be82010-05-06 00:08:46 +00003302 }
3303 resobj = PyUnicode_FromWideChar(wbuf2, len);
Victor Stinnerb024e842012-10-31 22:24:06 +01003304 if (wbuf2 != wbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003305 PyMem_RawFree(wbuf2);
Victor Stinner8c62be82010-05-06 00:08:46 +00003306 return resobj;
3307 }
Victor Stinnerf7c5ae22011-11-16 23:43:07 +01003308
3309 if (win32_warn_bytes_api())
3310 return NULL;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003311#endif
3312
Victor Stinner4403d7d2015-04-25 00:16:10 +02003313 buf = cwd = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003314 Py_BEGIN_ALLOW_THREADS
Victor Stinner4403d7d2015-04-25 00:16:10 +02003315 do {
3316 buflen += chunk;
Victor Stinnerc44f7072016-03-14 18:07:53 +01003317#ifdef MS_WINDOWS
3318 if (buflen > INT_MAX) {
3319 PyErr_NoMemory();
3320 break;
3321 }
3322#endif
Victor Stinner4403d7d2015-04-25 00:16:10 +02003323 tmpbuf = PyMem_RawRealloc(buf, buflen);
3324 if (tmpbuf == NULL)
3325 break;
3326
3327 buf = tmpbuf;
Victor Stinnerc44f7072016-03-14 18:07:53 +01003328#ifdef MS_WINDOWS
3329 cwd = getcwd(buf, (int)buflen);
3330#else
Victor Stinner4403d7d2015-04-25 00:16:10 +02003331 cwd = getcwd(buf, buflen);
Victor Stinnerc44f7072016-03-14 18:07:53 +01003332#endif
Victor Stinner4403d7d2015-04-25 00:16:10 +02003333 } while (cwd == NULL && errno == ERANGE);
Victor Stinner8c62be82010-05-06 00:08:46 +00003334 Py_END_ALLOW_THREADS
Victor Stinner4403d7d2015-04-25 00:16:10 +02003335
3336 if (cwd == NULL) {
3337 PyMem_RawFree(buf);
Victor Stinner8c62be82010-05-06 00:08:46 +00003338 return posix_error();
Victor Stinner4403d7d2015-04-25 00:16:10 +02003339 }
3340
Victor Stinner8c62be82010-05-06 00:08:46 +00003341 if (use_bytes)
Victor Stinner4403d7d2015-04-25 00:16:10 +02003342 obj = PyBytes_FromStringAndSize(buf, strlen(buf));
3343 else
3344 obj = PyUnicode_DecodeFSDefault(buf);
3345 PyMem_RawFree(buf);
3346
3347 return obj;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003348}
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003349
Larry Hastings2f936352014-08-05 14:04:04 +10003350
3351/*[clinic input]
3352os.getcwd
3353
3354Return a unicode string representing the current working directory.
3355[clinic start generated code]*/
3356
Larry Hastings2f936352014-08-05 14:04:04 +10003357static PyObject *
3358os_getcwd_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003359/*[clinic end generated code: output=efe3a8c0121525ea input=f069211bb70e3d39]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003360{
3361 return posix_getcwd(0);
3362}
3363
Larry Hastings2f936352014-08-05 14:04:04 +10003364
3365/*[clinic input]
3366os.getcwdb
3367
3368Return a bytes string representing the current working directory.
3369[clinic start generated code]*/
3370
Larry Hastings2f936352014-08-05 14:04:04 +10003371static PyObject *
3372os_getcwdb_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003373/*[clinic end generated code: output=7fce42ee4b2a296a input=f6f6a378dad3d9cb]*/
Guido van Rossumf0af3e32008-10-02 18:55:37 +00003374{
3375 return posix_getcwd(1);
3376}
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003377
Larry Hastings2f936352014-08-05 14:04:04 +10003378
Larry Hastings9cf065c2012-06-22 16:30:09 -07003379#if ((!defined(HAVE_LINK)) && defined(MS_WINDOWS))
3380#define HAVE_LINK 1
3381#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00003382
Guido van Rossumb6775db1994-08-01 11:34:53 +00003383#ifdef HAVE_LINK
Larry Hastings2f936352014-08-05 14:04:04 +10003384/*[clinic input]
3385
3386os.link
3387
3388 src : path_t
3389 dst : path_t
3390 *
3391 src_dir_fd : dir_fd = None
3392 dst_dir_fd : dir_fd = None
3393 follow_symlinks: bool = True
3394
3395Create a hard link to a file.
3396
3397If either src_dir_fd or dst_dir_fd is not None, it should be a file
3398 descriptor open to a directory, and the respective path string (src or dst)
3399 should be relative; the path will then be relative to that directory.
3400If follow_symlinks is False, and the last element of src is a symbolic
3401 link, link will create a link to the symbolic link itself instead of the
3402 file the link points to.
3403src_dir_fd, dst_dir_fd, and follow_symlinks may not be implemented on your
3404 platform. If they are unavailable, using them will raise a
3405 NotImplementedError.
3406[clinic start generated code]*/
3407
Larry Hastings2f936352014-08-05 14:04:04 +10003408static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04003409os_link_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd,
3410 int dst_dir_fd, int follow_symlinks)
3411/*[clinic end generated code: output=f47a7e88f7b391b6 input=b0095ebbcbaa7e04]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003412{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003413#ifdef MS_WINDOWS
3414 BOOL result;
3415#else
3416 int result;
3417#endif
3418
Larry Hastings9cf065c2012-06-22 16:30:09 -07003419#ifndef HAVE_LINKAT
3420 if ((src_dir_fd != DEFAULT_DIR_FD) || (dst_dir_fd != DEFAULT_DIR_FD)) {
3421 argument_unavailable_error("link", "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10003422 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003423 }
3424#endif
3425
Larry Hastings2f936352014-08-05 14:04:04 +10003426 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003427 PyErr_SetString(PyExc_NotImplementedError,
3428 "link: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10003429 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003430 }
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00003431
Brian Curtin1b9df392010-11-24 20:24:31 +00003432#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003433 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003434 if (src->wide)
3435 result = CreateHardLinkW(dst->wide, src->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003436 else
Larry Hastings2f936352014-08-05 14:04:04 +10003437 result = CreateHardLinkA(dst->narrow, src->narrow, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003438 Py_END_ALLOW_THREADS
Brian Curtin1b9df392010-11-24 20:24:31 +00003439
Larry Hastings2f936352014-08-05 14:04:04 +10003440 if (!result)
3441 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003442#else
3443 Py_BEGIN_ALLOW_THREADS
Larry Hastings67cbf7b2012-06-22 17:06:48 -07003444#ifdef HAVE_LINKAT
Larry Hastings9cf065c2012-06-22 16:30:09 -07003445 if ((src_dir_fd != DEFAULT_DIR_FD) ||
3446 (dst_dir_fd != DEFAULT_DIR_FD) ||
3447 (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10003448 result = linkat(src_dir_fd, src->narrow,
3449 dst_dir_fd, dst->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07003450 follow_symlinks ? AT_SYMLINK_FOLLOW : 0);
3451 else
3452#endif
Larry Hastings2f936352014-08-05 14:04:04 +10003453 result = link(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003454 Py_END_ALLOW_THREADS
Brian Curtinfc889c42010-11-28 23:59:46 +00003455
Larry Hastings2f936352014-08-05 14:04:04 +10003456 if (result)
3457 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003458#endif
3459
Larry Hastings2f936352014-08-05 14:04:04 +10003460 Py_RETURN_NONE;
Brian Curtin1b9df392010-11-24 20:24:31 +00003461}
Larry Hastings9cf065c2012-06-22 16:30:09 -07003462#endif
3463
Brian Curtin1b9df392010-11-24 20:24:31 +00003464
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003465#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
Barry Warsaw53699e91996-12-10 23:23:01 +00003466static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07003467_listdir_windows_no_opendir(path_t *path, PyObject *list)
Guido van Rossumb6775db1994-08-01 11:34:53 +00003468{
Larry Hastings9cf065c2012-06-22 16:30:09 -07003469 PyObject *v;
3470 HANDLE hFindFile = INVALID_HANDLE_VALUE;
3471 BOOL result;
3472 WIN32_FIND_DATA FileData;
Victor Stinner75875072013-11-24 19:23:25 +01003473 char namebuf[MAX_PATH+4]; /* Overallocate for "\*.*" */
Larry Hastings9cf065c2012-06-22 16:30:09 -07003474 /* only claim to have space for MAX_PATH */
Victor Stinner75875072013-11-24 19:23:25 +01003475 Py_ssize_t len = Py_ARRAY_LENGTH(namebuf)-4;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003476 wchar_t *wnamebuf = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003477
Gregory P. Smith40a21602013-03-20 20:52:50 -07003478 if (!path->narrow) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003479 WIN32_FIND_DATAW wFileData;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003480 wchar_t *po_wchars;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003481
Gregory P. Smith40a21602013-03-20 20:52:50 -07003482 if (!path->wide) { /* Default arg: "." */
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003483 po_wchars = L".";
3484 len = 1;
3485 } else {
Gregory P. Smith40a21602013-03-20 20:52:50 -07003486 po_wchars = path->wide;
3487 len = wcslen(path->wide);
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003488 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003489 /* The +5 is so we can append "\\*.*\0" */
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003490 wnamebuf = PyMem_New(wchar_t, len + 5);
Victor Stinner8c62be82010-05-06 00:08:46 +00003491 if (!wnamebuf) {
3492 PyErr_NoMemory();
Larry Hastings9cf065c2012-06-22 16:30:09 -07003493 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003494 }
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +00003495 wcscpy(wnamebuf, po_wchars);
Victor Stinner8c62be82010-05-06 00:08:46 +00003496 if (len > 0) {
Victor Stinnereb5657a2011-09-30 01:44:27 +02003497 wchar_t wch = wnamebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01003498 if (wch != SEP && wch != ALTSEP && wch != L':')
3499 wnamebuf[len++] = SEP;
Victor Stinner8c62be82010-05-06 00:08:46 +00003500 wcscpy(wnamebuf + len, L"*.*");
3501 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003502 if ((list = PyList_New(0)) == NULL) {
3503 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003504 }
Antoine Pitroub73caab2010-08-09 23:39:31 +00003505 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003506 hFindFile = FindFirstFileW(wnamebuf, &wFileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00003507 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003508 if (hFindFile == INVALID_HANDLE_VALUE) {
3509 int error = GetLastError();
Larry Hastings9cf065c2012-06-22 16:30:09 -07003510 if (error == ERROR_FILE_NOT_FOUND)
3511 goto exit;
3512 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003513 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003514 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003515 }
3516 do {
3517 /* Skip over . and .. */
3518 if (wcscmp(wFileData.cFileName, L".") != 0 &&
3519 wcscmp(wFileData.cFileName, L"..") != 0) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003520 v = PyUnicode_FromWideChar(wFileData.cFileName,
3521 wcslen(wFileData.cFileName));
Victor Stinner8c62be82010-05-06 00:08:46 +00003522 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003523 Py_DECREF(list);
3524 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003525 break;
3526 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003527 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003528 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003529 Py_DECREF(list);
3530 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003531 break;
3532 }
3533 Py_DECREF(v);
3534 }
3535 Py_BEGIN_ALLOW_THREADS
3536 result = FindNextFileW(hFindFile, &wFileData);
3537 Py_END_ALLOW_THREADS
3538 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
3539 it got to the end of the directory. */
3540 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003541 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003542 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003543 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003544 }
3545 } while (result == TRUE);
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +00003546
Larry Hastings9cf065c2012-06-22 16:30:09 -07003547 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003548 }
Gregory P. Smith40a21602013-03-20 20:52:50 -07003549 strcpy(namebuf, path->narrow);
3550 len = path->length;
Victor Stinner8c62be82010-05-06 00:08:46 +00003551 if (len > 0) {
3552 char ch = namebuf[len-1];
Tim Golden781bbeb2013-10-25 20:24:06 +01003553 if (ch != '\\' && ch != '/' && ch != ':')
3554 namebuf[len++] = '\\';
Victor Stinner8c62be82010-05-06 00:08:46 +00003555 strcpy(namebuf + len, "*.*");
3556 }
Guido van Rossumb6775db1994-08-01 11:34:53 +00003557
Larry Hastings9cf065c2012-06-22 16:30:09 -07003558 if ((list = PyList_New(0)) == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +00003559 return NULL;
Guido van Rossumb6775db1994-08-01 11:34:53 +00003560
Antoine Pitroub73caab2010-08-09 23:39:31 +00003561 Py_BEGIN_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003562 hFindFile = FindFirstFile(namebuf, &FileData);
Antoine Pitroub73caab2010-08-09 23:39:31 +00003563 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00003564 if (hFindFile == INVALID_HANDLE_VALUE) {
3565 int error = GetLastError();
3566 if (error == ERROR_FILE_NOT_FOUND)
Larry Hastings9cf065c2012-06-22 16:30:09 -07003567 goto exit;
3568 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003569 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003570 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003571 }
3572 do {
3573 /* Skip over . and .. */
3574 if (strcmp(FileData.cFileName, ".") != 0 &&
3575 strcmp(FileData.cFileName, "..") != 0) {
3576 v = PyBytes_FromString(FileData.cFileName);
3577 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003578 Py_DECREF(list);
3579 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003580 break;
3581 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003582 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003583 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003584 Py_DECREF(list);
3585 list = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00003586 break;
3587 }
3588 Py_DECREF(v);
3589 }
3590 Py_BEGIN_ALLOW_THREADS
3591 result = FindNextFile(hFindFile, &FileData);
3592 Py_END_ALLOW_THREADS
3593 /* FindNextFile sets error to ERROR_NO_MORE_FILES if
3594 it got to the end of the directory. */
3595 if (!result && GetLastError() != ERROR_NO_MORE_FILES) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003596 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003597 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003598 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003599 }
3600 } while (result == TRUE);
Guido van Rossumb6775db1994-08-01 11:34:53 +00003601
Larry Hastings9cf065c2012-06-22 16:30:09 -07003602exit:
3603 if (hFindFile != INVALID_HANDLE_VALUE) {
3604 if (FindClose(hFindFile) == FALSE) {
3605 if (list != NULL) {
3606 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003607 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003608 }
3609 }
Victor Stinner8c62be82010-05-06 00:08:46 +00003610 }
Victor Stinnerb6404912013-07-07 16:21:41 +02003611 PyMem_Free(wnamebuf);
Guido van Rossumb6775db1994-08-01 11:34:53 +00003612
Larry Hastings9cf065c2012-06-22 16:30:09 -07003613 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003614} /* end of _listdir_windows_no_opendir */
3615
3616#else /* thus POSIX, ie: not (MS_WINDOWS and not HAVE_OPENDIR) */
3617
3618static PyObject *
Gregory P. Smith40a21602013-03-20 20:52:50 -07003619_posix_listdir(path_t *path, PyObject *list)
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003620{
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003621 PyObject *v;
3622 DIR *dirp = NULL;
3623 struct dirent *ep;
3624 int return_str; /* if false, return bytes */
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003625#ifdef HAVE_FDOPENDIR
3626 int fd = -1;
3627#endif
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003628
Victor Stinner8c62be82010-05-06 00:08:46 +00003629 errno = 0;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003630#ifdef HAVE_FDOPENDIR
Gregory P. Smith40a21602013-03-20 20:52:50 -07003631 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003632 /* closedir() closes the FD, so we duplicate it */
Victor Stinnerdaf45552013-08-28 00:53:59 +02003633 fd = _Py_dup(path->fd);
Victor Stinnerf3266652013-12-19 13:24:49 +01003634 if (fd == -1)
3635 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07003636
Larry Hastingsfdaea062012-06-25 04:42:23 -07003637 return_str = 1;
3638
Larry Hastings9cf065c2012-06-22 16:30:09 -07003639 Py_BEGIN_ALLOW_THREADS
3640 dirp = fdopendir(fd);
3641 Py_END_ALLOW_THREADS
3642 }
3643 else
3644#endif
3645 {
Larry Hastingsfdaea062012-06-25 04:42:23 -07003646 char *name;
Gregory P. Smith40a21602013-03-20 20:52:50 -07003647 if (path->narrow) {
3648 name = path->narrow;
Larry Hastingsfdaea062012-06-25 04:42:23 -07003649 /* only return bytes if they specified a bytes object */
Gregory P. Smith40a21602013-03-20 20:52:50 -07003650 return_str = !(PyBytes_Check(path->object));
Larry Hastingsfdaea062012-06-25 04:42:23 -07003651 }
3652 else {
3653 name = ".";
3654 return_str = 1;
3655 }
3656
Larry Hastings9cf065c2012-06-22 16:30:09 -07003657 Py_BEGIN_ALLOW_THREADS
3658 dirp = opendir(name);
3659 Py_END_ALLOW_THREADS
3660 }
3661
3662 if (dirp == NULL) {
Gregory P. Smith40a21602013-03-20 20:52:50 -07003663 list = path_error(path);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003664#ifdef HAVE_FDOPENDIR
3665 if (fd != -1) {
3666 Py_BEGIN_ALLOW_THREADS
3667 close(fd);
3668 Py_END_ALLOW_THREADS
3669 }
3670#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07003671 goto exit;
3672 }
3673 if ((list = PyList_New(0)) == NULL) {
3674 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003675 }
3676 for (;;) {
3677 errno = 0;
3678 Py_BEGIN_ALLOW_THREADS
3679 ep = readdir(dirp);
3680 Py_END_ALLOW_THREADS
3681 if (ep == NULL) {
3682 if (errno == 0) {
3683 break;
3684 } else {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003685 Py_DECREF(list);
Gregory P. Smith40a21602013-03-20 20:52:50 -07003686 list = path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003687 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00003688 }
3689 }
3690 if (ep->d_name[0] == '.' &&
3691 (NAMLEN(ep) == 1 ||
3692 (ep->d_name[1] == '.' && NAMLEN(ep) == 2)))
3693 continue;
Larry Hastingsfdaea062012-06-25 04:42:23 -07003694 if (return_str)
Victor Stinnera45598a2010-05-14 16:35:39 +00003695 v = PyUnicode_DecodeFSDefaultAndSize(ep->d_name, NAMLEN(ep));
3696 else
3697 v = PyBytes_FromStringAndSize(ep->d_name, NAMLEN(ep));
Victor Stinner8c62be82010-05-06 00:08:46 +00003698 if (v == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07003699 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00003700 break;
3701 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07003702 if (PyList_Append(list, v) != 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00003703 Py_DECREF(v);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003704 Py_CLEAR(list);
Victor Stinner8c62be82010-05-06 00:08:46 +00003705 break;
3706 }
3707 Py_DECREF(v);
3708 }
Guido van Rossum0ee42cd1991-04-08 21:01:03 +00003709
Larry Hastings9cf065c2012-06-22 16:30:09 -07003710exit:
3711 if (dirp != NULL) {
3712 Py_BEGIN_ALLOW_THREADS
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003713#ifdef HAVE_FDOPENDIR
Larry Hastings9cf065c2012-06-22 16:30:09 -07003714 if (fd > -1)
3715 rewinddir(dirp);
Larry Hastings4dbc95e2013-08-01 18:18:56 -07003716#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07003717 closedir(dirp);
3718 Py_END_ALLOW_THREADS
3719 }
3720
Larry Hastings9cf065c2012-06-22 16:30:09 -07003721 return list;
Gregory P. Smith16ea14a2013-03-20 18:51:33 -07003722} /* end of _posix_listdir */
3723#endif /* which OS */
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00003724
Larry Hastings2f936352014-08-05 14:04:04 +10003725
3726/*[clinic input]
3727os.listdir
3728
3729 path : path_t(nullable=True, allow_fd='PATH_HAVE_FDOPENDIR') = None
3730
3731Return a list containing the names of the files in the directory.
3732
3733path can be specified as either str or bytes. If path is bytes,
3734 the filenames returned will also be bytes; in all other circumstances
3735 the filenames returned will be str.
3736If path is None, uses the path='.'.
3737On some platforms, path may also be specified as an open file descriptor;\
3738 the file descriptor must refer to a directory.
3739 If this functionality is unavailable, using it raises NotImplementedError.
3740
3741The list is in arbitrary order. It does not include the special
3742entries '.' and '..' even if they are present in the directory.
3743
3744
3745[clinic start generated code]*/
3746
Larry Hastings2f936352014-08-05 14:04:04 +10003747static PyObject *
3748os_listdir_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003749/*[clinic end generated code: output=1fbe67c1f780c8b7 input=09e300416e3cd729]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003750{
3751#if defined(MS_WINDOWS) && !defined(HAVE_OPENDIR)
3752 return _listdir_windows_no_opendir(path, NULL);
3753#else
3754 return _posix_listdir(path, NULL);
3755#endif
3756}
3757
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00003758#ifdef MS_WINDOWS
Mark Hammondef8b6542001-05-13 08:04:26 +00003759/* A helper function for abspath on win32 */
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003760/*[clinic input]
3761os._getfullpathname
Victor Stinnereb5657a2011-09-30 01:44:27 +02003762
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003763 path: path_t
3764 /
3765
3766[clinic start generated code]*/
3767
3768static PyObject *
3769os__getfullpathname_impl(PyModuleDef *module, path_t *path)
3770/*[clinic end generated code: output=b90b1f103b08773f input=332ed537c29d0a3e]*/
3771{
3772 if (!path->narrow)
Victor Stinnereb5657a2011-09-30 01:44:27 +02003773 {
Victor Stinner75875072013-11-24 19:23:25 +01003774 wchar_t woutbuf[MAX_PATH], *woutbufp = woutbuf;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003775 wchar_t *wtemp;
Victor Stinner8c62be82010-05-06 00:08:46 +00003776 DWORD result;
3777 PyObject *v;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003778
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003779 result = GetFullPathNameW(path->wide,
Victor Stinner63941882011-09-29 00:42:28 +02003780 Py_ARRAY_LENGTH(woutbuf),
Victor Stinner8c62be82010-05-06 00:08:46 +00003781 woutbuf, &wtemp);
Victor Stinner63941882011-09-29 00:42:28 +02003782 if (result > Py_ARRAY_LENGTH(woutbuf)) {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003783 woutbufp = PyMem_New(wchar_t, result);
Victor Stinner8c62be82010-05-06 00:08:46 +00003784 if (!woutbufp)
3785 return PyErr_NoMemory();
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003786 result = GetFullPathNameW(path->wide, result, woutbufp, &wtemp);
Victor Stinner8c62be82010-05-06 00:08:46 +00003787 }
3788 if (result)
Victor Stinner9d3b93b2011-11-22 02:27:30 +01003789 v = PyUnicode_FromWideChar(woutbufp, wcslen(woutbufp));
Victor Stinner8c62be82010-05-06 00:08:46 +00003790 else
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003791 v = win32_error_object("GetFullPathNameW", path->object);
Victor Stinner8c62be82010-05-06 00:08:46 +00003792 if (woutbufp != woutbuf)
Victor Stinnerb6404912013-07-07 16:21:41 +02003793 PyMem_Free(woutbufp);
Victor Stinner8c62be82010-05-06 00:08:46 +00003794 return v;
3795 }
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003796 else {
3797 char outbuf[MAX_PATH];
3798 char *temp;
Victor Stinnereb5657a2011-09-30 01:44:27 +02003799
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003800 if (!GetFullPathName(path->narrow, Py_ARRAY_LENGTH(outbuf),
3801 outbuf, &temp)) {
3802 win32_error_object("GetFullPathName", path->object);
3803 return NULL;
3804 }
3805 return PyBytes_FromString(outbuf);
Victor Stinner8c62be82010-05-06 00:08:46 +00003806 }
Larry Hastings2f936352014-08-05 14:04:04 +10003807}
Brian Curtind40e6f72010-07-08 21:39:08 +00003808
Brian Curtind25aef52011-06-13 15:16:04 -05003809
Larry Hastings2f936352014-08-05 14:04:04 +10003810/*[clinic input]
3811os._getfinalpathname
Brian Curtinf5e76d02010-11-24 13:14:05 +00003812
Larry Hastings2f936352014-08-05 14:04:04 +10003813 path: unicode
3814 /
3815
3816A helper function for samepath on windows.
3817[clinic start generated code]*/
3818
Larry Hastings2f936352014-08-05 14:04:04 +10003819static PyObject *
3820os__getfinalpathname_impl(PyModuleDef *module, PyObject *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003821/*[clinic end generated code: output=8be81a5f51a34bcf input=71d5e89334891bf4]*/
Brian Curtind40e6f72010-07-08 21:39:08 +00003822{
3823 HANDLE hFile;
3824 int buf_size;
3825 wchar_t *target_path;
3826 int result_length;
Larry Hastings2f936352014-08-05 14:04:04 +10003827 PyObject *result;
3828 wchar_t *path_wchar;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003829
Larry Hastings2f936352014-08-05 14:04:04 +10003830 path_wchar = PyUnicode_AsUnicode(path);
3831 if (path_wchar == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02003832 return NULL;
Brian Curtind40e6f72010-07-08 21:39:08 +00003833
Brian Curtind40e6f72010-07-08 21:39:08 +00003834 hFile = CreateFileW(
Larry Hastings2f936352014-08-05 14:04:04 +10003835 path_wchar,
Brian Curtind40e6f72010-07-08 21:39:08 +00003836 0, /* desired access */
3837 0, /* share mode */
3838 NULL, /* security attributes */
3839 OPEN_EXISTING,
3840 /* FILE_FLAG_BACKUP_SEMANTICS is required to open a directory */
3841 FILE_FLAG_BACKUP_SEMANTICS,
3842 NULL);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00003843
Victor Stinnereb5657a2011-09-30 01:44:27 +02003844 if(hFile == INVALID_HANDLE_VALUE)
Larry Hastings2f936352014-08-05 14:04:04 +10003845 return win32_error_object("CreateFileW", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003846
3847 /* We have a good handle to the target, use it to determine the
3848 target path name. */
Steve Dower2ea51c92015-03-20 21:49:12 -07003849 buf_size = GetFinalPathNameByHandleW(hFile, 0, 0, VOLUME_NAME_NT);
Brian Curtind40e6f72010-07-08 21:39:08 +00003850
3851 if(!buf_size)
Larry Hastings2f936352014-08-05 14:04:04 +10003852 return win32_error_object("GetFinalPathNameByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003853
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003854 target_path = PyMem_New(wchar_t, buf_size+1);
Brian Curtind40e6f72010-07-08 21:39:08 +00003855 if(!target_path)
3856 return PyErr_NoMemory();
3857
Steve Dower2ea51c92015-03-20 21:49:12 -07003858 result_length = GetFinalPathNameByHandleW(hFile, target_path,
3859 buf_size, VOLUME_NAME_DOS);
Brian Curtind40e6f72010-07-08 21:39:08 +00003860 if(!result_length)
Larry Hastings2f936352014-08-05 14:04:04 +10003861 return win32_error_object("GetFinalPathNamyByHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003862
3863 if(!CloseHandle(hFile))
Larry Hastings2f936352014-08-05 14:04:04 +10003864 return win32_error_object("CloseHandle", path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003865
3866 target_path[result_length] = 0;
Victor Stinner9d3b93b2011-11-22 02:27:30 +01003867 result = PyUnicode_FromWideChar(target_path, result_length);
Victor Stinnerb6404912013-07-07 16:21:41 +02003868 PyMem_Free(target_path);
Brian Curtind40e6f72010-07-08 21:39:08 +00003869 return result;
Larry Hastings2f936352014-08-05 14:04:04 +10003870}
Brian Curtin62857742010-09-06 17:07:27 +00003871
Brian Curtin95d028f2011-06-09 09:10:38 -05003872PyDoc_STRVAR(posix__isdir__doc__,
3873"Return true if the pathname refers to an existing directory.");
3874
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003875/*[clinic input]
3876os._isdir
3877
3878 path: path_t
3879 /
3880
3881[clinic start generated code]*/
3882
Brian Curtin9c669cc2011-06-08 18:17:18 -05003883static PyObject *
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003884os__isdir_impl(PyModuleDef *module, path_t *path)
3885/*[clinic end generated code: output=f17b2d4e1994b0ff input=e794f12faab62a2a]*/
Brian Curtin9c669cc2011-06-08 18:17:18 -05003886{
Brian Curtin9c669cc2011-06-08 18:17:18 -05003887 DWORD attributes;
3888
Serhiy Storchakaf0b50152015-05-13 00:52:39 +03003889 if (!path->narrow)
3890 attributes = GetFileAttributesW(path->wide);
3891 else
3892 attributes = GetFileAttributesA(path->narrow);
Brian Curtin9c669cc2011-06-08 18:17:18 -05003893
Brian Curtin9c669cc2011-06-08 18:17:18 -05003894 if (attributes == INVALID_FILE_ATTRIBUTES)
3895 Py_RETURN_FALSE;
3896
Brian Curtin9c669cc2011-06-08 18:17:18 -05003897 if (attributes & FILE_ATTRIBUTE_DIRECTORY)
3898 Py_RETURN_TRUE;
3899 else
3900 Py_RETURN_FALSE;
3901}
Tim Golden6b528062013-08-01 12:44:00 +01003902
Tim Golden6b528062013-08-01 12:44:00 +01003903
Larry Hastings2f936352014-08-05 14:04:04 +10003904/*[clinic input]
3905os._getvolumepathname
3906
3907 path: unicode
3908
3909A helper function for ismount on Win32.
3910[clinic start generated code]*/
3911
Larry Hastings2f936352014-08-05 14:04:04 +10003912static PyObject *
3913os__getvolumepathname_impl(PyModuleDef *module, PyObject *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003914/*[clinic end generated code: output=79a0ba729f956dbe input=7eacadc40acbda6b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003915{
3916 PyObject *result;
3917 wchar_t *path_wchar, *mountpath=NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01003918 size_t buflen;
Tim Golden6b528062013-08-01 12:44:00 +01003919 BOOL ret;
3920
Larry Hastings2f936352014-08-05 14:04:04 +10003921 path_wchar = PyUnicode_AsUnicodeAndSize(path, &buflen);
3922 if (path_wchar == NULL)
Tim Golden6b528062013-08-01 12:44:00 +01003923 return NULL;
Victor Stinner6edddfa2013-11-24 19:22:57 +01003924 buflen += 1;
Tim Golden6b528062013-08-01 12:44:00 +01003925
3926 /* Volume path should be shorter than entire path */
Victor Stinner6edddfa2013-11-24 19:22:57 +01003927 buflen = Py_MAX(buflen, MAX_PATH);
3928
3929 if (buflen > DWORD_MAX) {
3930 PyErr_SetString(PyExc_OverflowError, "path too long");
3931 return NULL;
3932 }
3933
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02003934 mountpath = PyMem_New(wchar_t, buflen);
Tim Golden6b528062013-08-01 12:44:00 +01003935 if (mountpath == NULL)
3936 return PyErr_NoMemory();
3937
3938 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003939 ret = GetVolumePathNameW(path_wchar, mountpath,
Victor Stinner6edddfa2013-11-24 19:22:57 +01003940 Py_SAFE_DOWNCAST(buflen, size_t, DWORD));
Tim Golden6b528062013-08-01 12:44:00 +01003941 Py_END_ALLOW_THREADS
3942
3943 if (!ret) {
Larry Hastings2f936352014-08-05 14:04:04 +10003944 result = win32_error_object("_getvolumepathname", path);
Tim Golden6b528062013-08-01 12:44:00 +01003945 goto exit;
3946 }
3947 result = PyUnicode_FromWideChar(mountpath, wcslen(mountpath));
3948
3949exit:
3950 PyMem_Free(mountpath);
3951 return result;
3952}
Tim Golden6b528062013-08-01 12:44:00 +01003953
Martin v. Löwis6238d2b2002-06-30 15:26:10 +00003954#endif /* MS_WINDOWS */
Mark Hammondef8b6542001-05-13 08:04:26 +00003955
Larry Hastings2f936352014-08-05 14:04:04 +10003956
3957/*[clinic input]
3958os.mkdir
3959
3960 path : path_t
3961
3962 mode: int = 0o777
3963
3964 *
3965
3966 dir_fd : dir_fd(requires='mkdirat') = None
3967
3968# "mkdir(path, mode=0o777, *, dir_fd=None)\n\n\
3969
3970Create a directory.
3971
3972If dir_fd is not None, it should be a file descriptor open to a directory,
3973 and path should be relative; path will then be relative to that directory.
3974dir_fd may not be implemented on your platform.
3975 If it is unavailable, using it will raise a NotImplementedError.
3976
3977The mode argument is ignored on Windows.
3978[clinic start generated code]*/
3979
Larry Hastings2f936352014-08-05 14:04:04 +10003980static PyObject *
3981os_mkdir_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03003982/*[clinic end generated code: output=8bf1f738873ef2c5 input=e965f68377e9b1ce]*/
Larry Hastings2f936352014-08-05 14:04:04 +10003983{
3984 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003985
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00003986#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00003987 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10003988 if (path->wide)
3989 result = CreateDirectoryW(path->wide, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003990 else
Larry Hastings2f936352014-08-05 14:04:04 +10003991 result = CreateDirectoryA(path->narrow, NULL);
Victor Stinner8c62be82010-05-06 00:08:46 +00003992 Py_END_ALLOW_THREADS
Mark Hammondc2e85bd2002-10-03 05:10:39 +00003993
Larry Hastings2f936352014-08-05 14:04:04 +10003994 if (!result)
3995 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07003996#else
Victor Stinner8c62be82010-05-06 00:08:46 +00003997 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07003998#if HAVE_MKDIRAT
3999 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10004000 result = mkdirat(dir_fd, path->narrow, mode);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004001 else
4002#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +00004003#if ( defined(__WATCOMC__) || defined(PYCC_VACPP) ) && !defined(__QNX__)
Larry Hastings2f936352014-08-05 14:04:04 +10004004 result = mkdir(path->narrow);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004005#else
Larry Hastings2f936352014-08-05 14:04:04 +10004006 result = mkdir(path->narrow, mode);
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004007#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00004008 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004009 if (result < 0)
4010 return path_error(path);
Thomas Wouters477c8d52006-05-27 19:21:47 +00004011#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004012 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004013}
4014
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004015
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00004016/* sys/resource.h is needed for at least: wait3(), wait4(), broken nice. */
4017#if defined(HAVE_SYS_RESOURCE_H)
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004018#include <sys/resource.h>
4019#endif
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004020
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00004021
4022#ifdef HAVE_NICE
Larry Hastings2f936352014-08-05 14:04:04 +10004023/*[clinic input]
4024os.nice
4025
4026 increment: int
4027 /
4028
4029Add increment to the priority of process and return the new priority.
4030[clinic start generated code]*/
4031
Larry Hastings2f936352014-08-05 14:04:04 +10004032static PyObject *
4033os_nice_impl(PyModuleDef *module, int increment)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004034/*[clinic end generated code: output=8870418a3fc07b51 input=864be2d402a21da2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004035{
4036 int value;
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004037
Victor Stinner8c62be82010-05-06 00:08:46 +00004038 /* There are two flavours of 'nice': one that returns the new
4039 priority (as required by almost all standards out there) and the
4040 Linux/FreeBSD/BSDI one, which returns '0' on success and advices
4041 the use of getpriority() to get the new priority.
Tim Peters5aa91602002-01-30 05:46:57 +00004042
Victor Stinner8c62be82010-05-06 00:08:46 +00004043 If we are of the nice family that returns the new priority, we
4044 need to clear errno before the call, and check if errno is filled
4045 before calling posix_error() on a returnvalue of -1, because the
4046 -1 may be the actual new priority! */
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004047
Victor Stinner8c62be82010-05-06 00:08:46 +00004048 errno = 0;
4049 value = nice(increment);
Thomas Wouterse38b2f12001-07-11 22:35:31 +00004050#if defined(HAVE_BROKEN_NICE) && defined(HAVE_GETPRIORITY)
Victor Stinner8c62be82010-05-06 00:08:46 +00004051 if (value == 0)
4052 value = getpriority(PRIO_PROCESS, 0);
Thomas Woutersc2c12dc2001-07-11 14:45:34 +00004053#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00004054 if (value == -1 && errno != 0)
4055 /* either nice() or getpriority() returned an error */
4056 return posix_error();
4057 return PyLong_FromLong((long) value);
Guido van Rossum775f4da1993-01-09 17:18:52 +00004058}
Guido van Rossumb6775db1994-08-01 11:34:53 +00004059#endif /* HAVE_NICE */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004060
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004061
4062#ifdef HAVE_GETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10004063/*[clinic input]
4064os.getpriority
4065
4066 which: int
4067 who: int
4068
4069Return program scheduling priority.
4070[clinic start generated code]*/
4071
Larry Hastings2f936352014-08-05 14:04:04 +10004072static PyObject *
4073os_getpriority_impl(PyModuleDef *module, int which, int who)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004074/*[clinic end generated code: output=4759937aa5b67ed6 input=9be615d40e2544ef]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004075{
4076 int retval;
4077
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004078 errno = 0;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004079 retval = getpriority(which, who);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004080 if (errno != 0)
4081 return posix_error();
4082 return PyLong_FromLong((long)retval);
4083}
4084#endif /* HAVE_GETPRIORITY */
4085
4086
4087#ifdef HAVE_SETPRIORITY
Larry Hastings2f936352014-08-05 14:04:04 +10004088/*[clinic input]
4089os.setpriority
4090
4091 which: int
4092 who: int
4093 priority: int
4094
4095Set program scheduling priority.
4096[clinic start generated code]*/
4097
Larry Hastings2f936352014-08-05 14:04:04 +10004098static PyObject *
4099os_setpriority_impl(PyModuleDef *module, int which, int who, int priority)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004100/*[clinic end generated code: output=6497d3301547e7d5 input=710ccbf65b9dc513]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004101{
4102 int retval;
4103
4104 retval = setpriority(which, who, priority);
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +00004105 if (retval == -1)
4106 return posix_error();
4107 Py_RETURN_NONE;
4108}
4109#endif /* HAVE_SETPRIORITY */
4110
4111
Barry Warsaw53699e91996-12-10 23:23:01 +00004112static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10004113internal_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 +00004114{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004115 char *function_name = is_replace ? "replace" : "rename";
Larry Hastings9cf065c2012-06-22 16:30:09 -07004116 int dir_fd_specified;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004117
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004118#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00004119 BOOL result;
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004120 int flags = is_replace ? MOVEFILE_REPLACE_EXISTING : 0;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004121#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07004122 int result;
Mark Hammondc2e85bd2002-10-03 05:10:39 +00004123#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004124
Larry Hastings9cf065c2012-06-22 16:30:09 -07004125 dir_fd_specified = (src_dir_fd != DEFAULT_DIR_FD) ||
4126 (dst_dir_fd != DEFAULT_DIR_FD);
4127#ifndef HAVE_RENAMEAT
4128 if (dir_fd_specified) {
4129 argument_unavailable_error(function_name, "src_dir_fd and dst_dir_fd");
Larry Hastings2f936352014-08-05 14:04:04 +10004130 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004131 }
4132#endif
4133
Larry Hastings2f936352014-08-05 14:04:04 +10004134 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004135 PyErr_Format(PyExc_ValueError,
4136 "%s: src and dst must be the same type", function_name);
Larry Hastings2f936352014-08-05 14:04:04 +10004137 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004138 }
4139
4140#ifdef MS_WINDOWS
4141 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004142 if (src->wide)
4143 result = MoveFileExW(src->wide, dst->wide, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004144 else
Larry Hastings2f936352014-08-05 14:04:04 +10004145 result = MoveFileExA(src->narrow, dst->narrow, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004146 Py_END_ALLOW_THREADS
4147
Larry Hastings2f936352014-08-05 14:04:04 +10004148 if (!result)
4149 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004150
4151#else
4152 Py_BEGIN_ALLOW_THREADS
4153#ifdef HAVE_RENAMEAT
4154 if (dir_fd_specified)
Larry Hastings2f936352014-08-05 14:04:04 +10004155 result = renameat(src_dir_fd, src->narrow, dst_dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004156 else
4157#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004158 result = rename(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004159 Py_END_ALLOW_THREADS
4160
Larry Hastings2f936352014-08-05 14:04:04 +10004161 if (result)
4162 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004163#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004164 Py_RETURN_NONE;
4165}
Larry Hastings9cf065c2012-06-22 16:30:09 -07004166
Larry Hastings2f936352014-08-05 14:04:04 +10004167
4168/*[clinic input]
4169os.rename
4170
4171 src : path_t
4172 dst : path_t
4173 *
4174 src_dir_fd : dir_fd = None
4175 dst_dir_fd : dir_fd = None
4176
4177Rename a file or directory.
4178
4179If either src_dir_fd or dst_dir_fd is not None, it should be a file
4180 descriptor open to a directory, and the respective path string (src or dst)
4181 should be relative; the path will then be relative to that directory.
4182src_dir_fd and dst_dir_fd, may not be implemented on your platform.
4183 If they are unavailable, using them will raise a NotImplementedError.
4184[clinic start generated code]*/
4185
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004186static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004187os_rename_impl(PyModuleDef *module, path_t *src, path_t *dst, int src_dir_fd,
4188 int dst_dir_fd)
4189/*[clinic end generated code: output=08033bb2ec27fb5f input=faa61c847912c850]*/
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004190{
Larry Hastings2f936352014-08-05 14:04:04 +10004191 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 0);
Antoine Pitrouf3b2d882012-01-30 22:08:52 +01004192}
4193
Larry Hastings2f936352014-08-05 14:04:04 +10004194
4195/*[clinic input]
4196os.replace = os.rename
4197
4198Rename a file or directory, overwriting the destination.
4199
4200If either src_dir_fd or dst_dir_fd is not None, it should be a file
4201 descriptor open to a directory, and the respective path string (src or dst)
4202 should be relative; the path will then be relative to that directory.
4203src_dir_fd and dst_dir_fd, may not be implemented on your platform.
4204 If they are unavailable, using them will raise a NotImplementedError."
4205[clinic start generated code]*/
4206
Larry Hastings2f936352014-08-05 14:04:04 +10004207static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004208os_replace_impl(PyModuleDef *module, path_t *src, path_t *dst,
4209 int src_dir_fd, int dst_dir_fd)
4210/*[clinic end generated code: output=131d012eed8d3b8b input=25515dfb107c8421]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004211{
4212 return internal_rename(src, dst, src_dir_fd, dst_dir_fd, 1);
4213}
4214
4215
4216/*[clinic input]
4217os.rmdir
4218
4219 path: path_t
4220 *
4221 dir_fd: dir_fd(requires='unlinkat') = None
4222
4223Remove a directory.
4224
4225If dir_fd is not None, it should be a file descriptor open to a directory,
4226 and path should be relative; path will then be relative to that directory.
4227dir_fd may not be implemented on your platform.
4228 If it is unavailable, using it will raise a NotImplementedError.
4229[clinic start generated code]*/
4230
Larry Hastings2f936352014-08-05 14:04:04 +10004231static PyObject *
4232os_rmdir_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004233/*[clinic end generated code: output=cabadec80d5a77c7 input=38c8b375ca34a7e2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004234{
4235 int result;
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004236
4237 Py_BEGIN_ALLOW_THREADS
4238#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10004239 if (path->wide)
4240 result = RemoveDirectoryW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004241 else
Larry Hastings2f936352014-08-05 14:04:04 +10004242 result = RemoveDirectoryA(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004243 result = !result; /* Windows, success=1, UNIX, success=0 */
4244#else
4245#ifdef HAVE_UNLINKAT
4246 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10004247 result = unlinkat(dir_fd, path->narrow, AT_REMOVEDIR);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004248 else
4249#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004250 result = rmdir(path->narrow);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004251#endif
4252 Py_END_ALLOW_THREADS
4253
Larry Hastings2f936352014-08-05 14:04:04 +10004254 if (result)
4255 return path_error(path);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004256
Larry Hastings2f936352014-08-05 14:04:04 +10004257 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004258}
4259
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004260
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004261#ifdef HAVE_SYSTEM
Larry Hastings2f936352014-08-05 14:04:04 +10004262#ifdef MS_WINDOWS
4263/*[clinic input]
4264os.system -> long
4265
4266 command: Py_UNICODE
4267
4268Execute the command in a subshell.
4269[clinic start generated code]*/
4270
Larry Hastings2f936352014-08-05 14:04:04 +10004271static long
4272os_system_impl(PyModuleDef *module, Py_UNICODE *command)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004273/*[clinic end generated code: output=4c3bd5abcd9c29e7 input=303f5ce97df606b0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004274{
4275 long result;
Victor Stinner8c62be82010-05-06 00:08:46 +00004276 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004277 result = _wsystem(command);
Victor Stinner8c62be82010-05-06 00:08:46 +00004278 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004279 return result;
4280}
4281#else /* MS_WINDOWS */
4282/*[clinic input]
4283os.system -> long
4284
4285 command: FSConverter
4286
4287Execute the command in a subshell.
4288[clinic start generated code]*/
4289
Larry Hastings2f936352014-08-05 14:04:04 +10004290static long
4291os_system_impl(PyModuleDef *module, PyObject *command)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004292/*[clinic end generated code: output=800f775e10b7be55 input=86a58554ba6094af]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004293{
4294 long result;
4295 char *bytes = PyBytes_AsString(command);
4296 Py_BEGIN_ALLOW_THREADS
4297 result = system(bytes);
4298 Py_END_ALLOW_THREADS
4299 return result;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004300}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00004301#endif
Larry Hastings2f936352014-08-05 14:04:04 +10004302#endif /* HAVE_SYSTEM */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004303
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004304
Larry Hastings2f936352014-08-05 14:04:04 +10004305/*[clinic input]
4306os.umask
4307
4308 mask: int
4309 /
4310
4311Set the current numeric umask and return the previous umask.
4312[clinic start generated code]*/
4313
Larry Hastings2f936352014-08-05 14:04:04 +10004314static PyObject *
4315os_umask_impl(PyModuleDef *module, int mask)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004316/*[clinic end generated code: output=9e1fe3c9f14d6a05 input=ab6bfd9b24d8a7e8]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004317{
4318 int i = (int)umask(mask);
Victor Stinner8c62be82010-05-06 00:08:46 +00004319 if (i < 0)
4320 return posix_error();
4321 return PyLong_FromLong((long)i);
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004322}
4323
Brian Curtind40e6f72010-07-08 21:39:08 +00004324#ifdef MS_WINDOWS
4325
4326/* override the default DeleteFileW behavior so that directory
4327symlinks can be removed with this function, the same as with
4328Unix symlinks */
4329BOOL WINAPI Py_DeleteFileW(LPCWSTR lpFileName)
4330{
4331 WIN32_FILE_ATTRIBUTE_DATA info;
4332 WIN32_FIND_DATAW find_data;
4333 HANDLE find_data_handle;
4334 int is_directory = 0;
4335 int is_link = 0;
4336
4337 if (GetFileAttributesExW(lpFileName, GetFileExInfoStandard, &info)) {
4338 is_directory = info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00004339
Brian Curtind40e6f72010-07-08 21:39:08 +00004340 /* Get WIN32_FIND_DATA structure for the path to determine if
4341 it is a symlink */
4342 if(is_directory &&
4343 info.dwFileAttributes & FILE_ATTRIBUTE_REPARSE_POINT) {
4344 find_data_handle = FindFirstFileW(lpFileName, &find_data);
4345
4346 if(find_data_handle != INVALID_HANDLE_VALUE) {
Tim Golden0321cf22014-05-05 19:46:17 +01004347 /* IO_REPARSE_TAG_SYMLINK if it is a symlink and
4348 IO_REPARSE_TAG_MOUNT_POINT if it is a junction point. */
4349 is_link = find_data.dwReserved0 == IO_REPARSE_TAG_SYMLINK ||
4350 find_data.dwReserved0 == IO_REPARSE_TAG_MOUNT_POINT;
Brian Curtind40e6f72010-07-08 21:39:08 +00004351 FindClose(find_data_handle);
4352 }
4353 }
4354 }
4355
4356 if (is_directory && is_link)
4357 return RemoveDirectoryW(lpFileName);
4358
4359 return DeleteFileW(lpFileName);
4360}
4361#endif /* MS_WINDOWS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004362
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004363
Larry Hastings2f936352014-08-05 14:04:04 +10004364/*[clinic input]
4365os.unlink
4366
4367 path: path_t
4368 *
4369 dir_fd: dir_fd(requires='unlinkat')=None
4370
4371Remove a file (same as remove()).
4372
4373If dir_fd is not None, it should be a file descriptor open to a directory,
4374 and path should be relative; path will then be relative to that directory.
4375dir_fd may not be implemented on your platform.
4376 If it is unavailable, using it will raise a NotImplementedError.
4377
4378[clinic start generated code]*/
4379
Larry Hastings2f936352014-08-05 14:04:04 +10004380static PyObject *
4381os_unlink_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004382/*[clinic end generated code: output=474afd5cd09b237e input=d7bcde2b1b2a2552]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004383{
4384 int result;
Larry Hastings9cf065c2012-06-22 16:30:09 -07004385
4386 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04004387 _Py_BEGIN_SUPPRESS_IPH
Larry Hastings9cf065c2012-06-22 16:30:09 -07004388#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10004389 if (path->wide)
4390 result = Py_DeleteFileW(path->wide);
Larry Hastingsb698d8e2012-06-23 16:55:07 -07004391 else
Larry Hastings2f936352014-08-05 14:04:04 +10004392 result = DeleteFileA(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004393 result = !result; /* Windows, success=1, UNIX, success=0 */
4394#else
Larry Hastings9cf065c2012-06-22 16:30:09 -07004395#ifdef HAVE_UNLINKAT
4396 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10004397 result = unlinkat(dir_fd, path->narrow, 0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004398 else
4399#endif /* HAVE_UNLINKAT */
Larry Hastings2f936352014-08-05 14:04:04 +10004400 result = unlink(path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004401#endif
Steve Dower8fc89802015-04-12 00:26:27 -04004402 _Py_END_SUPPRESS_IPH
Larry Hastings9cf065c2012-06-22 16:30:09 -07004403 Py_END_ALLOW_THREADS
4404
Larry Hastings2f936352014-08-05 14:04:04 +10004405 if (result)
4406 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004407
Larry Hastings2f936352014-08-05 14:04:04 +10004408 Py_RETURN_NONE;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004409}
4410
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004411
Larry Hastings2f936352014-08-05 14:04:04 +10004412/*[clinic input]
4413os.remove = os.unlink
4414
4415Remove a file (same as unlink()).
4416
4417If dir_fd is not None, it should be a file descriptor open to a directory,
4418 and path should be relative; path will then be relative to that directory.
4419dir_fd may not be implemented on your platform.
4420 If it is unavailable, using it will raise a NotImplementedError.
4421[clinic start generated code]*/
4422
Larry Hastings2f936352014-08-05 14:04:04 +10004423static PyObject *
4424os_remove_impl(PyModuleDef *module, path_t *path, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004425/*[clinic end generated code: output=d0d5149e64832b9e input=e05c5ab55cd30983]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004426{
4427 return os_unlink_impl(module, path, dir_fd);
4428}
4429
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00004430
Larry Hastings605a62d2012-06-24 04:33:36 -07004431static PyStructSequence_Field uname_result_fields[] = {
4432 {"sysname", "operating system name"},
4433 {"nodename", "name of machine on network (implementation-defined)"},
4434 {"release", "operating system release"},
4435 {"version", "operating system version"},
4436 {"machine", "hardware identifier"},
4437 {NULL}
4438};
4439
4440PyDoc_STRVAR(uname_result__doc__,
4441"uname_result: Result from os.uname().\n\n\
4442This object may be accessed either as a tuple of\n\
4443 (sysname, nodename, release, version, machine),\n\
4444or via the attributes sysname, nodename, release, version, and machine.\n\
4445\n\
4446See os.uname for more information.");
4447
4448static PyStructSequence_Desc uname_result_desc = {
4449 "uname_result", /* name */
4450 uname_result__doc__, /* doc */
4451 uname_result_fields,
4452 5
4453};
4454
4455static PyTypeObject UnameResultType;
4456
4457
4458#ifdef HAVE_UNAME
Larry Hastings2f936352014-08-05 14:04:04 +10004459/*[clinic input]
4460os.uname
4461
4462Return an object identifying the current operating system.
4463
4464The object behaves like a named tuple with the following fields:
4465 (sysname, nodename, release, version, machine)
4466
4467[clinic start generated code]*/
4468
Larry Hastings2f936352014-08-05 14:04:04 +10004469static PyObject *
4470os_uname_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004471/*[clinic end generated code: output=01e1421b757e753f input=e68bd246db3043ed]*/
Guido van Rossumc39de5f1992-02-05 11:15:54 +00004472{
Victor Stinner8c62be82010-05-06 00:08:46 +00004473 struct utsname u;
4474 int res;
Larry Hastings605a62d2012-06-24 04:33:36 -07004475 PyObject *value;
Neal Norwitze241ce82003-02-17 18:17:05 +00004476
Victor Stinner8c62be82010-05-06 00:08:46 +00004477 Py_BEGIN_ALLOW_THREADS
4478 res = uname(&u);
4479 Py_END_ALLOW_THREADS
4480 if (res < 0)
4481 return posix_error();
Larry Hastings605a62d2012-06-24 04:33:36 -07004482
4483 value = PyStructSequence_New(&UnameResultType);
4484 if (value == NULL)
4485 return NULL;
4486
4487#define SET(i, field) \
4488 { \
Victor Stinnera534fc42013-06-03 22:07:27 +02004489 PyObject *o = PyUnicode_DecodeFSDefault(field); \
Larry Hastings605a62d2012-06-24 04:33:36 -07004490 if (!o) { \
4491 Py_DECREF(value); \
4492 return NULL; \
4493 } \
4494 PyStructSequence_SET_ITEM(value, i, o); \
4495 } \
4496
4497 SET(0, u.sysname);
4498 SET(1, u.nodename);
4499 SET(2, u.release);
4500 SET(3, u.version);
4501 SET(4, u.machine);
4502
4503#undef SET
4504
4505 return value;
Guido van Rossumc39de5f1992-02-05 11:15:54 +00004506}
Guido van Rossumb6775db1994-08-01 11:34:53 +00004507#endif /* HAVE_UNAME */
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004508
Larry Hastings9e3e70b2011-09-08 19:29:07 -07004509
Larry Hastings9cf065c2012-06-22 16:30:09 -07004510
4511typedef struct {
4512 int now;
4513 time_t atime_s;
4514 long atime_ns;
4515 time_t mtime_s;
4516 long mtime_ns;
4517} utime_t;
4518
4519/*
Victor Stinner484df002014-10-09 13:52:31 +02004520 * these macros assume that "ut" is a pointer to a utime_t
Larry Hastings9cf065c2012-06-22 16:30:09 -07004521 * they also intentionally leak the declaration of a pointer named "time"
4522 */
4523#define UTIME_TO_TIMESPEC \
4524 struct timespec ts[2]; \
4525 struct timespec *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004526 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004527 time = NULL; \
4528 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004529 ts[0].tv_sec = ut->atime_s; \
4530 ts[0].tv_nsec = ut->atime_ns; \
4531 ts[1].tv_sec = ut->mtime_s; \
4532 ts[1].tv_nsec = ut->mtime_ns; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004533 time = ts; \
4534 } \
4535
4536#define UTIME_TO_TIMEVAL \
4537 struct timeval tv[2]; \
4538 struct timeval *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004539 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004540 time = NULL; \
4541 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004542 tv[0].tv_sec = ut->atime_s; \
4543 tv[0].tv_usec = ut->atime_ns / 1000; \
4544 tv[1].tv_sec = ut->mtime_s; \
4545 tv[1].tv_usec = ut->mtime_ns / 1000; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004546 time = tv; \
4547 } \
4548
4549#define UTIME_TO_UTIMBUF \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004550 struct utimbuf u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004551 struct utimbuf *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004552 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004553 time = NULL; \
4554 else { \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004555 u.actime = ut->atime_s; \
4556 u.modtime = ut->mtime_s; \
4557 time = &u; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004558 }
4559
4560#define UTIME_TO_TIME_T \
4561 time_t timet[2]; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004562 time_t *time; \
Victor Stinner484df002014-10-09 13:52:31 +02004563 if (ut->now) \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004564 time = NULL; \
4565 else { \
Victor Stinner484df002014-10-09 13:52:31 +02004566 timet[0] = ut->atime_s; \
4567 timet[1] = ut->mtime_s; \
Georg Brandle1a7d9d2014-10-12 08:45:15 +02004568 time = timet; \
Larry Hastings9cf065c2012-06-22 16:30:09 -07004569 } \
4570
4571
Victor Stinner528a9ab2015-09-03 21:30:26 +02004572#if defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004573
4574static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02004575utime_dir_fd(utime_t *ut, int dir_fd, const char *path, int follow_symlinks)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004576{
4577#ifdef HAVE_UTIMENSAT
4578 int flags = follow_symlinks ? 0 : AT_SYMLINK_NOFOLLOW;
4579 UTIME_TO_TIMESPEC;
4580 return utimensat(dir_fd, path, time, flags);
4581#elif defined(HAVE_FUTIMESAT)
4582 UTIME_TO_TIMEVAL;
4583 /*
4584 * follow_symlinks will never be false here;
4585 * we only allow !follow_symlinks and dir_fd together
4586 * if we have utimensat()
4587 */
4588 assert(follow_symlinks);
4589 return futimesat(dir_fd, path, time);
4590#endif
4591}
4592
Larry Hastings2f936352014-08-05 14:04:04 +10004593 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_converter
4594#else
4595 #define FUTIMENSAT_DIR_FD_CONVERTER dir_fd_unavailable
Larry Hastings9cf065c2012-06-22 16:30:09 -07004596#endif
4597
Victor Stinner528a9ab2015-09-03 21:30:26 +02004598#if defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004599
4600static int
Victor Stinner484df002014-10-09 13:52:31 +02004601utime_fd(utime_t *ut, int fd)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004602{
4603#ifdef HAVE_FUTIMENS
4604 UTIME_TO_TIMESPEC;
4605 return futimens(fd, time);
4606#else
4607 UTIME_TO_TIMEVAL;
4608 return futimes(fd, time);
4609#endif
4610}
4611
Larry Hastings2f936352014-08-05 14:04:04 +10004612 #define PATH_UTIME_HAVE_FD 1
4613#else
4614 #define PATH_UTIME_HAVE_FD 0
Larry Hastings9cf065c2012-06-22 16:30:09 -07004615#endif
4616
Victor Stinner5ebae872015-09-22 01:29:33 +02004617#if defined(HAVE_UTIMENSAT) || defined(HAVE_LUTIMES)
4618# define UTIME_HAVE_NOFOLLOW_SYMLINKS
4619#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004620
Victor Stinner4552ced2015-09-21 22:37:15 +02004621#ifdef UTIME_HAVE_NOFOLLOW_SYMLINKS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004622
4623static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02004624utime_nofollow_symlinks(utime_t *ut, const char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004625{
4626#ifdef HAVE_UTIMENSAT
4627 UTIME_TO_TIMESPEC;
4628 return utimensat(DEFAULT_DIR_FD, path, time, AT_SYMLINK_NOFOLLOW);
4629#else
4630 UTIME_TO_TIMEVAL;
4631 return lutimes(path, time);
4632#endif
4633}
4634
4635#endif
4636
4637#ifndef MS_WINDOWS
4638
4639static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02004640utime_default(utime_t *ut, const char *path)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004641{
4642#ifdef HAVE_UTIMENSAT
4643 UTIME_TO_TIMESPEC;
4644 return utimensat(DEFAULT_DIR_FD, path, time, 0);
4645#elif defined(HAVE_UTIMES)
4646 UTIME_TO_TIMEVAL;
4647 return utimes(path, time);
4648#elif defined(HAVE_UTIME_H)
4649 UTIME_TO_UTIMBUF;
4650 return utime(path, time);
4651#else
4652 UTIME_TO_TIME_T;
4653 return utime(path, time);
4654#endif
4655}
4656
4657#endif
4658
Larry Hastings76ad59b2012-05-03 00:30:07 -07004659static int
4660split_py_long_to_s_and_ns(PyObject *py_long, time_t *s, long *ns)
4661{
4662 int result = 0;
Benjamin Petersonfbd85a02012-05-04 11:06:09 -04004663 PyObject *divmod;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004664 divmod = PyNumber_Divmod(py_long, billion);
4665 if (!divmod)
4666 goto exit;
4667 *s = _PyLong_AsTime_t(PyTuple_GET_ITEM(divmod, 0));
4668 if ((*s == -1) && PyErr_Occurred())
4669 goto exit;
4670 *ns = PyLong_AsLong(PyTuple_GET_ITEM(divmod, 1));
Benjamin Peterson35a8f0d2012-05-04 01:10:59 -04004671 if ((*ns == -1) && PyErr_Occurred())
Larry Hastings76ad59b2012-05-03 00:30:07 -07004672 goto exit;
4673
4674 result = 1;
4675exit:
4676 Py_XDECREF(divmod);
4677 return result;
4678}
4679
Larry Hastings2f936352014-08-05 14:04:04 +10004680
4681/*[clinic input]
4682os.utime
4683
4684 path: path_t(allow_fd='PATH_UTIME_HAVE_FD')
4685 times: object = NULL
4686 *
4687 ns: object = NULL
4688 dir_fd: dir_fd(requires='futimensat') = None
4689 follow_symlinks: bool=True
4690
Martin Panter0ff89092015-09-09 01:56:53 +00004691# "utime(path, times=None, *[, ns], dir_fd=None, follow_symlinks=True)\n\
Larry Hastings2f936352014-08-05 14:04:04 +10004692
4693Set the access and modified time of path.
4694
4695path may always be specified as a string.
4696On some platforms, path may also be specified as an open file descriptor.
4697 If this functionality is unavailable, using it raises an exception.
4698
4699If times is not None, it must be a tuple (atime, mtime);
4700 atime and mtime should be expressed as float seconds since the epoch.
Martin Panter0ff89092015-09-09 01:56:53 +00004701If ns is specified, it must be a tuple (atime_ns, mtime_ns);
Larry Hastings2f936352014-08-05 14:04:04 +10004702 atime_ns and mtime_ns should be expressed as integer nanoseconds
4703 since the epoch.
Martin Panter0ff89092015-09-09 01:56:53 +00004704If times is None and ns is unspecified, utime uses the current time.
Larry Hastings2f936352014-08-05 14:04:04 +10004705Specifying tuples for both times and ns is an error.
4706
4707If dir_fd is not None, it should be a file descriptor open to a directory,
4708 and path should be relative; path will then be relative to that directory.
4709If follow_symlinks is False, and the last element of the path is a symbolic
4710 link, utime will modify the symbolic link itself instead of the file the
4711 link points to.
4712It is an error to use dir_fd or follow_symlinks when specifying path
4713 as an open file descriptor.
4714dir_fd and follow_symlinks may not be available on your platform.
4715 If they are unavailable, using them will raise a NotImplementedError.
4716
4717[clinic start generated code]*/
4718
Larry Hastings2f936352014-08-05 14:04:04 +10004719static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04004720os_utime_impl(PyModuleDef *module, path_t *path, PyObject *times,
4721 PyObject *ns, int dir_fd, int follow_symlinks)
Martin Panter0ff89092015-09-09 01:56:53 +00004722/*[clinic end generated code: output=31f3434e560ba2f0 input=081cdc54ca685385]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004723{
Larry Hastings9cf065c2012-06-22 16:30:09 -07004724#ifdef MS_WINDOWS
4725 HANDLE hFile;
4726 FILETIME atime, mtime;
4727#else
4728 int result;
4729#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07004730
Larry Hastings9cf065c2012-06-22 16:30:09 -07004731 PyObject *return_value = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10004732 utime_t utime;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004733
Christian Heimesb3c87242013-08-01 00:08:16 +02004734 memset(&utime, 0, sizeof(utime_t));
Larry Hastings76ad59b2012-05-03 00:30:07 -07004735
Larry Hastings9cf065c2012-06-22 16:30:09 -07004736 if (times && (times != Py_None) && ns) {
4737 PyErr_SetString(PyExc_ValueError,
4738 "utime: you may specify either 'times'"
4739 " or 'ns' but not both");
4740 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004741 }
4742
4743 if (times && (times != Py_None)) {
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02004744 time_t a_sec, m_sec;
4745 long a_nsec, m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004746 if (!PyTuple_CheckExact(times) || (PyTuple_Size(times) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004747 PyErr_SetString(PyExc_TypeError,
4748 "utime: 'times' must be either"
4749 " a tuple of two ints or None");
4750 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004751 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004752 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004753 if (_PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 0),
Victor Stinnerdca028b2015-03-30 01:02:57 +02004754 &a_sec, &a_nsec, _PyTime_ROUND_FLOOR) == -1 ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004755 _PyTime_ObjectToTimespec(PyTuple_GET_ITEM(times, 1),
Victor Stinnerdca028b2015-03-30 01:02:57 +02004756 &m_sec, &m_nsec, _PyTime_ROUND_FLOOR) == -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004757 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004758 }
Antoine Pitroucf8a1e52013-04-17 22:06:44 +02004759 utime.atime_s = a_sec;
4760 utime.atime_ns = a_nsec;
4761 utime.mtime_s = m_sec;
4762 utime.mtime_ns = m_nsec;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004763 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004764 else if (ns) {
Larry Hastings76ad59b2012-05-03 00:30:07 -07004765 if (!PyTuple_CheckExact(ns) || (PyTuple_Size(ns) != 2)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07004766 PyErr_SetString(PyExc_TypeError,
4767 "utime: 'ns' must be a tuple of two ints");
4768 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004769 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004770 utime.now = 0;
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004771 if (!split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 0),
Larry Hastings9cf065c2012-06-22 16:30:09 -07004772 &utime.atime_s, &utime.atime_ns) ||
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004773 !split_py_long_to_s_and_ns(PyTuple_GET_ITEM(ns, 1),
Larry Hastings9cf065c2012-06-22 16:30:09 -07004774 &utime.mtime_s, &utime.mtime_ns)) {
4775 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004776 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07004777 }
4778 else {
4779 /* times and ns are both None/unspecified. use "now". */
4780 utime.now = 1;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004781 }
4782
Victor Stinner4552ced2015-09-21 22:37:15 +02004783#if !defined(UTIME_HAVE_NOFOLLOW_SYMLINKS)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004784 if (follow_symlinks_specified("utime", follow_symlinks))
4785 goto exit;
4786#endif
Benjamin Petersonb399ab22012-05-04 01:31:13 -04004787
Larry Hastings2f936352014-08-05 14:04:04 +10004788 if (path_and_dir_fd_invalid("utime", path, dir_fd) ||
4789 dir_fd_and_fd_invalid("utime", dir_fd, path->fd) ||
4790 fd_and_follow_symlinks_invalid("utime", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -07004791 goto exit;
Larry Hastings76ad59b2012-05-03 00:30:07 -07004792
Larry Hastings9cf065c2012-06-22 16:30:09 -07004793#if !defined(HAVE_UTIMENSAT)
4794 if ((dir_fd != DEFAULT_DIR_FD) && (!follow_symlinks)) {
Georg Brandl969288e2012-06-26 09:25:44 +02004795 PyErr_SetString(PyExc_ValueError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07004796 "utime: cannot use dir_fd and follow_symlinks "
4797 "together on this platform");
4798 goto exit;
4799 }
4800#endif
Larry Hastings76ad59b2012-05-03 00:30:07 -07004801
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004802#ifdef MS_WINDOWS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004803 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10004804 if (path->wide)
4805 hFile = CreateFileW(path->wide, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00004806 NULL, OPEN_EXISTING,
4807 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004808 else
Larry Hastings2f936352014-08-05 14:04:04 +10004809 hFile = CreateFileA(path->narrow, FILE_WRITE_ATTRIBUTES, 0,
Victor Stinner8c62be82010-05-06 00:08:46 +00004810 NULL, OPEN_EXISTING,
4811 FILE_FLAG_BACKUP_SEMANTICS, NULL);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004812 Py_END_ALLOW_THREADS
4813 if (hFile == INVALID_HANDLE_VALUE) {
Larry Hastings2f936352014-08-05 14:04:04 +10004814 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004815 goto exit;
Larry Hastingsb3336402012-05-04 02:31:57 -07004816 }
4817
Larry Hastings9cf065c2012-06-22 16:30:09 -07004818 if (utime.now) {
Antoine Pitrou91a7af32013-11-23 15:23:26 +01004819 GetSystemTimeAsFileTime(&mtime);
4820 atime = mtime;
Victor Stinner8c62be82010-05-06 00:08:46 +00004821 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004822 else {
Steve Dowerbf1f3762015-02-21 15:26:02 -08004823 _Py_time_t_to_FILE_TIME(utime.atime_s, utime.atime_ns, &atime);
4824 _Py_time_t_to_FILE_TIME(utime.mtime_s, utime.mtime_ns, &mtime);
Victor Stinner8c62be82010-05-06 00:08:46 +00004825 }
4826 if (!SetFileTime(hFile, NULL, &atime, &mtime)) {
4827 /* Avoid putting the file name into the error here,
4828 as that may confuse the user into believing that
4829 something is wrong with the file, when it also
4830 could be the time stamp that gives a problem. */
Victor Stinnerb024e842012-10-31 22:24:06 +01004831 PyErr_SetFromWindowsErr(0);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004832 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004833 }
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004834#else /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004835 Py_BEGIN_ALLOW_THREADS
Guido van Rossum1ff6cb41991-04-08 20:59:13 +00004836
Victor Stinner4552ced2015-09-21 22:37:15 +02004837#ifdef UTIME_HAVE_NOFOLLOW_SYMLINKS
Larry Hastings9cf065c2012-06-22 16:30:09 -07004838 if ((!follow_symlinks) && (dir_fd == DEFAULT_DIR_FD))
Larry Hastings2f936352014-08-05 14:04:04 +10004839 result = utime_nofollow_symlinks(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004840 else
Larry Hastings9e3e70b2011-09-08 19:29:07 -07004841#endif
Larry Hastings9cf065c2012-06-22 16:30:09 -07004842
Victor Stinner528a9ab2015-09-03 21:30:26 +02004843#if defined(HAVE_FUTIMESAT) || defined(HAVE_UTIMENSAT)
Larry Hastings9cf065c2012-06-22 16:30:09 -07004844 if ((dir_fd != DEFAULT_DIR_FD) || (!follow_symlinks))
Larry Hastings2f936352014-08-05 14:04:04 +10004845 result = utime_dir_fd(&utime, dir_fd, path->narrow, follow_symlinks);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004846 else
4847#endif
4848
Victor Stinner528a9ab2015-09-03 21:30:26 +02004849#if defined(HAVE_FUTIMES) || defined(HAVE_FUTIMENS)
Larry Hastings2f936352014-08-05 14:04:04 +10004850 if (path->fd != -1)
4851 result = utime_fd(&utime, path->fd);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004852 else
4853#endif
4854
Larry Hastings2f936352014-08-05 14:04:04 +10004855 result = utime_default(&utime, path->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07004856
4857 Py_END_ALLOW_THREADS
4858
4859 if (result < 0) {
4860 /* see previous comment about not putting filename in error here */
4861 return_value = posix_error();
4862 goto exit;
Victor Stinner8c62be82010-05-06 00:08:46 +00004863 }
Larry Hastings76ad59b2012-05-03 00:30:07 -07004864
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +00004865#endif /* MS_WINDOWS */
Larry Hastings9cf065c2012-06-22 16:30:09 -07004866
4867 Py_INCREF(Py_None);
4868 return_value = Py_None;
4869
4870exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -07004871#ifdef MS_WINDOWS
4872 if (hFile != INVALID_HANDLE_VALUE)
4873 CloseHandle(hFile);
4874#endif
4875 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00004876}
4877
Guido van Rossum3b066191991-06-04 19:40:25 +00004878/* Process operations */
Guido van Rossum85e3b011991-06-03 12:42:10 +00004879
Larry Hastings2f936352014-08-05 14:04:04 +10004880
4881/*[clinic input]
4882os._exit
4883
4884 status: int
4885
4886Exit to the system with specified status, without normal exit processing.
4887[clinic start generated code]*/
4888
Larry Hastings2f936352014-08-05 14:04:04 +10004889static PyObject *
4890os__exit_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03004891/*[clinic end generated code: output=472a3cbaf68f3621 input=5e6d57556b0c4a62]*/
Larry Hastings2f936352014-08-05 14:04:04 +10004892{
4893 _exit(status);
Victor Stinner8c62be82010-05-06 00:08:46 +00004894 return NULL; /* Make gcc -Wall happy */
Guido van Rossum85e3b011991-06-03 12:42:10 +00004895}
4896
Martin v. Löwis114619e2002-10-07 06:44:21 +00004897#if defined(HAVE_EXECV) || defined(HAVE_SPAWNV)
4898static void
Martin v. Löwis725507b2006-03-07 12:08:51 +00004899free_string_array(char **array, Py_ssize_t count)
Martin v. Löwis114619e2002-10-07 06:44:21 +00004900{
Victor Stinner8c62be82010-05-06 00:08:46 +00004901 Py_ssize_t i;
4902 for (i = 0; i < count; i++)
4903 PyMem_Free(array[i]);
4904 PyMem_DEL(array);
Martin v. Löwis114619e2002-10-07 06:44:21 +00004905}
Martin v. Löwis011e8422009-05-05 04:43:17 +00004906
Antoine Pitrou69f71142009-05-24 21:25:49 +00004907static
Martin v. Löwis011e8422009-05-05 04:43:17 +00004908int fsconvert_strdup(PyObject *o, char**out)
4909{
Victor Stinner8c62be82010-05-06 00:08:46 +00004910 PyObject *bytes;
4911 Py_ssize_t size;
4912 if (!PyUnicode_FSConverter(o, &bytes))
4913 return 0;
4914 size = PyBytes_GET_SIZE(bytes);
4915 *out = PyMem_Malloc(size+1);
Victor Stinner50abf222013-11-07 23:56:10 +01004916 if (!*out) {
4917 PyErr_NoMemory();
Victor Stinner8c62be82010-05-06 00:08:46 +00004918 return 0;
Victor Stinner50abf222013-11-07 23:56:10 +01004919 }
Victor Stinner8c62be82010-05-06 00:08:46 +00004920 memcpy(*out, PyBytes_AsString(bytes), size+1);
4921 Py_DECREF(bytes);
4922 return 1;
Martin v. Löwis011e8422009-05-05 04:43:17 +00004923}
Martin v. Löwis114619e2002-10-07 06:44:21 +00004924#endif
4925
Ross Lagerwall7807c352011-03-17 20:20:30 +02004926#if defined(HAVE_EXECV) || defined (HAVE_FEXECVE)
Victor Stinner13bb71c2010-04-23 21:41:56 +00004927static char**
4928parse_envlist(PyObject* env, Py_ssize_t *envc_ptr)
4929{
Victor Stinner8c62be82010-05-06 00:08:46 +00004930 char **envlist;
4931 Py_ssize_t i, pos, envc;
4932 PyObject *keys=NULL, *vals=NULL;
4933 PyObject *key, *val, *key2, *val2;
4934 char *p, *k, *v;
4935 size_t len;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004936
Victor Stinner8c62be82010-05-06 00:08:46 +00004937 i = PyMapping_Size(env);
4938 if (i < 0)
4939 return NULL;
4940 envlist = PyMem_NEW(char *, i + 1);
4941 if (envlist == NULL) {
4942 PyErr_NoMemory();
4943 return NULL;
4944 }
4945 envc = 0;
4946 keys = PyMapping_Keys(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01004947 if (!keys)
4948 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00004949 vals = PyMapping_Values(env);
Victor Stinnerb0314272013-11-14 21:37:05 +01004950 if (!vals)
Victor Stinner8c62be82010-05-06 00:08:46 +00004951 goto error;
4952 if (!PyList_Check(keys) || !PyList_Check(vals)) {
4953 PyErr_Format(PyExc_TypeError,
4954 "env.keys() or env.values() is not a list");
4955 goto error;
4956 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00004957
Victor Stinner8c62be82010-05-06 00:08:46 +00004958 for (pos = 0; pos < i; pos++) {
4959 key = PyList_GetItem(keys, pos);
4960 val = PyList_GetItem(vals, pos);
4961 if (!key || !val)
4962 goto error;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004963
Victor Stinner8c62be82010-05-06 00:08:46 +00004964 if (PyUnicode_FSConverter(key, &key2) == 0)
4965 goto error;
4966 if (PyUnicode_FSConverter(val, &val2) == 0) {
4967 Py_DECREF(key2);
4968 goto error;
4969 }
Victor Stinner13bb71c2010-04-23 21:41:56 +00004970
Victor Stinner8c62be82010-05-06 00:08:46 +00004971 k = PyBytes_AsString(key2);
4972 v = PyBytes_AsString(val2);
4973 len = PyBytes_GET_SIZE(key2) + PyBytes_GET_SIZE(val2) + 2;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004974
Victor Stinner8c62be82010-05-06 00:08:46 +00004975 p = PyMem_NEW(char, len);
4976 if (p == NULL) {
4977 PyErr_NoMemory();
4978 Py_DECREF(key2);
4979 Py_DECREF(val2);
4980 goto error;
4981 }
4982 PyOS_snprintf(p, len, "%s=%s", k, v);
4983 envlist[envc++] = p;
4984 Py_DECREF(key2);
4985 Py_DECREF(val2);
Victor Stinner8c62be82010-05-06 00:08:46 +00004986 }
4987 Py_DECREF(vals);
4988 Py_DECREF(keys);
Victor Stinner13bb71c2010-04-23 21:41:56 +00004989
Victor Stinner8c62be82010-05-06 00:08:46 +00004990 envlist[envc] = 0;
4991 *envc_ptr = envc;
4992 return envlist;
Victor Stinner13bb71c2010-04-23 21:41:56 +00004993
4994error:
Victor Stinner8c62be82010-05-06 00:08:46 +00004995 Py_XDECREF(keys);
4996 Py_XDECREF(vals);
4997 while (--envc >= 0)
4998 PyMem_DEL(envlist[envc]);
4999 PyMem_DEL(envlist);
5000 return NULL;
Victor Stinner13bb71c2010-04-23 21:41:56 +00005001}
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005002
Ross Lagerwall7807c352011-03-17 20:20:30 +02005003static char**
5004parse_arglist(PyObject* argv, Py_ssize_t *argc)
5005{
5006 int i;
5007 char **argvlist = PyMem_NEW(char *, *argc+1);
5008 if (argvlist == NULL) {
5009 PyErr_NoMemory();
5010 return NULL;
5011 }
5012 for (i = 0; i < *argc; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005013 PyObject* item = PySequence_ITEM(argv, i);
5014 if (item == NULL)
5015 goto fail;
5016 if (!fsconvert_strdup(item, &argvlist[i])) {
5017 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005018 goto fail;
5019 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005020 Py_DECREF(item);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005021 }
5022 argvlist[*argc] = NULL;
5023 return argvlist;
5024fail:
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02005025 *argc = i;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005026 free_string_array(argvlist, *argc);
5027 return NULL;
5028}
5029#endif
5030
Larry Hastings2f936352014-08-05 14:04:04 +10005031
Ross Lagerwall7807c352011-03-17 20:20:30 +02005032#ifdef HAVE_EXECV
Larry Hastings2f936352014-08-05 14:04:04 +10005033/*[clinic input]
5034os.execv
5035
5036 path: FSConverter
5037 Path of executable file.
5038 argv: object
5039 Tuple or list of strings.
5040 /
5041
5042Execute an executable path with arguments, replacing current process.
5043[clinic start generated code]*/
5044
Larry Hastings2f936352014-08-05 14:04:04 +10005045static PyObject *
5046os_execv_impl(PyModuleDef *module, PyObject *path, PyObject *argv)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005047/*[clinic end generated code: output=9221f08143146fff input=96041559925e5229]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005048{
5049 char *path_char;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005050 char **argvlist;
5051 Py_ssize_t argc;
5052
5053 /* execv has two arguments: (path, argv), where
5054 argv is a list or tuple of strings. */
5055
Larry Hastings2f936352014-08-05 14:04:04 +10005056 path_char = PyBytes_AsString(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005057 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
5058 PyErr_SetString(PyExc_TypeError,
5059 "execv() arg 2 must be a tuple or list");
Ross Lagerwall7807c352011-03-17 20:20:30 +02005060 return NULL;
5061 }
5062 argc = PySequence_Size(argv);
5063 if (argc < 1) {
5064 PyErr_SetString(PyExc_ValueError, "execv() arg 2 must not be empty");
Ross Lagerwall7807c352011-03-17 20:20:30 +02005065 return NULL;
5066 }
5067
5068 argvlist = parse_arglist(argv, &argc);
5069 if (argvlist == NULL) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02005070 return NULL;
5071 }
5072
Larry Hastings2f936352014-08-05 14:04:04 +10005073 execv(path_char, argvlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005074
5075 /* If we get here it's definitely an error */
5076
5077 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005078 return posix_error();
5079}
5080
Larry Hastings2f936352014-08-05 14:04:04 +10005081
5082/*[clinic input]
5083os.execve
5084
5085 path: path_t(allow_fd='PATH_HAVE_FEXECVE')
5086 Path of executable file.
5087 argv: object
5088 Tuple or list of strings.
5089 env: object
5090 Dictionary of strings mapping to strings.
5091
5092Execute an executable path with arguments, replacing current process.
5093[clinic start generated code]*/
5094
Larry Hastings2f936352014-08-05 14:04:04 +10005095static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005096os_execve_impl(PyModuleDef *module, path_t *path, PyObject *argv,
5097 PyObject *env)
5098/*[clinic end generated code: output=181884fcdb21508e input=626804fa092606d9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005099{
Larry Hastings9cf065c2012-06-22 16:30:09 -07005100 char **argvlist = NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00005101 char **envlist;
Ross Lagerwall7807c352011-03-17 20:20:30 +02005102 Py_ssize_t argc, envc;
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005103
Victor Stinner8c62be82010-05-06 00:08:46 +00005104 /* execve has three arguments: (path, argv, env), where
5105 argv is a list or tuple of strings and env is a dictionary
5106 like posix.environ. */
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005107
Ross Lagerwall7807c352011-03-17 20:20:30 +02005108 if (!PyList_Check(argv) && !PyTuple_Check(argv)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00005109 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07005110 "execve: argv must be a tuple or list");
5111 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005112 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02005113 argc = PySequence_Size(argv);
Victor Stinner8c62be82010-05-06 00:08:46 +00005114 if (!PyMapping_Check(env)) {
5115 PyErr_SetString(PyExc_TypeError,
Larry Hastings9cf065c2012-06-22 16:30:09 -07005116 "execve: environment must be a mapping object");
5117 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005118 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005119
Ross Lagerwall7807c352011-03-17 20:20:30 +02005120 argvlist = parse_arglist(argv, &argc);
Victor Stinner8c62be82010-05-06 00:08:46 +00005121 if (argvlist == NULL) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07005122 goto fail;
Victor Stinner8c62be82010-05-06 00:08:46 +00005123 }
Guido van Rossumc6dcc9f1993-11-05 10:15:19 +00005124
Victor Stinner8c62be82010-05-06 00:08:46 +00005125 envlist = parse_envlist(env, &envc);
5126 if (envlist == NULL)
Ross Lagerwall7807c352011-03-17 20:20:30 +02005127 goto fail;
5128
Larry Hastings9cf065c2012-06-22 16:30:09 -07005129#ifdef HAVE_FEXECVE
Larry Hastings2f936352014-08-05 14:04:04 +10005130 if (path->fd > -1)
5131 fexecve(path->fd, argvlist, envlist);
Larry Hastings9cf065c2012-06-22 16:30:09 -07005132 else
5133#endif
Larry Hastings2f936352014-08-05 14:04:04 +10005134 execve(path->narrow, argvlist, envlist);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005135
5136 /* If we get here it's definitely an error */
5137
Larry Hastings2f936352014-08-05 14:04:04 +10005138 path_error(path);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005139
5140 while (--envc >= 0)
5141 PyMem_DEL(envlist[envc]);
5142 PyMem_DEL(envlist);
5143 fail:
Larry Hastings9cf065c2012-06-22 16:30:09 -07005144 if (argvlist)
5145 free_string_array(argvlist, argc);
Ross Lagerwall7807c352011-03-17 20:20:30 +02005146 return NULL;
5147}
Larry Hastings9cf065c2012-06-22 16:30:09 -07005148#endif /* HAVE_EXECV */
5149
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005150
Guido van Rossuma1065681999-01-25 23:20:23 +00005151#ifdef HAVE_SPAWNV
Larry Hastings2f936352014-08-05 14:04:04 +10005152/*[clinic input]
5153os.spawnv
5154
5155 mode: int
5156 Mode of process creation.
5157 path: FSConverter
5158 Path of executable file.
5159 argv: object
5160 Tuple or list of strings.
5161 /
5162
5163Execute the program specified by path in a new process.
5164[clinic start generated code]*/
5165
Larry Hastings2f936352014-08-05 14:04:04 +10005166static PyObject *
5167os_spawnv_impl(PyModuleDef *module, int mode, PyObject *path, PyObject *argv)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005168/*[clinic end generated code: output=140a7945484c8cc5 input=042c91dfc1e6debc]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005169{
5170 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00005171 char **argvlist;
Larry Hastings2f936352014-08-05 14:04:04 +10005172 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00005173 Py_ssize_t argc;
5174 Py_intptr_t spawnval;
5175 PyObject *(*getitem)(PyObject *, Py_ssize_t);
Guido van Rossuma1065681999-01-25 23:20:23 +00005176
Victor Stinner8c62be82010-05-06 00:08:46 +00005177 /* spawnv has three arguments: (mode, path, argv), where
5178 argv is a list or tuple of strings. */
Guido van Rossuma1065681999-01-25 23:20:23 +00005179
Larry Hastings2f936352014-08-05 14:04:04 +10005180 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00005181 if (PyList_Check(argv)) {
5182 argc = PyList_Size(argv);
5183 getitem = PyList_GetItem;
5184 }
5185 else if (PyTuple_Check(argv)) {
5186 argc = PyTuple_Size(argv);
5187 getitem = PyTuple_GetItem;
5188 }
5189 else {
5190 PyErr_SetString(PyExc_TypeError,
5191 "spawnv() arg 2 must be a tuple or list");
Victor Stinner8c62be82010-05-06 00:08:46 +00005192 return NULL;
5193 }
Guido van Rossuma1065681999-01-25 23:20:23 +00005194
Victor Stinner8c62be82010-05-06 00:08:46 +00005195 argvlist = PyMem_NEW(char *, argc+1);
5196 if (argvlist == NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00005197 return PyErr_NoMemory();
5198 }
5199 for (i = 0; i < argc; i++) {
5200 if (!fsconvert_strdup((*getitem)(argv, i),
5201 &argvlist[i])) {
5202 free_string_array(argvlist, i);
5203 PyErr_SetString(
5204 PyExc_TypeError,
5205 "spawnv() arg 2 must contain only strings");
Victor Stinner8c62be82010-05-06 00:08:46 +00005206 return NULL;
5207 }
5208 }
5209 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00005210
Victor Stinner8c62be82010-05-06 00:08:46 +00005211 if (mode == _OLD_P_OVERLAY)
5212 mode = _P_OVERLAY;
Tim Peters5aa91602002-01-30 05:46:57 +00005213
Victor Stinner8c62be82010-05-06 00:08:46 +00005214 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005215 spawnval = _spawnv(mode, path_char, argvlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00005216 Py_END_ALLOW_THREADS
Tim Peters5aa91602002-01-30 05:46:57 +00005217
Victor Stinner8c62be82010-05-06 00:08:46 +00005218 free_string_array(argvlist, argc);
Guido van Rossuma1065681999-01-25 23:20:23 +00005219
Victor Stinner8c62be82010-05-06 00:08:46 +00005220 if (spawnval == -1)
5221 return posix_error();
5222 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01005223 return Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00005224}
5225
5226
Larry Hastings2f936352014-08-05 14:04:04 +10005227/*[clinic input]
5228os.spawnve
5229
5230 mode: int
5231 Mode of process creation.
5232 path: FSConverter
5233 Path of executable file.
5234 argv: object
5235 Tuple or list of strings.
5236 env: object
5237 Dictionary of strings mapping to strings.
5238 /
5239
5240Execute the program specified by path in a new process.
5241[clinic start generated code]*/
5242
Larry Hastings2f936352014-08-05 14:04:04 +10005243static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005244os_spawnve_impl(PyModuleDef *module, int mode, PyObject *path,
5245 PyObject *argv, PyObject *env)
5246/*[clinic end generated code: output=e7f5f0703610531f input=02362fd937963f8f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005247{
5248 char *path_char;
Victor Stinner8c62be82010-05-06 00:08:46 +00005249 char **argvlist;
5250 char **envlist;
5251 PyObject *res = NULL;
Antoine Pitrou22e41552010-08-15 18:07:50 +00005252 Py_ssize_t argc, i, envc;
Victor Stinner8c62be82010-05-06 00:08:46 +00005253 Py_intptr_t spawnval;
5254 PyObject *(*getitem)(PyObject *, Py_ssize_t);
5255 Py_ssize_t lastarg = 0;
Guido van Rossuma1065681999-01-25 23:20:23 +00005256
Victor Stinner8c62be82010-05-06 00:08:46 +00005257 /* spawnve has four arguments: (mode, path, argv, env), where
5258 argv is a list or tuple of strings and env is a dictionary
5259 like posix.environ. */
Guido van Rossuma1065681999-01-25 23:20:23 +00005260
Larry Hastings2f936352014-08-05 14:04:04 +10005261 path_char = PyBytes_AsString(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00005262 if (PyList_Check(argv)) {
5263 argc = PyList_Size(argv);
5264 getitem = PyList_GetItem;
5265 }
5266 else if (PyTuple_Check(argv)) {
5267 argc = PyTuple_Size(argv);
5268 getitem = PyTuple_GetItem;
5269 }
5270 else {
5271 PyErr_SetString(PyExc_TypeError,
5272 "spawnve() arg 2 must be a tuple or list");
5273 goto fail_0;
5274 }
5275 if (!PyMapping_Check(env)) {
5276 PyErr_SetString(PyExc_TypeError,
5277 "spawnve() arg 3 must be a mapping object");
5278 goto fail_0;
5279 }
Guido van Rossuma1065681999-01-25 23:20:23 +00005280
Victor Stinner8c62be82010-05-06 00:08:46 +00005281 argvlist = PyMem_NEW(char *, argc+1);
5282 if (argvlist == NULL) {
5283 PyErr_NoMemory();
5284 goto fail_0;
5285 }
5286 for (i = 0; i < argc; i++) {
5287 if (!fsconvert_strdup((*getitem)(argv, i),
5288 &argvlist[i]))
5289 {
5290 lastarg = i;
5291 goto fail_1;
5292 }
5293 }
5294 lastarg = argc;
5295 argvlist[argc] = NULL;
Guido van Rossuma1065681999-01-25 23:20:23 +00005296
Victor Stinner8c62be82010-05-06 00:08:46 +00005297 envlist = parse_envlist(env, &envc);
5298 if (envlist == NULL)
5299 goto fail_1;
Guido van Rossuma1065681999-01-25 23:20:23 +00005300
Victor Stinner8c62be82010-05-06 00:08:46 +00005301 if (mode == _OLD_P_OVERLAY)
5302 mode = _P_OVERLAY;
Tim Peters25059d32001-12-07 20:35:43 +00005303
Victor Stinner8c62be82010-05-06 00:08:46 +00005304 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10005305 spawnval = _spawnve(mode, path_char, argvlist, envlist);
Victor Stinner8c62be82010-05-06 00:08:46 +00005306 Py_END_ALLOW_THREADS
Tim Peters25059d32001-12-07 20:35:43 +00005307
Victor Stinner8c62be82010-05-06 00:08:46 +00005308 if (spawnval == -1)
5309 (void) posix_error();
5310 else
Richard Oudkerkac0ad882013-06-05 23:29:30 +01005311 res = Py_BuildValue(_Py_PARSE_INTPTR, spawnval);
Guido van Rossuma1065681999-01-25 23:20:23 +00005312
Victor Stinner8c62be82010-05-06 00:08:46 +00005313 while (--envc >= 0)
5314 PyMem_DEL(envlist[envc]);
5315 PyMem_DEL(envlist);
Guido van Rossum0847c5c2002-12-13 18:36:22 +00005316 fail_1:
Victor Stinner8c62be82010-05-06 00:08:46 +00005317 free_string_array(argvlist, lastarg);
Martin v. Löwis114619e2002-10-07 06:44:21 +00005318 fail_0:
Victor Stinner8c62be82010-05-06 00:08:46 +00005319 return res;
Guido van Rossuma1065681999-01-25 23:20:23 +00005320}
Andrew MacIntyre69e18c92004-04-04 07:11:43 +00005321
Guido van Rossuma1065681999-01-25 23:20:23 +00005322#endif /* HAVE_SPAWNV */
5323
5324
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005325#ifdef HAVE_FORK1
Larry Hastings2f936352014-08-05 14:04:04 +10005326/*[clinic input]
5327os.fork1
5328
5329Fork a child process with a single multiplexed (i.e., not bound) thread.
5330
5331Return 0 to child process and PID of child to parent process.
5332[clinic start generated code]*/
5333
Larry Hastings2f936352014-08-05 14:04:04 +10005334static PyObject *
5335os_fork1_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005336/*[clinic end generated code: output=e27b4f66419c9dcf input=12db02167893926e]*/
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005337{
Victor Stinner8c62be82010-05-06 00:08:46 +00005338 pid_t pid;
5339 int result = 0;
5340 _PyImport_AcquireLock();
5341 pid = fork1();
5342 if (pid == 0) {
5343 /* child: this clobbers and resets the import lock. */
5344 PyOS_AfterFork();
5345 } else {
5346 /* parent: release the import lock. */
5347 result = _PyImport_ReleaseLock();
5348 }
5349 if (pid == -1)
5350 return posix_error();
5351 if (result < 0) {
5352 /* Don't clobber the OSError if the fork failed. */
5353 PyErr_SetString(PyExc_RuntimeError,
5354 "not holding the import lock");
5355 return NULL;
5356 }
5357 return PyLong_FromPid(pid);
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005358}
Larry Hastings2f936352014-08-05 14:04:04 +10005359#endif /* HAVE_FORK1 */
Guido van Rossum2242f2f2001-04-11 20:58:20 +00005360
5361
Guido van Rossumad0ee831995-03-01 10:34:45 +00005362#ifdef HAVE_FORK
Larry Hastings2f936352014-08-05 14:04:04 +10005363/*[clinic input]
5364os.fork
5365
5366Fork a child process.
5367
5368Return 0 to child process and PID of child to parent process.
5369[clinic start generated code]*/
5370
Larry Hastings2f936352014-08-05 14:04:04 +10005371static PyObject *
5372os_fork_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005373/*[clinic end generated code: output=898b1ecd3498ba12 input=13c956413110eeaa]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00005374{
Victor Stinner8c62be82010-05-06 00:08:46 +00005375 pid_t pid;
5376 int result = 0;
5377 _PyImport_AcquireLock();
5378 pid = fork();
5379 if (pid == 0) {
5380 /* child: this clobbers and resets the import lock. */
5381 PyOS_AfterFork();
5382 } else {
5383 /* parent: release the import lock. */
5384 result = _PyImport_ReleaseLock();
5385 }
5386 if (pid == -1)
5387 return posix_error();
5388 if (result < 0) {
5389 /* Don't clobber the OSError if the fork failed. */
5390 PyErr_SetString(PyExc_RuntimeError,
5391 "not holding the import lock");
5392 return NULL;
5393 }
5394 return PyLong_FromPid(pid);
Guido van Rossum85e3b011991-06-03 12:42:10 +00005395}
Larry Hastings2f936352014-08-05 14:04:04 +10005396#endif /* HAVE_FORK */
5397
Guido van Rossum85e3b011991-06-03 12:42:10 +00005398
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005399#ifdef HAVE_SCHED_H
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005400#ifdef HAVE_SCHED_GET_PRIORITY_MAX
Larry Hastings2f936352014-08-05 14:04:04 +10005401/*[clinic input]
5402os.sched_get_priority_max
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005403
Larry Hastings2f936352014-08-05 14:04:04 +10005404 policy: int
5405
5406Get the maximum scheduling priority for policy.
5407[clinic start generated code]*/
5408
Larry Hastings2f936352014-08-05 14:04:04 +10005409static PyObject *
5410os_sched_get_priority_max_impl(PyModuleDef *module, int policy)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005411/*[clinic end generated code: output=a6a30fa5071f2d81 input=2097b7998eca6874]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005412{
5413 int max;
5414
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005415 max = sched_get_priority_max(policy);
5416 if (max < 0)
5417 return posix_error();
5418 return PyLong_FromLong(max);
5419}
5420
Larry Hastings2f936352014-08-05 14:04:04 +10005421
5422/*[clinic input]
5423os.sched_get_priority_min
5424
5425 policy: int
5426
5427Get the minimum scheduling priority for policy.
5428[clinic start generated code]*/
5429
Larry Hastings2f936352014-08-05 14:04:04 +10005430static PyObject *
5431os_sched_get_priority_min_impl(PyModuleDef *module, int policy)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005432/*[clinic end generated code: output=5ca3ed6bc43e9b20 input=21bc8fa0d70983bf]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005433{
5434 int min = sched_get_priority_min(policy);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005435 if (min < 0)
5436 return posix_error();
5437 return PyLong_FromLong(min);
5438}
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02005439#endif /* HAVE_SCHED_GET_PRIORITY_MAX */
5440
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005441
Larry Hastings2f936352014-08-05 14:04:04 +10005442#ifdef HAVE_SCHED_SETSCHEDULER
5443/*[clinic input]
5444os.sched_getscheduler
5445 pid: pid_t
5446 /
5447
5448Get the scheduling policy for the process identifiedy by pid.
5449
5450Passing 0 for pid returns the scheduling policy for the calling process.
5451[clinic start generated code]*/
5452
Larry Hastings2f936352014-08-05 14:04:04 +10005453static PyObject *
5454os_sched_getscheduler_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005455/*[clinic end generated code: output=8cd63c15caf54fa9 input=5f14cfd1f189e1a0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005456{
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005457 int policy;
5458
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005459 policy = sched_getscheduler(pid);
5460 if (policy < 0)
5461 return posix_error();
5462 return PyLong_FromLong(policy);
5463}
Larry Hastings2f936352014-08-05 14:04:04 +10005464#endif /* HAVE_SCHED_SETSCHEDULER */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005465
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005466
5467#if defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM)
Larry Hastings2f936352014-08-05 14:04:04 +10005468/*[clinic input]
5469class os.sched_param "PyObject *" "&SchedParamType"
5470
5471@classmethod
5472os.sched_param.__new__
5473
5474 sched_priority: object
5475 A scheduling parameter.
5476
5477Current has only one field: sched_priority");
5478[clinic start generated code]*/
5479
Larry Hastings2f936352014-08-05 14:04:04 +10005480static PyObject *
5481os_sched_param_impl(PyTypeObject *type, PyObject *sched_priority)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005482/*[clinic end generated code: output=48f4067d60f48c13 input=73a4c22f7071fc62]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005483{
5484 PyObject *res;
5485
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005486 res = PyStructSequence_New(type);
5487 if (!res)
5488 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10005489 Py_INCREF(sched_priority);
5490 PyStructSequence_SET_ITEM(res, 0, sched_priority);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005491 return res;
5492}
5493
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005494
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005495PyDoc_VAR(os_sched_param__doc__);
5496
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005497static PyStructSequence_Field sched_param_fields[] = {
5498 {"sched_priority", "the scheduling priority"},
5499 {0}
5500};
5501
5502static PyStructSequence_Desc sched_param_desc = {
5503 "sched_param", /* name */
Larry Hastings2f936352014-08-05 14:04:04 +10005504 os_sched_param__doc__, /* doc */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005505 sched_param_fields,
5506 1
5507};
5508
5509static int
5510convert_sched_param(PyObject *param, struct sched_param *res)
5511{
5512 long priority;
5513
5514 if (Py_TYPE(param) != &SchedParamType) {
5515 PyErr_SetString(PyExc_TypeError, "must have a sched_param object");
5516 return 0;
5517 }
5518 priority = PyLong_AsLong(PyStructSequence_GET_ITEM(param, 0));
5519 if (priority == -1 && PyErr_Occurred())
5520 return 0;
5521 if (priority > INT_MAX || priority < INT_MIN) {
5522 PyErr_SetString(PyExc_OverflowError, "sched_priority out of range");
5523 return 0;
5524 }
5525 res->sched_priority = Py_SAFE_DOWNCAST(priority, long, int);
5526 return 1;
5527}
Larry Hastings2f936352014-08-05 14:04:04 +10005528#endif /* defined(HAVE_SCHED_SETSCHEDULER) || defined(HAVE_SCHED_SETPARAM) */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005529
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005530
5531#ifdef HAVE_SCHED_SETSCHEDULER
Larry Hastings2f936352014-08-05 14:04:04 +10005532/*[clinic input]
5533os.sched_setscheduler
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005534
Larry Hastings2f936352014-08-05 14:04:04 +10005535 pid: pid_t
5536 policy: int
5537 param: sched_param
5538 /
5539
5540Set the scheduling policy for the process identified by pid.
5541
5542If pid is 0, the calling process is changed.
5543param is an instance of sched_param.
5544[clinic start generated code]*/
5545
Larry Hastings2f936352014-08-05 14:04:04 +10005546static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005547os_sched_setscheduler_impl(PyModuleDef *module, pid_t pid, int policy,
5548 struct sched_param *param)
5549/*[clinic end generated code: output=37053e5c528c35c9 input=c581f9469a5327dd]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005550{
Jesus Cea9c822272011-09-10 01:40:52 +02005551 /*
Jesus Cea54b01492011-09-10 01:53:19 +02005552 ** sched_setscheduler() returns 0 in Linux, but the previous
5553 ** scheduling policy under Solaris/Illumos, and others.
5554 ** On error, -1 is returned in all Operating Systems.
Jesus Cea9c822272011-09-10 01:40:52 +02005555 */
Larry Hastings2f936352014-08-05 14:04:04 +10005556 if (sched_setscheduler(pid, policy, param) == -1)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005557 return posix_error();
5558 Py_RETURN_NONE;
5559}
Larry Hastings2f936352014-08-05 14:04:04 +10005560#endif /* HAVE_SCHED_SETSCHEDULER*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005561
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005562
5563#ifdef HAVE_SCHED_SETPARAM
Larry Hastings2f936352014-08-05 14:04:04 +10005564/*[clinic input]
5565os.sched_getparam
5566 pid: pid_t
5567 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005568
Larry Hastings2f936352014-08-05 14:04:04 +10005569Returns scheduling parameters for the process identified by pid.
5570
5571If pid is 0, returns parameters for the calling process.
5572Return value is an instance of sched_param.
5573[clinic start generated code]*/
5574
Larry Hastings2f936352014-08-05 14:04:04 +10005575static PyObject *
5576os_sched_getparam_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005577/*[clinic end generated code: output=f42c5bd2604ecd08 input=18a1ef9c2efae296]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005578{
5579 struct sched_param param;
5580 PyObject *result;
5581 PyObject *priority;
5582
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005583 if (sched_getparam(pid, &param))
5584 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10005585 result = PyStructSequence_New(&SchedParamType);
5586 if (!result)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005587 return NULL;
5588 priority = PyLong_FromLong(param.sched_priority);
5589 if (!priority) {
Larry Hastings2f936352014-08-05 14:04:04 +10005590 Py_DECREF(result);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005591 return NULL;
5592 }
Larry Hastings2f936352014-08-05 14:04:04 +10005593 PyStructSequence_SET_ITEM(result, 0, priority);
5594 return result;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005595}
5596
Larry Hastings2f936352014-08-05 14:04:04 +10005597
5598/*[clinic input]
5599os.sched_setparam
5600 pid: pid_t
5601 param: sched_param
5602 /
5603
5604Set scheduling parameters for the process identified by pid.
5605
5606If pid is 0, sets parameters for the calling process.
5607param should be an instance of sched_param.
5608[clinic start generated code]*/
5609
Larry Hastings2f936352014-08-05 14:04:04 +10005610static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04005611os_sched_setparam_impl(PyModuleDef *module, pid_t pid,
5612 struct sched_param *param)
5613/*[clinic end generated code: output=b7a3c589436cec9b input=6b8d6dfcecdc21bd]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005614{
5615 if (sched_setparam(pid, param))
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005616 return posix_error();
5617 Py_RETURN_NONE;
5618}
Larry Hastings2f936352014-08-05 14:04:04 +10005619#endif /* HAVE_SCHED_SETPARAM */
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005620
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005621
5622#ifdef HAVE_SCHED_RR_GET_INTERVAL
Larry Hastings2f936352014-08-05 14:04:04 +10005623/*[clinic input]
5624os.sched_rr_get_interval -> double
5625 pid: pid_t
5626 /
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005627
Larry Hastings2f936352014-08-05 14:04:04 +10005628Return the round-robin quantum for the process identified by pid, in seconds.
5629
5630Value returned is a float.
5631[clinic start generated code]*/
5632
Larry Hastings2f936352014-08-05 14:04:04 +10005633static double
5634os_sched_rr_get_interval_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005635/*[clinic end generated code: output=7adc137a86dea581 input=2a973da15cca6fae]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005636{
5637 struct timespec interval;
5638 if (sched_rr_get_interval(pid, &interval)) {
5639 posix_error();
5640 return -1.0;
5641 }
5642 return (double)interval.tv_sec + 1e-9*interval.tv_nsec;
5643}
5644#endif /* HAVE_SCHED_RR_GET_INTERVAL */
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05005645
Larry Hastings2f936352014-08-05 14:04:04 +10005646
5647/*[clinic input]
5648os.sched_yield
5649
5650Voluntarily relinquish the CPU.
5651[clinic start generated code]*/
5652
Larry Hastings2f936352014-08-05 14:04:04 +10005653static PyObject *
5654os_sched_yield_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005655/*[clinic end generated code: output=d7bd51869c4cb6a8 input=e54d6f98189391d4]*/
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005656{
5657 if (sched_yield())
5658 return posix_error();
5659 Py_RETURN_NONE;
5660}
5661
Benjamin Peterson2740af82011-08-02 17:41:34 -05005662#ifdef HAVE_SCHED_SETAFFINITY
Antoine Pitrou84869872012-08-04 16:16:35 +02005663/* The minimum number of CPUs allocated in a cpu_set_t */
5664static const int NCPUS_START = sizeof(unsigned long) * CHAR_BIT;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005665
Larry Hastings2f936352014-08-05 14:04:04 +10005666/*[clinic input]
5667os.sched_setaffinity
5668 pid: pid_t
5669 mask : object
5670 /
5671
5672Set the CPU affinity of the process identified by pid to mask.
5673
5674mask should be an iterable of integers identifying CPUs.
5675[clinic start generated code]*/
5676
Larry Hastings2f936352014-08-05 14:04:04 +10005677static PyObject *
5678os_sched_setaffinity_impl(PyModuleDef *module, pid_t pid, PyObject *mask)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005679/*[clinic end generated code: output=582bcbf40d3253a9 input=a0791a597c7085ba]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005680{
Antoine Pitrou84869872012-08-04 16:16:35 +02005681 int ncpus;
5682 size_t setsize;
Larry Hastings2f936352014-08-05 14:04:04 +10005683 cpu_set_t *cpu_set = NULL;
5684 PyObject *iterator = NULL, *item;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005685
Larry Hastings2f936352014-08-05 14:04:04 +10005686 iterator = PyObject_GetIter(mask);
Antoine Pitrou84869872012-08-04 16:16:35 +02005687 if (iterator == NULL)
5688 return NULL;
5689
5690 ncpus = NCPUS_START;
5691 setsize = CPU_ALLOC_SIZE(ncpus);
Larry Hastings2f936352014-08-05 14:04:04 +10005692 cpu_set = CPU_ALLOC(ncpus);
5693 if (cpu_set == NULL) {
Antoine Pitrou84869872012-08-04 16:16:35 +02005694 PyErr_NoMemory();
5695 goto error;
5696 }
Larry Hastings2f936352014-08-05 14:04:04 +10005697 CPU_ZERO_S(setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005698
5699 while ((item = PyIter_Next(iterator))) {
5700 long cpu;
5701 if (!PyLong_Check(item)) {
5702 PyErr_Format(PyExc_TypeError,
5703 "expected an iterator of ints, "
5704 "but iterator yielded %R",
5705 Py_TYPE(item));
5706 Py_DECREF(item);
5707 goto error;
5708 }
5709 cpu = PyLong_AsLong(item);
5710 Py_DECREF(item);
5711 if (cpu < 0) {
5712 if (!PyErr_Occurred())
5713 PyErr_SetString(PyExc_ValueError, "negative CPU number");
5714 goto error;
5715 }
5716 if (cpu > INT_MAX - 1) {
5717 PyErr_SetString(PyExc_OverflowError, "CPU number too large");
5718 goto error;
5719 }
5720 if (cpu >= ncpus) {
5721 /* Grow CPU mask to fit the CPU number */
5722 int newncpus = ncpus;
5723 cpu_set_t *newmask;
5724 size_t newsetsize;
5725 while (newncpus <= cpu) {
5726 if (newncpus > INT_MAX / 2)
5727 newncpus = cpu + 1;
5728 else
5729 newncpus = newncpus * 2;
5730 }
5731 newmask = CPU_ALLOC(newncpus);
5732 if (newmask == NULL) {
5733 PyErr_NoMemory();
5734 goto error;
5735 }
5736 newsetsize = CPU_ALLOC_SIZE(newncpus);
5737 CPU_ZERO_S(newsetsize, newmask);
Larry Hastings2f936352014-08-05 14:04:04 +10005738 memcpy(newmask, cpu_set, setsize);
5739 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005740 setsize = newsetsize;
Larry Hastings2f936352014-08-05 14:04:04 +10005741 cpu_set = newmask;
Antoine Pitrou84869872012-08-04 16:16:35 +02005742 ncpus = newncpus;
5743 }
Larry Hastings2f936352014-08-05 14:04:04 +10005744 CPU_SET_S(cpu, setsize, cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005745 }
5746 Py_CLEAR(iterator);
5747
Larry Hastings2f936352014-08-05 14:04:04 +10005748 if (sched_setaffinity(pid, setsize, cpu_set)) {
Antoine Pitrou84869872012-08-04 16:16:35 +02005749 posix_error();
5750 goto error;
5751 }
Larry Hastings2f936352014-08-05 14:04:04 +10005752 CPU_FREE(cpu_set);
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005753 Py_RETURN_NONE;
Antoine Pitrou84869872012-08-04 16:16:35 +02005754
5755error:
Larry Hastings2f936352014-08-05 14:04:04 +10005756 if (cpu_set)
5757 CPU_FREE(cpu_set);
Antoine Pitrou84869872012-08-04 16:16:35 +02005758 Py_XDECREF(iterator);
5759 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005760}
5761
Larry Hastings2f936352014-08-05 14:04:04 +10005762
5763/*[clinic input]
5764os.sched_getaffinity
5765 pid: pid_t
5766 /
5767
Charles-François Natalidc87e4b2015-07-13 21:01:39 +01005768Return the affinity of the process identified by pid (or the current process if zero).
Larry Hastings2f936352014-08-05 14:04:04 +10005769
5770The affinity is returned as a set of CPU identifiers.
5771[clinic start generated code]*/
5772
Larry Hastings2f936352014-08-05 14:04:04 +10005773static PyObject *
5774os_sched_getaffinity_impl(PyModuleDef *module, pid_t pid)
Charles-François Natali80d62e62015-08-13 20:37:08 +01005775/*[clinic end generated code: output=b431a8f310e369e7 input=983ce7cb4a565980]*/
Larry Hastings2f936352014-08-05 14:04:04 +10005776{
Antoine Pitrou84869872012-08-04 16:16:35 +02005777 int cpu, ncpus, count;
5778 size_t setsize;
5779 cpu_set_t *mask = NULL;
5780 PyObject *res = NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005781
Antoine Pitrou84869872012-08-04 16:16:35 +02005782 ncpus = NCPUS_START;
5783 while (1) {
5784 setsize = CPU_ALLOC_SIZE(ncpus);
5785 mask = CPU_ALLOC(ncpus);
5786 if (mask == NULL)
5787 return PyErr_NoMemory();
5788 if (sched_getaffinity(pid, setsize, mask) == 0)
5789 break;
5790 CPU_FREE(mask);
5791 if (errno != EINVAL)
5792 return posix_error();
5793 if (ncpus > INT_MAX / 2) {
5794 PyErr_SetString(PyExc_OverflowError, "could not allocate "
5795 "a large enough CPU set");
5796 return NULL;
5797 }
5798 ncpus = ncpus * 2;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005799 }
Antoine Pitrou84869872012-08-04 16:16:35 +02005800
5801 res = PySet_New(NULL);
5802 if (res == NULL)
5803 goto error;
5804 for (cpu = 0, count = CPU_COUNT_S(setsize, mask); count; cpu++) {
5805 if (CPU_ISSET_S(cpu, setsize, mask)) {
5806 PyObject *cpu_num = PyLong_FromLong(cpu);
5807 --count;
5808 if (cpu_num == NULL)
5809 goto error;
5810 if (PySet_Add(res, cpu_num)) {
5811 Py_DECREF(cpu_num);
5812 goto error;
5813 }
5814 Py_DECREF(cpu_num);
5815 }
5816 }
5817 CPU_FREE(mask);
5818 return res;
5819
5820error:
5821 if (mask)
5822 CPU_FREE(mask);
5823 Py_XDECREF(res);
5824 return NULL;
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005825}
5826
Benjamin Peterson2740af82011-08-02 17:41:34 -05005827#endif /* HAVE_SCHED_SETAFFINITY */
5828
Benjamin Peterson94b580d2011-08-02 17:30:04 -05005829#endif /* HAVE_SCHED_H */
5830
Larry Hastings2f936352014-08-05 14:04:04 +10005831
Neal Norwitzb59798b2003-03-21 01:43:31 +00005832/* AIX uses /dev/ptc but is otherwise the same as /dev/ptmx */
Neal Norwitz2deaddb2003-03-21 03:08:31 +00005833/* IRIX has both /dev/ptc and /dev/ptmx, use ptmx */
5834#if defined(HAVE_DEV_PTC) && !defined(HAVE_DEV_PTMX)
Neal Norwitzb59798b2003-03-21 01:43:31 +00005835#define DEV_PTY_FILE "/dev/ptc"
5836#define HAVE_DEV_PTMX
5837#else
5838#define DEV_PTY_FILE "/dev/ptmx"
5839#endif
5840
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005841#if defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX)
Fred Drake8cef4cf2000-06-28 16:40:38 +00005842#ifdef HAVE_PTY_H
5843#include <pty.h>
5844#else
5845#ifdef HAVE_LIBUTIL_H
5846#include <libutil.h>
Ronald Oussoren755740f2010-02-07 19:56:39 +00005847#else
5848#ifdef HAVE_UTIL_H
5849#include <util.h>
5850#endif /* HAVE_UTIL_H */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005851#endif /* HAVE_LIBUTIL_H */
5852#endif /* HAVE_PTY_H */
Martin v. Löwis14e73b12003-01-01 09:51:12 +00005853#ifdef HAVE_STROPTS_H
5854#include <stropts.h>
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005855#endif
5856#endif /* defined(HAVE_OPENPTY) || defined(HAVE_FORKPTY) || defined(HAVE_DEV_PTMX */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005857
Larry Hastings2f936352014-08-05 14:04:04 +10005858
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005859#if defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX)
Larry Hastings2f936352014-08-05 14:04:04 +10005860/*[clinic input]
5861os.openpty
5862
5863Open a pseudo-terminal.
5864
5865Return a tuple of (master_fd, slave_fd) containing open file descriptors
5866for both the master and slave ends.
5867[clinic start generated code]*/
5868
Larry Hastings2f936352014-08-05 14:04:04 +10005869static PyObject *
5870os_openpty_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005871/*[clinic end generated code: output=358e571c1ba135ee input=f3d99fd99e762907]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00005872{
Victor Stinnerdaf45552013-08-28 00:53:59 +02005873 int master_fd = -1, slave_fd = -1;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005874#ifndef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00005875 char * slave_name;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005876#endif
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005877#if defined(HAVE_DEV_PTMX) && !defined(HAVE_OPENPTY) && !defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005878 PyOS_sighandler_t sig_saved;
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005879#ifdef sun
Victor Stinner8c62be82010-05-06 00:08:46 +00005880 extern char *ptsname(int fildes);
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005881#endif
5882#endif
Thomas Wouters70c21a12000-07-14 14:28:33 +00005883
Thomas Wouters70c21a12000-07-14 14:28:33 +00005884#ifdef HAVE_OPENPTY
Victor Stinner8c62be82010-05-06 00:08:46 +00005885 if (openpty(&master_fd, &slave_fd, NULL, NULL, NULL) != 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005886 goto posix_error;
5887
5888 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5889 goto error;
5890 if (_Py_set_inheritable(slave_fd, 0, NULL) < 0)
5891 goto error;
5892
Neal Norwitzb59798b2003-03-21 01:43:31 +00005893#elif defined(HAVE__GETPTY)
Victor Stinner8c62be82010-05-06 00:08:46 +00005894 slave_name = _getpty(&master_fd, O_RDWR, 0666, 0);
5895 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005896 goto posix_error;
5897 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5898 goto error;
Thomas Wouters70c21a12000-07-14 14:28:33 +00005899
Victor Stinnerdaf45552013-08-28 00:53:59 +02005900 slave_fd = _Py_open(slave_name, O_RDWR);
Victor Stinner8c62be82010-05-06 00:08:46 +00005901 if (slave_fd < 0)
Victor Stinnera555cfc2015-03-18 00:22:14 +01005902 goto error;
Victor Stinnerdaf45552013-08-28 00:53:59 +02005903
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005904#else
Victor Stinner000de532013-11-25 23:19:58 +01005905 master_fd = open(DEV_PTY_FILE, O_RDWR | O_NOCTTY); /* open master */
Victor Stinner8c62be82010-05-06 00:08:46 +00005906 if (master_fd < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005907 goto posix_error;
5908
Victor Stinner8c62be82010-05-06 00:08:46 +00005909 sig_saved = PyOS_setsig(SIGCHLD, SIG_DFL);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005910
Victor Stinner8c62be82010-05-06 00:08:46 +00005911 /* change permission of slave */
5912 if (grantpt(master_fd) < 0) {
5913 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005914 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00005915 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02005916
Victor Stinner8c62be82010-05-06 00:08:46 +00005917 /* unlock slave */
5918 if (unlockpt(master_fd) < 0) {
5919 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005920 goto posix_error;
Victor Stinner8c62be82010-05-06 00:08:46 +00005921 }
Victor Stinnerdaf45552013-08-28 00:53:59 +02005922
Victor Stinner8c62be82010-05-06 00:08:46 +00005923 PyOS_setsig(SIGCHLD, sig_saved);
Victor Stinnerdaf45552013-08-28 00:53:59 +02005924
Victor Stinner8c62be82010-05-06 00:08:46 +00005925 slave_name = ptsname(master_fd); /* get name of slave */
5926 if (slave_name == NULL)
Victor Stinnerdaf45552013-08-28 00:53:59 +02005927 goto posix_error;
5928
5929 slave_fd = _Py_open(slave_name, O_RDWR | O_NOCTTY); /* open slave */
Victor Stinnera555cfc2015-03-18 00:22:14 +01005930 if (slave_fd == -1)
5931 goto error;
Victor Stinner000de532013-11-25 23:19:58 +01005932
5933 if (_Py_set_inheritable(master_fd, 0, NULL) < 0)
5934 goto posix_error;
5935
Neal Norwitzb59798b2003-03-21 01:43:31 +00005936#if !defined(__CYGWIN__) && !defined(HAVE_DEV_PTC)
Victor Stinner8c62be82010-05-06 00:08:46 +00005937 ioctl(slave_fd, I_PUSH, "ptem"); /* push ptem */
5938 ioctl(slave_fd, I_PUSH, "ldterm"); /* push ldterm */
Neal Norwitz6700e472002-12-31 16:16:07 +00005939#ifndef __hpux
Victor Stinner8c62be82010-05-06 00:08:46 +00005940 ioctl(slave_fd, I_PUSH, "ttcompat"); /* push ttcompat */
Neal Norwitz6700e472002-12-31 16:16:07 +00005941#endif /* __hpux */
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005942#endif /* HAVE_CYGWIN */
Thomas Wouters1e0c2f42000-07-24 16:06:23 +00005943#endif /* HAVE_OPENPTY */
Thomas Wouters70c21a12000-07-14 14:28:33 +00005944
Victor Stinner8c62be82010-05-06 00:08:46 +00005945 return Py_BuildValue("(ii)", master_fd, slave_fd);
Thomas Wouters70c21a12000-07-14 14:28:33 +00005946
Victor Stinnerdaf45552013-08-28 00:53:59 +02005947posix_error:
5948 posix_error();
5949error:
5950 if (master_fd != -1)
5951 close(master_fd);
5952 if (slave_fd != -1)
5953 close(slave_fd);
5954 return NULL;
Fred Drake8cef4cf2000-06-28 16:40:38 +00005955}
Martin v. Löwis24a880b2002-12-31 12:55:15 +00005956#endif /* defined(HAVE_OPENPTY) || defined(HAVE__GETPTY) || defined(HAVE_DEV_PTMX) */
Fred Drake8cef4cf2000-06-28 16:40:38 +00005957
Larry Hastings2f936352014-08-05 14:04:04 +10005958
Fred Drake8cef4cf2000-06-28 16:40:38 +00005959#ifdef HAVE_FORKPTY
Larry Hastings2f936352014-08-05 14:04:04 +10005960/*[clinic input]
5961os.forkpty
5962
5963Fork a new process with a new pseudo-terminal as controlling tty.
5964
5965Returns a tuple of (pid, master_fd).
5966Like fork(), return pid of 0 to the child process,
5967and pid of child to the parent process.
5968To both, return fd of newly opened pseudo-terminal.
5969[clinic start generated code]*/
5970
Larry Hastings2f936352014-08-05 14:04:04 +10005971static PyObject *
5972os_forkpty_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03005973/*[clinic end generated code: output=a11b8391dce3cb57 input=f1f7f4bae3966010]*/
Fred Drake8cef4cf2000-06-28 16:40:38 +00005974{
Victor Stinner8c62be82010-05-06 00:08:46 +00005975 int master_fd = -1, result = 0;
5976 pid_t pid;
Tim Peters5aa91602002-01-30 05:46:57 +00005977
Victor Stinner8c62be82010-05-06 00:08:46 +00005978 _PyImport_AcquireLock();
5979 pid = forkpty(&master_fd, NULL, NULL, NULL);
5980 if (pid == 0) {
5981 /* child: this clobbers and resets the import lock. */
5982 PyOS_AfterFork();
5983 } else {
5984 /* parent: release the import lock. */
5985 result = _PyImport_ReleaseLock();
5986 }
5987 if (pid == -1)
5988 return posix_error();
5989 if (result < 0) {
5990 /* Don't clobber the OSError if the fork failed. */
5991 PyErr_SetString(PyExc_RuntimeError,
5992 "not holding the import lock");
5993 return NULL;
5994 }
5995 return Py_BuildValue("(Ni)", PyLong_FromPid(pid), master_fd);
Fred Drake8cef4cf2000-06-28 16:40:38 +00005996}
Larry Hastings2f936352014-08-05 14:04:04 +10005997#endif /* HAVE_FORKPTY */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00005998
Ross Lagerwall7807c352011-03-17 20:20:30 +02005999
Guido van Rossumad0ee831995-03-01 10:34:45 +00006000#ifdef HAVE_GETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10006001/*[clinic input]
6002os.getegid
6003
6004Return the current process's effective group id.
6005[clinic start generated code]*/
6006
Larry Hastings2f936352014-08-05 14:04:04 +10006007static PyObject *
6008os_getegid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006009/*[clinic end generated code: output=90f433a8c0b1d919 input=1596f79ad1107d5d]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006010{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006011 return _PyLong_FromGid(getegid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006012}
Larry Hastings2f936352014-08-05 14:04:04 +10006013#endif /* HAVE_GETEGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006014
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006015
Guido van Rossumad0ee831995-03-01 10:34:45 +00006016#ifdef HAVE_GETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10006017/*[clinic input]
6018os.geteuid
6019
6020Return the current process's effective user id.
6021[clinic start generated code]*/
6022
Larry Hastings2f936352014-08-05 14:04:04 +10006023static PyObject *
6024os_geteuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006025/*[clinic end generated code: output=1a532c4a66874357 input=4644c662d3bd9f19]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006026{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006027 return _PyLong_FromUid(geteuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006028}
Larry Hastings2f936352014-08-05 14:04:04 +10006029#endif /* HAVE_GETEUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006030
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006031
Guido van Rossumad0ee831995-03-01 10:34:45 +00006032#ifdef HAVE_GETGID
Larry Hastings2f936352014-08-05 14:04:04 +10006033/*[clinic input]
6034os.getgid
6035
6036Return the current process's group id.
6037[clinic start generated code]*/
6038
Larry Hastings2f936352014-08-05 14:04:04 +10006039static PyObject *
6040os_getgid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006041/*[clinic end generated code: output=91a22021b74ea46b input=58796344cd87c0f6]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006042{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006043 return _PyLong_FromGid(getgid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006044}
Larry Hastings2f936352014-08-05 14:04:04 +10006045#endif /* HAVE_GETGID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006046
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006047
Larry Hastings2f936352014-08-05 14:04:04 +10006048/*[clinic input]
6049os.getpid
6050
6051Return the current process id.
6052[clinic start generated code]*/
6053
Larry Hastings2f936352014-08-05 14:04:04 +10006054static PyObject *
6055os_getpid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006056/*[clinic end generated code: output=8fbf3a934ee09e62 input=5a9a00f0ab68aa00]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00006057{
Victor Stinner8c62be82010-05-06 00:08:46 +00006058 return PyLong_FromPid(getpid());
Guido van Rossum85e3b011991-06-03 12:42:10 +00006059}
6060
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006061#ifdef HAVE_GETGROUPLIST
Larry Hastings2f936352014-08-05 14:04:04 +10006062
6063/* AC 3.5: funny apple logic below */
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006064PyDoc_STRVAR(posix_getgrouplist__doc__,
6065"getgrouplist(user, group) -> list of groups to which a user belongs\n\n\
6066Returns a list of groups to which a user belongs.\n\n\
6067 user: username to lookup\n\
6068 group: base group id of the user");
6069
6070static PyObject *
6071posix_getgrouplist(PyObject *self, PyObject *args)
6072{
6073#ifdef NGROUPS_MAX
6074#define MAX_GROUPS NGROUPS_MAX
6075#else
6076 /* defined to be 16 on Solaris7, so this should be a small number */
6077#define MAX_GROUPS 64
6078#endif
6079
6080 const char *user;
6081 int i, ngroups;
6082 PyObject *list;
6083#ifdef __APPLE__
6084 int *groups, basegid;
6085#else
6086 gid_t *groups, basegid;
6087#endif
6088 ngroups = MAX_GROUPS;
6089
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006090#ifdef __APPLE__
6091 if (!PyArg_ParseTuple(args, "si:getgrouplist", &user, &basegid))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006092 return NULL;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006093#else
6094 if (!PyArg_ParseTuple(args, "sO&:getgrouplist", &user,
6095 _Py_Gid_Converter, &basegid))
6096 return NULL;
6097#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006098
6099#ifdef __APPLE__
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006100 groups = PyMem_New(int, ngroups);
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006101#else
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006102 groups = PyMem_New(gid_t, ngroups);
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006103#endif
6104 if (groups == NULL)
6105 return PyErr_NoMemory();
6106
6107 if (getgrouplist(user, basegid, groups, &ngroups) == -1) {
6108 PyMem_Del(groups);
6109 return posix_error();
6110 }
6111
6112 list = PyList_New(ngroups);
6113 if (list == NULL) {
6114 PyMem_Del(groups);
6115 return NULL;
6116 }
6117
6118 for (i = 0; i < ngroups; i++) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006119#ifdef __APPLE__
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006120 PyObject *o = PyLong_FromUnsignedLong((unsigned long)groups[i]);
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006121#else
6122 PyObject *o = _PyLong_FromGid(groups[i]);
6123#endif
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +02006124 if (o == NULL) {
6125 Py_DECREF(list);
6126 PyMem_Del(groups);
6127 return NULL;
6128 }
6129 PyList_SET_ITEM(list, i, o);
6130 }
6131
6132 PyMem_Del(groups);
6133
6134 return list;
6135}
Larry Hastings2f936352014-08-05 14:04:04 +10006136#endif /* HAVE_GETGROUPLIST */
6137
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006138
Fred Drakec9680921999-12-13 16:37:25 +00006139#ifdef HAVE_GETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10006140/*[clinic input]
6141os.getgroups
6142
6143Return list of supplemental group IDs for the process.
6144[clinic start generated code]*/
6145
Larry Hastings2f936352014-08-05 14:04:04 +10006146static PyObject *
6147os_getgroups_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006148/*[clinic end generated code: output=6e7c4fd2db6d5c60 input=d3f109412e6a155c]*/
Fred Drakec9680921999-12-13 16:37:25 +00006149{
6150 PyObject *result = NULL;
6151
Fred Drakec9680921999-12-13 16:37:25 +00006152#ifdef NGROUPS_MAX
6153#define MAX_GROUPS NGROUPS_MAX
6154#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006155 /* defined to be 16 on Solaris7, so this should be a small number */
Fred Drakec9680921999-12-13 16:37:25 +00006156#define MAX_GROUPS 64
6157#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00006158 gid_t grouplist[MAX_GROUPS];
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006159
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006160 /* On MacOSX getgroups(2) can return more than MAX_GROUPS results
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006161 * This is a helper variable to store the intermediate result when
6162 * that happens.
6163 *
6164 * To keep the code readable the OSX behaviour is unconditional,
6165 * according to the POSIX spec this should be safe on all unix-y
6166 * systems.
6167 */
6168 gid_t* alt_grouplist = grouplist;
Victor Stinner8c62be82010-05-06 00:08:46 +00006169 int n;
Fred Drakec9680921999-12-13 16:37:25 +00006170
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006171#ifdef __APPLE__
6172 /* Issue #17557: As of OS X 10.8, getgroups(2) no longer raises EINVAL if
6173 * there are more groups than can fit in grouplist. Therefore, on OS X
6174 * always first call getgroups with length 0 to get the actual number
6175 * of groups.
6176 */
6177 n = getgroups(0, NULL);
6178 if (n < 0) {
6179 return posix_error();
6180 } else if (n <= MAX_GROUPS) {
6181 /* groups will fit in existing array */
6182 alt_grouplist = grouplist;
6183 } else {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006184 alt_grouplist = PyMem_New(gid_t, n);
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006185 if (alt_grouplist == NULL) {
6186 errno = EINVAL;
6187 return posix_error();
6188 }
6189 }
6190
6191 n = getgroups(n, alt_grouplist);
6192 if (n == -1) {
6193 if (alt_grouplist != grouplist) {
6194 PyMem_Free(alt_grouplist);
6195 }
6196 return posix_error();
6197 }
6198#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006199 n = getgroups(MAX_GROUPS, grouplist);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006200 if (n < 0) {
6201 if (errno == EINVAL) {
6202 n = getgroups(0, NULL);
6203 if (n == -1) {
6204 return posix_error();
6205 }
6206 if (n == 0) {
6207 /* Avoid malloc(0) */
6208 alt_grouplist = grouplist;
6209 } else {
Serhiy Storchaka1a1ff292015-02-16 13:28:22 +02006210 alt_grouplist = PyMem_New(gid_t, n);
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006211 if (alt_grouplist == NULL) {
6212 errno = EINVAL;
6213 return posix_error();
6214 }
6215 n = getgroups(n, alt_grouplist);
6216 if (n == -1) {
6217 PyMem_Free(alt_grouplist);
6218 return posix_error();
6219 }
6220 }
6221 } else {
6222 return posix_error();
6223 }
6224 }
Ned Deilyb5dd6d22013-08-01 21:21:15 -07006225#endif
6226
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006227 result = PyList_New(n);
6228 if (result != NULL) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006229 int i;
6230 for (i = 0; i < n; ++i) {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006231 PyObject *o = _PyLong_FromGid(alt_grouplist[i]);
Victor Stinner8c62be82010-05-06 00:08:46 +00006232 if (o == NULL) {
Stefan Krah0e803b32010-11-26 16:16:47 +00006233 Py_DECREF(result);
6234 result = NULL;
6235 break;
Fred Drakec9680921999-12-13 16:37:25 +00006236 }
Victor Stinner8c62be82010-05-06 00:08:46 +00006237 PyList_SET_ITEM(result, i, o);
Fred Drakec9680921999-12-13 16:37:25 +00006238 }
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00006239 }
6240
6241 if (alt_grouplist != grouplist) {
6242 PyMem_Free(alt_grouplist);
Victor Stinner8c62be82010-05-06 00:08:46 +00006243 }
Neal Norwitze241ce82003-02-17 18:17:05 +00006244
Fred Drakec9680921999-12-13 16:37:25 +00006245 return result;
6246}
Larry Hastings2f936352014-08-05 14:04:04 +10006247#endif /* HAVE_GETGROUPS */
Fred Drakec9680921999-12-13 16:37:25 +00006248
Antoine Pitroub7572f02009-12-02 20:46:48 +00006249#ifdef HAVE_INITGROUPS
6250PyDoc_STRVAR(posix_initgroups__doc__,
6251"initgroups(username, gid) -> None\n\n\
6252Call the system initgroups() to initialize the group access list with all of\n\
6253the groups of which the specified username is a member, plus the specified\n\
6254group id.");
6255
Larry Hastings2f936352014-08-05 14:04:04 +10006256/* AC 3.5: funny apple logic */
Antoine Pitroub7572f02009-12-02 20:46:48 +00006257static PyObject *
6258posix_initgroups(PyObject *self, PyObject *args)
6259{
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006260 PyObject *oname;
Victor Stinner8c62be82010-05-06 00:08:46 +00006261 char *username;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006262 int res;
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006263#ifdef __APPLE__
6264 int gid;
6265#else
6266 gid_t gid;
6267#endif
Antoine Pitroub7572f02009-12-02 20:46:48 +00006268
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006269#ifdef __APPLE__
6270 if (!PyArg_ParseTuple(args, "O&i:initgroups",
6271 PyUnicode_FSConverter, &oname,
6272 &gid))
6273#else
6274 if (!PyArg_ParseTuple(args, "O&O&:initgroups",
6275 PyUnicode_FSConverter, &oname,
6276 _Py_Gid_Converter, &gid))
6277#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00006278 return NULL;
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006279 username = PyBytes_AS_STRING(oname);
Antoine Pitroub7572f02009-12-02 20:46:48 +00006280
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006281 res = initgroups(username, gid);
Victor Stinner61ec5dc2010-08-15 09:22:44 +00006282 Py_DECREF(oname);
6283 if (res == -1)
Victor Stinner8c62be82010-05-06 00:08:46 +00006284 return PyErr_SetFromErrno(PyExc_OSError);
Antoine Pitroub7572f02009-12-02 20:46:48 +00006285
Victor Stinner8c62be82010-05-06 00:08:46 +00006286 Py_INCREF(Py_None);
6287 return Py_None;
Antoine Pitroub7572f02009-12-02 20:46:48 +00006288}
Larry Hastings2f936352014-08-05 14:04:04 +10006289#endif /* HAVE_INITGROUPS */
6290
Antoine Pitroub7572f02009-12-02 20:46:48 +00006291
Martin v. Löwis606edc12002-06-13 21:09:11 +00006292#ifdef HAVE_GETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10006293/*[clinic input]
6294os.getpgid
6295
6296 pid: pid_t
6297
6298Call the system call getpgid(), and return the result.
6299[clinic start generated code]*/
6300
Larry Hastings2f936352014-08-05 14:04:04 +10006301static PyObject *
6302os_getpgid_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006303/*[clinic end generated code: output=70e713b4d54b7c61 input=39d710ae3baaf1c7]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006304{
6305 pid_t pgid = getpgid(pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00006306 if (pgid < 0)
6307 return posix_error();
6308 return PyLong_FromPid(pgid);
Martin v. Löwis606edc12002-06-13 21:09:11 +00006309}
6310#endif /* HAVE_GETPGID */
6311
6312
Guido van Rossumb6775db1994-08-01 11:34:53 +00006313#ifdef HAVE_GETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10006314/*[clinic input]
6315os.getpgrp
6316
6317Return the current process group id.
6318[clinic start generated code]*/
6319
Larry Hastings2f936352014-08-05 14:04:04 +10006320static PyObject *
6321os_getpgrp_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006322/*[clinic end generated code: output=cf3403585846811f input=6846fb2bb9a3705e]*/
Guido van Rossum04814471991-06-04 20:23:49 +00006323{
Guido van Rossumb6775db1994-08-01 11:34:53 +00006324#ifdef GETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00006325 return PyLong_FromPid(getpgrp(0));
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006326#else /* GETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006327 return PyLong_FromPid(getpgrp());
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006328#endif /* GETPGRP_HAVE_ARG */
Guido van Rossum04814471991-06-04 20:23:49 +00006329}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006330#endif /* HAVE_GETPGRP */
Guido van Rossum04814471991-06-04 20:23:49 +00006331
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006332
Guido van Rossumb6775db1994-08-01 11:34:53 +00006333#ifdef HAVE_SETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10006334/*[clinic input]
6335os.setpgrp
6336
6337Make the current process the leader of its process group.
6338[clinic start generated code]*/
6339
Larry Hastings2f936352014-08-05 14:04:04 +10006340static PyObject *
6341os_setpgrp_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006342/*[clinic end generated code: output=59650f55a963d7ac input=1f0619fcb5731e7e]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00006343{
Guido van Rossum64933891994-10-20 21:56:42 +00006344#ifdef SETPGRP_HAVE_ARG
Victor Stinner8c62be82010-05-06 00:08:46 +00006345 if (setpgrp(0, 0) < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00006346#else /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006347 if (setpgrp() < 0)
Guido van Rossum64933891994-10-20 21:56:42 +00006348#endif /* SETPGRP_HAVE_ARG */
Victor Stinner8c62be82010-05-06 00:08:46 +00006349 return posix_error();
6350 Py_INCREF(Py_None);
6351 return Py_None;
Guido van Rossumc2670a01992-09-13 20:07:29 +00006352}
Guido van Rossumb6775db1994-08-01 11:34:53 +00006353#endif /* HAVE_SETPGRP */
6354
Guido van Rossumad0ee831995-03-01 10:34:45 +00006355#ifdef HAVE_GETPPID
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006356
6357#ifdef MS_WINDOWS
6358#include <tlhelp32.h>
6359
6360static PyObject*
6361win32_getppid()
6362{
6363 HANDLE snapshot;
6364 pid_t mypid;
6365 PyObject* result = NULL;
6366 BOOL have_record;
6367 PROCESSENTRY32 pe;
6368
6369 mypid = getpid(); /* This function never fails */
6370
6371 snapshot = CreateToolhelp32Snapshot(TH32CS_SNAPPROCESS, 0);
6372 if (snapshot == INVALID_HANDLE_VALUE)
6373 return PyErr_SetFromWindowsErr(GetLastError());
6374
6375 pe.dwSize = sizeof(pe);
6376 have_record = Process32First(snapshot, &pe);
6377 while (have_record) {
6378 if (mypid == (pid_t)pe.th32ProcessID) {
6379 /* We could cache the ulong value in a static variable. */
6380 result = PyLong_FromPid((pid_t)pe.th32ParentProcessID);
6381 break;
6382 }
6383
6384 have_record = Process32Next(snapshot, &pe);
6385 }
6386
6387 /* If our loop exits and our pid was not found (result will be NULL)
6388 * then GetLastError will return ERROR_NO_MORE_FILES. This is an
6389 * error anyway, so let's raise it. */
6390 if (!result)
6391 result = PyErr_SetFromWindowsErr(GetLastError());
6392
6393 CloseHandle(snapshot);
6394
6395 return result;
6396}
6397#endif /*MS_WINDOWS*/
6398
Larry Hastings2f936352014-08-05 14:04:04 +10006399
6400/*[clinic input]
6401os.getppid
6402
6403Return the parent's process id.
6404
6405If the parent process has already exited, Windows machines will still
6406return its id; others systems will return the id of the 'init' process (1).
6407[clinic start generated code]*/
6408
Larry Hastings2f936352014-08-05 14:04:04 +10006409static PyObject *
6410os_getppid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006411/*[clinic end generated code: output=4e49c8e7a8738cd2 input=e637cb87539c030e]*/
Guido van Rossum85e3b011991-06-03 12:42:10 +00006412{
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006413#ifdef MS_WINDOWS
6414 return win32_getppid();
6415#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006416 return PyLong_FromPid(getppid());
Guido van Rossumad0ee831995-03-01 10:34:45 +00006417#endif
Amaury Forgeot d'Arc4b6fdf32010-09-07 21:31:17 +00006418}
6419#endif /* HAVE_GETPPID */
Guido van Rossum85e3b011991-06-03 12:42:10 +00006420
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006421
Fred Drake12c6e2d1999-12-14 21:25:03 +00006422#ifdef HAVE_GETLOGIN
Larry Hastings2f936352014-08-05 14:04:04 +10006423/*[clinic input]
6424os.getlogin
6425
6426Return the actual login name.
6427[clinic start generated code]*/
6428
Larry Hastings2f936352014-08-05 14:04:04 +10006429static PyObject *
6430os_getlogin_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006431/*[clinic end generated code: output=037ebdb3e4b5dac1 input=2a21ab1e917163df]*/
Fred Drake12c6e2d1999-12-14 21:25:03 +00006432{
Victor Stinner8c62be82010-05-06 00:08:46 +00006433 PyObject *result = NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006434#ifdef MS_WINDOWS
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006435 wchar_t user_name[UNLEN + 1];
Victor Stinner63941882011-09-29 00:42:28 +02006436 DWORD num_chars = Py_ARRAY_LENGTH(user_name);
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006437
6438 if (GetUserNameW(user_name, &num_chars)) {
6439 /* num_chars is the number of unicode chars plus null terminator */
6440 result = PyUnicode_FromWideChar(user_name, num_chars - 1);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00006441 }
6442 else
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006443 result = PyErr_SetFromWindowsErr(GetLastError());
6444#else
Victor Stinner8c62be82010-05-06 00:08:46 +00006445 char *name;
6446 int old_errno = errno;
Fred Drake12c6e2d1999-12-14 21:25:03 +00006447
Victor Stinner8c62be82010-05-06 00:08:46 +00006448 errno = 0;
6449 name = getlogin();
6450 if (name == NULL) {
6451 if (errno)
Victor Stinnere039ffe2010-08-15 09:33:08 +00006452 posix_error();
Fred Drake12c6e2d1999-12-14 21:25:03 +00006453 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00006454 PyErr_SetString(PyExc_OSError, "unable to determine login name");
Victor Stinner8c62be82010-05-06 00:08:46 +00006455 }
6456 else
Victor Stinnere039ffe2010-08-15 09:33:08 +00006457 result = PyUnicode_DecodeFSDefault(name);
Victor Stinner8c62be82010-05-06 00:08:46 +00006458 errno = old_errno;
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006459#endif
Fred Drake12c6e2d1999-12-14 21:25:03 +00006460 return result;
6461}
Brian Curtine8e4b3b2010-09-23 20:04:14 +00006462#endif /* HAVE_GETLOGIN */
Fred Drake12c6e2d1999-12-14 21:25:03 +00006463
Larry Hastings2f936352014-08-05 14:04:04 +10006464
Guido van Rossumad0ee831995-03-01 10:34:45 +00006465#ifdef HAVE_GETUID
Larry Hastings2f936352014-08-05 14:04:04 +10006466/*[clinic input]
6467os.getuid
6468
6469Return the current process's user id.
6470[clinic start generated code]*/
6471
Larry Hastings2f936352014-08-05 14:04:04 +10006472static PyObject *
6473os_getuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006474/*[clinic end generated code: output=03a8b894cefb3fa5 input=b53c8b35f110a516]*/
Guido van Rossum46003ff1992-05-15 11:05:24 +00006475{
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006476 return _PyLong_FromUid(getuid());
Guido van Rossum46003ff1992-05-15 11:05:24 +00006477}
Larry Hastings2f936352014-08-05 14:04:04 +10006478#endif /* HAVE_GETUID */
Guido van Rossum46003ff1992-05-15 11:05:24 +00006479
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006480
Brian Curtineb24d742010-04-12 17:16:38 +00006481#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10006482#define HAVE_KILL
6483#endif /* MS_WINDOWS */
6484
6485#ifdef HAVE_KILL
6486/*[clinic input]
6487os.kill
6488
6489 pid: pid_t
6490 signal: Py_ssize_t
6491 /
6492
6493Kill a process with a signal.
6494[clinic start generated code]*/
6495
Larry Hastings2f936352014-08-05 14:04:04 +10006496static PyObject *
6497os_kill_impl(PyModuleDef *module, pid_t pid, Py_ssize_t signal)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006498/*[clinic end generated code: output=74f907dd00a83c26 input=61a36b86ca275ab9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006499#ifndef MS_WINDOWS
6500{
6501 if (kill(pid, (int)signal) == -1)
6502 return posix_error();
6503 Py_RETURN_NONE;
6504}
6505#else /* !MS_WINDOWS */
Brian Curtineb24d742010-04-12 17:16:38 +00006506{
Amaury Forgeot d'Arc0a589c92010-05-15 20:35:12 +00006507 PyObject *result;
Larry Hastings2f936352014-08-05 14:04:04 +10006508 DWORD sig = (DWORD)signal;
6509 DWORD err;
Victor Stinner8c62be82010-05-06 00:08:46 +00006510 HANDLE handle;
Brian Curtineb24d742010-04-12 17:16:38 +00006511
Victor Stinner8c62be82010-05-06 00:08:46 +00006512 /* Console processes which share a common console can be sent CTRL+C or
6513 CTRL+BREAK events, provided they handle said events. */
6514 if (sig == CTRL_C_EVENT || sig == CTRL_BREAK_EVENT) {
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006515 if (GenerateConsoleCtrlEvent(sig, (DWORD)pid) == 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006516 err = GetLastError();
6517 PyErr_SetFromWindowsErr(err);
6518 }
6519 else
6520 Py_RETURN_NONE;
6521 }
Brian Curtineb24d742010-04-12 17:16:38 +00006522
Victor Stinner8c62be82010-05-06 00:08:46 +00006523 /* If the signal is outside of what GenerateConsoleCtrlEvent can use,
6524 attempt to open and terminate the process. */
Richard Oudkerkac0ad882013-06-05 23:29:30 +01006525 handle = OpenProcess(PROCESS_ALL_ACCESS, FALSE, (DWORD)pid);
Victor Stinner8c62be82010-05-06 00:08:46 +00006526 if (handle == NULL) {
6527 err = GetLastError();
6528 return PyErr_SetFromWindowsErr(err);
6529 }
Brian Curtineb24d742010-04-12 17:16:38 +00006530
Victor Stinner8c62be82010-05-06 00:08:46 +00006531 if (TerminateProcess(handle, sig) == 0) {
6532 err = GetLastError();
6533 result = PyErr_SetFromWindowsErr(err);
6534 } else {
6535 Py_INCREF(Py_None);
6536 result = Py_None;
6537 }
Brian Curtineb24d742010-04-12 17:16:38 +00006538
Victor Stinner8c62be82010-05-06 00:08:46 +00006539 CloseHandle(handle);
6540 return result;
Brian Curtineb24d742010-04-12 17:16:38 +00006541}
Larry Hastings2f936352014-08-05 14:04:04 +10006542#endif /* !MS_WINDOWS */
6543#endif /* HAVE_KILL */
6544
6545
6546#ifdef HAVE_KILLPG
6547/*[clinic input]
6548os.killpg
6549
6550 pgid: pid_t
6551 signal: int
6552 /
6553
6554Kill a process group with a signal.
6555[clinic start generated code]*/
6556
Larry Hastings2f936352014-08-05 14:04:04 +10006557static PyObject *
6558os_killpg_impl(PyModuleDef *module, pid_t pgid, int signal)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006559/*[clinic end generated code: output=3434a766ef945f93 input=38b5449eb8faec19]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006560{
6561 /* XXX some man pages make the `pgid` parameter an int, others
6562 a pid_t. Since getpgrp() returns a pid_t, we assume killpg should
6563 take the same type. Moreover, pid_t is always at least as wide as
6564 int (else compilation of this module fails), which is safe. */
6565 if (killpg(pgid, signal) == -1)
6566 return posix_error();
6567 Py_RETURN_NONE;
6568}
6569#endif /* HAVE_KILLPG */
6570
Brian Curtineb24d742010-04-12 17:16:38 +00006571
Guido van Rossumc0125471996-06-28 18:55:32 +00006572#ifdef HAVE_PLOCK
Guido van Rossumc0125471996-06-28 18:55:32 +00006573#ifdef HAVE_SYS_LOCK_H
6574#include <sys/lock.h>
6575#endif
6576
Larry Hastings2f936352014-08-05 14:04:04 +10006577/*[clinic input]
6578os.plock
6579 op: int
6580 /
6581
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +00006582Lock program segments into memory.");
Larry Hastings2f936352014-08-05 14:04:04 +10006583[clinic start generated code]*/
6584
Larry Hastings2f936352014-08-05 14:04:04 +10006585static PyObject *
6586os_plock_impl(PyModuleDef *module, int op)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006587/*[clinic end generated code: output=5cb851f81b914984 input=e6e5e348e1525f60]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006588{
Victor Stinner8c62be82010-05-06 00:08:46 +00006589 if (plock(op) == -1)
6590 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006591 Py_RETURN_NONE;
Guido van Rossumc0125471996-06-28 18:55:32 +00006592}
Larry Hastings2f936352014-08-05 14:04:04 +10006593#endif /* HAVE_PLOCK */
6594
Guido van Rossumc0125471996-06-28 18:55:32 +00006595
Guido van Rossumb6775db1994-08-01 11:34:53 +00006596#ifdef HAVE_SETUID
Larry Hastings2f936352014-08-05 14:04:04 +10006597/*[clinic input]
6598os.setuid
6599
6600 uid: uid_t
6601 /
6602
6603Set the current process's user id.
6604[clinic start generated code]*/
6605
Larry Hastings2f936352014-08-05 14:04:04 +10006606static PyObject *
6607os_setuid_impl(PyModuleDef *module, uid_t uid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006608/*[clinic end generated code: output=941ea9a8d1e5d565 input=c921a3285aa22256]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006609{
Victor Stinner8c62be82010-05-06 00:08:46 +00006610 if (setuid(uid) < 0)
6611 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006612 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006613}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006614#endif /* HAVE_SETUID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006615
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006616
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006617#ifdef HAVE_SETEUID
Larry Hastings2f936352014-08-05 14:04:04 +10006618/*[clinic input]
6619os.seteuid
6620
6621 euid: uid_t
6622 /
6623
6624Set the current process's effective user id.
6625[clinic start generated code]*/
6626
Larry Hastings2f936352014-08-05 14:04:04 +10006627static PyObject *
6628os_seteuid_impl(PyModuleDef *module, uid_t euid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006629/*[clinic end generated code: output=66f4f6823a648d6d input=ba93d927e4781aa9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006630{
6631 if (seteuid(euid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006632 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006633 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006634}
6635#endif /* HAVE_SETEUID */
6636
Larry Hastings2f936352014-08-05 14:04:04 +10006637
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006638#ifdef HAVE_SETEGID
Larry Hastings2f936352014-08-05 14:04:04 +10006639/*[clinic input]
6640os.setegid
6641
6642 egid: gid_t
6643 /
6644
6645Set the current process's effective group id.
6646[clinic start generated code]*/
6647
Larry Hastings2f936352014-08-05 14:04:04 +10006648static PyObject *
6649os_setegid_impl(PyModuleDef *module, gid_t egid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006650/*[clinic end generated code: output=ca094a69a081a60f input=4080526d0ccd6ce3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006651{
6652 if (setegid(egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006653 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006654 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006655}
6656#endif /* HAVE_SETEGID */
6657
Larry Hastings2f936352014-08-05 14:04:04 +10006658
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006659#ifdef HAVE_SETREUID
Larry Hastings2f936352014-08-05 14:04:04 +10006660/*[clinic input]
6661os.setreuid
6662
6663 ruid: uid_t
6664 euid: uid_t
6665 /
6666
6667Set the current process's real and effective user ids.
6668[clinic start generated code]*/
6669
Larry Hastings2f936352014-08-05 14:04:04 +10006670static PyObject *
6671os_setreuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006672/*[clinic end generated code: output=b2938c3e73d27ec7 input=0ca8978de663880c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006673{
Victor Stinner8c62be82010-05-06 00:08:46 +00006674 if (setreuid(ruid, euid) < 0) {
6675 return posix_error();
6676 } else {
6677 Py_INCREF(Py_None);
6678 return Py_None;
6679 }
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006680}
6681#endif /* HAVE_SETREUID */
6682
Larry Hastings2f936352014-08-05 14:04:04 +10006683
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006684#ifdef HAVE_SETREGID
Larry Hastings2f936352014-08-05 14:04:04 +10006685/*[clinic input]
6686os.setregid
6687
6688 rgid: gid_t
6689 egid: gid_t
6690 /
6691
6692Set the current process's real and effective group ids.
6693[clinic start generated code]*/
6694
Larry Hastings2f936352014-08-05 14:04:04 +10006695static PyObject *
6696os_setregid_impl(PyModuleDef *module, gid_t rgid, gid_t egid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006697/*[clinic end generated code: output=db18f1839ababe3d input=c59499f72846db78]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006698{
6699 if (setregid(rgid, egid) < 0)
Victor Stinner8c62be82010-05-06 00:08:46 +00006700 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006701 Py_RETURN_NONE;
Andrew M. Kuchling8d2f2b2d2000-07-13 01:26:58 +00006702}
6703#endif /* HAVE_SETREGID */
6704
Larry Hastings2f936352014-08-05 14:04:04 +10006705
Guido van Rossumb6775db1994-08-01 11:34:53 +00006706#ifdef HAVE_SETGID
Larry Hastings2f936352014-08-05 14:04:04 +10006707/*[clinic input]
6708os.setgid
6709 gid: gid_t
6710 /
6711
6712Set the current process's group id.
6713[clinic start generated code]*/
6714
Larry Hastings2f936352014-08-05 14:04:04 +10006715static PyObject *
6716os_setgid_impl(PyModuleDef *module, gid_t gid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006717/*[clinic end generated code: output=756cb42c6abd9d87 input=27d30c4059045dc6]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006718{
Victor Stinner8c62be82010-05-06 00:08:46 +00006719 if (setgid(gid) < 0)
6720 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10006721 Py_RETURN_NONE;
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006722}
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00006723#endif /* HAVE_SETGID */
Guido van Rossuma3d78fb1993-11-10 09:23:53 +00006724
Larry Hastings2f936352014-08-05 14:04:04 +10006725
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006726#ifdef HAVE_SETGROUPS
Larry Hastings2f936352014-08-05 14:04:04 +10006727/*[clinic input]
6728os.setgroups
6729
6730 groups: object
6731 /
6732
6733Set the groups of the current process to list.
6734[clinic start generated code]*/
6735
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006736static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10006737os_setgroups(PyModuleDef *module, PyObject *groups)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006738/*[clinic end generated code: output=7945c2e3cc817c58 input=fa742ca3daf85a7e]*/
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006739{
Victor Stinner8c62be82010-05-06 00:08:46 +00006740 int i, len;
6741 gid_t grouplist[MAX_GROUPS];
Tim Peters5aa91602002-01-30 05:46:57 +00006742
Victor Stinner8c62be82010-05-06 00:08:46 +00006743 if (!PySequence_Check(groups)) {
6744 PyErr_SetString(PyExc_TypeError, "setgroups argument must be a sequence");
6745 return NULL;
6746 }
6747 len = PySequence_Size(groups);
6748 if (len > MAX_GROUPS) {
6749 PyErr_SetString(PyExc_ValueError, "too many groups");
6750 return NULL;
6751 }
6752 for(i = 0; i < len; i++) {
6753 PyObject *elem;
6754 elem = PySequence_GetItem(groups, i);
6755 if (!elem)
6756 return NULL;
6757 if (!PyLong_Check(elem)) {
6758 PyErr_SetString(PyExc_TypeError,
6759 "groups must be integers");
6760 Py_DECREF(elem);
6761 return NULL;
6762 } else {
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006763 if (!_Py_Gid_Converter(elem, &grouplist[i])) {
Victor Stinner8c62be82010-05-06 00:08:46 +00006764 Py_DECREF(elem);
6765 return NULL;
6766 }
6767 }
6768 Py_DECREF(elem);
6769 }
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006770
Victor Stinner8c62be82010-05-06 00:08:46 +00006771 if (setgroups(len, grouplist) < 0)
6772 return posix_error();
6773 Py_INCREF(Py_None);
6774 return Py_None;
Martin v. Löwis61c5edf2001-10-18 04:06:00 +00006775}
6776#endif /* HAVE_SETGROUPS */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00006777
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006778#if defined(HAVE_WAIT3) || defined(HAVE_WAIT4)
6779static PyObject *
Victor Stinner4195b5c2012-02-08 23:03:19 +01006780wait_helper(pid_t pid, int status, struct rusage *ru)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006781{
Victor Stinner8c62be82010-05-06 00:08:46 +00006782 PyObject *result;
6783 static PyObject *struct_rusage;
Martin v. Löwisbd928fe2011-10-14 10:20:37 +02006784 _Py_IDENTIFIER(struct_rusage);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006785
Victor Stinner8c62be82010-05-06 00:08:46 +00006786 if (pid == -1)
6787 return posix_error();
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006788
Victor Stinner8c62be82010-05-06 00:08:46 +00006789 if (struct_rusage == NULL) {
6790 PyObject *m = PyImport_ImportModuleNoBlock("resource");
6791 if (m == NULL)
6792 return NULL;
Martin v. Löwis1ee1b6f2011-10-10 18:11:30 +02006793 struct_rusage = _PyObject_GetAttrId(m, &PyId_struct_rusage);
Victor Stinner8c62be82010-05-06 00:08:46 +00006794 Py_DECREF(m);
6795 if (struct_rusage == NULL)
6796 return NULL;
6797 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006798
Victor Stinner8c62be82010-05-06 00:08:46 +00006799 /* XXX(nnorwitz): Copied (w/mods) from resource.c, there should be only one. */
6800 result = PyStructSequence_New((PyTypeObject*) struct_rusage);
6801 if (!result)
6802 return NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006803
6804#ifndef doubletime
6805#define doubletime(TV) ((double)(TV).tv_sec + (TV).tv_usec * 0.000001)
6806#endif
6807
Victor Stinner8c62be82010-05-06 00:08:46 +00006808 PyStructSequence_SET_ITEM(result, 0,
Victor Stinner4195b5c2012-02-08 23:03:19 +01006809 PyFloat_FromDouble(doubletime(ru->ru_utime)));
Victor Stinner8c62be82010-05-06 00:08:46 +00006810 PyStructSequence_SET_ITEM(result, 1,
Victor Stinner4195b5c2012-02-08 23:03:19 +01006811 PyFloat_FromDouble(doubletime(ru->ru_stime)));
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006812#define SET_INT(result, index, value)\
Victor Stinner8c62be82010-05-06 00:08:46 +00006813 PyStructSequence_SET_ITEM(result, index, PyLong_FromLong(value))
6814 SET_INT(result, 2, ru->ru_maxrss);
6815 SET_INT(result, 3, ru->ru_ixrss);
6816 SET_INT(result, 4, ru->ru_idrss);
6817 SET_INT(result, 5, ru->ru_isrss);
6818 SET_INT(result, 6, ru->ru_minflt);
6819 SET_INT(result, 7, ru->ru_majflt);
6820 SET_INT(result, 8, ru->ru_nswap);
6821 SET_INT(result, 9, ru->ru_inblock);
6822 SET_INT(result, 10, ru->ru_oublock);
6823 SET_INT(result, 11, ru->ru_msgsnd);
6824 SET_INT(result, 12, ru->ru_msgrcv);
6825 SET_INT(result, 13, ru->ru_nsignals);
6826 SET_INT(result, 14, ru->ru_nvcsw);
6827 SET_INT(result, 15, ru->ru_nivcsw);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006828#undef SET_INT
6829
Victor Stinner8c62be82010-05-06 00:08:46 +00006830 if (PyErr_Occurred()) {
6831 Py_DECREF(result);
6832 return NULL;
6833 }
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006834
Victor Stinner8c62be82010-05-06 00:08:46 +00006835 return Py_BuildValue("NiN", PyLong_FromPid(pid), status, result);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006836}
6837#endif /* HAVE_WAIT3 || HAVE_WAIT4 */
6838
Larry Hastings2f936352014-08-05 14:04:04 +10006839
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006840#ifdef HAVE_WAIT3
Larry Hastings2f936352014-08-05 14:04:04 +10006841/*[clinic input]
6842os.wait3
6843
6844 options: int
6845Wait for completion of a child process.
6846
6847Returns a tuple of information about the child process:
6848 (pid, status, rusage)
6849[clinic start generated code]*/
6850
Larry Hastings2f936352014-08-05 14:04:04 +10006851static PyObject *
6852os_wait3_impl(PyModuleDef *module, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006853/*[clinic end generated code: output=e18af4924dc54945 input=8ac4c56956b61710]*/
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006854{
Victor Stinner8c62be82010-05-06 00:08:46 +00006855 pid_t pid;
Victor Stinner8c62be82010-05-06 00:08:46 +00006856 struct rusage ru;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006857 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006858 WAIT_TYPE status;
6859 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006860
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006861 do {
6862 Py_BEGIN_ALLOW_THREADS
6863 pid = wait3(&status, options, &ru);
6864 Py_END_ALLOW_THREADS
6865 } while (pid < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6866 if (pid < 0)
6867 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006868
Victor Stinner4195b5c2012-02-08 23:03:19 +01006869 return wait_helper(pid, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006870}
6871#endif /* HAVE_WAIT3 */
6872
Larry Hastings2f936352014-08-05 14:04:04 +10006873
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006874#ifdef HAVE_WAIT4
Larry Hastings2f936352014-08-05 14:04:04 +10006875/*[clinic input]
6876
6877os.wait4
6878
6879 pid: pid_t
6880 options: int
6881
6882Wait for completion of a specific child process.
6883
6884Returns a tuple of information about the child process:
6885 (pid, status, rusage)
6886[clinic start generated code]*/
6887
Larry Hastings2f936352014-08-05 14:04:04 +10006888static PyObject *
6889os_wait4_impl(PyModuleDef *module, pid_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006890/*[clinic end generated code: output=714f19e6ff01e099 input=d11deed0750600ba]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006891{
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006892 pid_t res;
Victor Stinner8c62be82010-05-06 00:08:46 +00006893 struct rusage ru;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006894 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006895 WAIT_TYPE status;
6896 WAIT_STATUS_INT(status) = 0;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006897
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006898 do {
6899 Py_BEGIN_ALLOW_THREADS
6900 res = wait4(pid, &status, options, &ru);
6901 Py_END_ALLOW_THREADS
6902 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6903 if (res < 0)
6904 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006905
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006906 return wait_helper(res, WAIT_STATUS_INT(status), &ru);
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00006907}
6908#endif /* HAVE_WAIT4 */
6909
Larry Hastings2f936352014-08-05 14:04:04 +10006910
Ross Lagerwall7807c352011-03-17 20:20:30 +02006911#if defined(HAVE_WAITID) && !defined(__APPLE__)
Larry Hastings2f936352014-08-05 14:04:04 +10006912/*[clinic input]
6913os.waitid
6914
6915 idtype: idtype_t
6916 Must be one of be P_PID, P_PGID or P_ALL.
6917 id: id_t
6918 The id to wait on.
6919 options: int
6920 Constructed from the ORing of one or more of WEXITED, WSTOPPED
6921 or WCONTINUED and additionally may be ORed with WNOHANG or WNOWAIT.
6922 /
6923
6924Returns the result of waiting for a process or processes.
6925
6926Returns either waitid_result or None if WNOHANG is specified and there are
6927no children in a waitable state.
6928[clinic start generated code]*/
6929
Larry Hastings2f936352014-08-05 14:04:04 +10006930static PyObject *
6931os_waitid_impl(PyModuleDef *module, idtype_t idtype, id_t id, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006932/*[clinic end generated code: output=5c0192750e22fa2e input=d8e7f76e052b7920]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006933{
6934 PyObject *result;
6935 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006936 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006937 siginfo_t si;
6938 si.si_pid = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10006939
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006940 do {
6941 Py_BEGIN_ALLOW_THREADS
6942 res = waitid(idtype, id, &si, options);
6943 Py_END_ALLOW_THREADS
6944 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6945 if (res < 0)
6946 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02006947
6948 if (si.si_pid == 0)
6949 Py_RETURN_NONE;
6950
6951 result = PyStructSequence_New(&WaitidResultType);
6952 if (!result)
6953 return NULL;
6954
6955 PyStructSequence_SET_ITEM(result, 0, PyLong_FromPid(si.si_pid));
Serhiy Storchaka7cf55992013-02-10 21:56:49 +02006956 PyStructSequence_SET_ITEM(result, 1, _PyLong_FromUid(si.si_uid));
Ross Lagerwall7807c352011-03-17 20:20:30 +02006957 PyStructSequence_SET_ITEM(result, 2, PyLong_FromLong((long)(si.si_signo)));
6958 PyStructSequence_SET_ITEM(result, 3, PyLong_FromLong((long)(si.si_status)));
6959 PyStructSequence_SET_ITEM(result, 4, PyLong_FromLong((long)(si.si_code)));
6960 if (PyErr_Occurred()) {
6961 Py_DECREF(result);
6962 return NULL;
6963 }
6964
6965 return result;
6966}
Larry Hastings2f936352014-08-05 14:04:04 +10006967#endif /* defined(HAVE_WAITID) && !defined(__APPLE__) */
Ross Lagerwall7807c352011-03-17 20:20:30 +02006968
Larry Hastings2f936352014-08-05 14:04:04 +10006969
6970#if defined(HAVE_WAITPID)
6971/*[clinic input]
6972os.waitpid
6973 pid: pid_t
6974 options: int
6975 /
6976
6977Wait for completion of a given child process.
6978
6979Returns a tuple of information regarding the child process:
6980 (pid, status)
6981
6982The options argument is ignored on Windows.
6983[clinic start generated code]*/
6984
Larry Hastings2f936352014-08-05 14:04:04 +10006985static PyObject *
6986os_waitpid_impl(PyModuleDef *module, pid_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03006987/*[clinic end generated code: output=5e3593353d54b15b input=0bf1666b8758fda3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10006988{
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006989 pid_t res;
6990 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00006991 WAIT_TYPE status;
6992 WAIT_STATUS_INT(status) = 0;
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00006993
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00006994 do {
6995 Py_BEGIN_ALLOW_THREADS
6996 res = waitpid(pid, &status, options);
6997 Py_END_ALLOW_THREADS
6998 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
6999 if (res < 0)
7000 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00007001
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007002 return Py_BuildValue("Ni", PyLong_FromPid(res), WAIT_STATUS_INT(status));
Guido van Rossum21803b81992-08-09 12:55:27 +00007003}
Tim Petersab034fa2002-02-01 11:27:43 +00007004#elif defined(HAVE_CWAIT)
Tim Petersab034fa2002-02-01 11:27:43 +00007005/* MS C has a variant of waitpid() that's usable for most purposes. */
Larry Hastings2f936352014-08-05 14:04:04 +10007006/*[clinic input]
7007os.waitpid
7008 pid: Py_intptr_t
7009 options: int
7010 /
7011
7012Wait for completion of a given process.
7013
7014Returns a tuple of information regarding the process:
7015 (pid, status << 8)
7016
7017The options argument is ignored on Windows.
7018[clinic start generated code]*/
7019
Larry Hastings2f936352014-08-05 14:04:04 +10007020static PyObject *
7021os_waitpid_impl(PyModuleDef *module, Py_intptr_t pid, int options)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007022/*[clinic end generated code: output=fc1d520db019625f input=444c8f51cca5b862]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007023{
7024 int status;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007025 Py_intptr_t res;
7026 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10007027
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007028 do {
7029 Py_BEGIN_ALLOW_THREADS
7030 res = _cwait(&status, pid, options);
7031 Py_END_ALLOW_THREADS
7032 } while (res < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Victor Stinnerd3ffd322015-09-15 10:11:03 +02007033 if (res < 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007034 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00007035
Victor Stinner8c62be82010-05-06 00:08:46 +00007036 /* shift the status left a byte so this is more like the POSIX waitpid */
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007037 return Py_BuildValue(_Py_PARSE_INTPTR "i", res, status << 8);
Tim Petersab034fa2002-02-01 11:27:43 +00007038}
Larry Hastings2f936352014-08-05 14:04:04 +10007039#endif
7040
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007041
Guido van Rossumad0ee831995-03-01 10:34:45 +00007042#ifdef HAVE_WAIT
Larry Hastings2f936352014-08-05 14:04:04 +10007043/*[clinic input]
7044os.wait
7045
7046Wait for completion of a child process.
7047
7048Returns a tuple of information about the child process:
7049 (pid, status)
7050[clinic start generated code]*/
7051
Larry Hastings2f936352014-08-05 14:04:04 +10007052static PyObject *
7053os_wait_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007054/*[clinic end generated code: output=4a7f4978393e0654 input=03b0182d4a4700ce]*/
Guido van Rossum21803b81992-08-09 12:55:27 +00007055{
Victor Stinner8c62be82010-05-06 00:08:46 +00007056 pid_t pid;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007057 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00007058 WAIT_TYPE status;
7059 WAIT_STATUS_INT(status) = 0;
Neal Norwitze241ce82003-02-17 18:17:05 +00007060
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007061 do {
7062 Py_BEGIN_ALLOW_THREADS
7063 pid = wait(&status);
7064 Py_END_ALLOW_THREADS
7065 } while (pid < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
7066 if (pid < 0)
7067 return (!async_err) ? posix_error() : NULL;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +00007068
Victor Stinner8c62be82010-05-06 00:08:46 +00007069 return Py_BuildValue("Ni", PyLong_FromPid(pid), WAIT_STATUS_INT(status));
Guido van Rossum85e3b011991-06-03 12:42:10 +00007070}
Larry Hastings2f936352014-08-05 14:04:04 +10007071#endif /* HAVE_WAIT */
Guido van Rossum85e3b011991-06-03 12:42:10 +00007072
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007073
Larry Hastings9cf065c2012-06-22 16:30:09 -07007074#if defined(HAVE_READLINK) || defined(MS_WINDOWS)
7075PyDoc_STRVAR(readlink__doc__,
7076"readlink(path, *, dir_fd=None) -> path\n\n\
7077Return a string representing the path to which the symbolic link points.\n\
7078\n\
7079If dir_fd is not None, it should be a file descriptor open to a directory,\n\
7080 and path should be relative; path will then be relative to that directory.\n\
7081dir_fd may not be implemented on your platform.\n\
7082 If it is unavailable, using it will raise a NotImplementedError.");
Mark Hammondc2e85bd2002-10-03 05:10:39 +00007083#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007084
Guido van Rossumb6775db1994-08-01 11:34:53 +00007085#ifdef HAVE_READLINK
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007086
Larry Hastings2f936352014-08-05 14:04:04 +10007087/* AC 3.5: merge win32 and not together */
Barry Warsaw53699e91996-12-10 23:23:01 +00007088static PyObject *
Larry Hastings9cf065c2012-06-22 16:30:09 -07007089posix_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007090{
Larry Hastings9cf065c2012-06-22 16:30:09 -07007091 path_t path;
7092 int dir_fd = DEFAULT_DIR_FD;
7093 char buffer[MAXPATHLEN];
7094 ssize_t length;
7095 PyObject *return_value = NULL;
7096 static char *keywords[] = {"path", "dir_fd", NULL};
Thomas Wouters89f507f2006-12-13 04:49:30 +00007097
Larry Hastings9cf065c2012-06-22 16:30:09 -07007098 memset(&path, 0, sizeof(path));
Victor Stinner292c8352012-10-30 02:17:38 +01007099 path.function_name = "readlink";
Larry Hastings9cf065c2012-06-22 16:30:09 -07007100 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "O&|$O&:readlink", keywords,
7101 path_converter, &path,
Larry Hastings2f936352014-08-05 14:04:04 +10007102 READLINKAT_DIR_FD_CONVERTER, &dir_fd))
Victor Stinner8c62be82010-05-06 00:08:46 +00007103 return NULL;
Thomas Wouters89f507f2006-12-13 04:49:30 +00007104
Victor Stinner8c62be82010-05-06 00:08:46 +00007105 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07007106#ifdef HAVE_READLINKAT
7107 if (dir_fd != DEFAULT_DIR_FD)
7108 length = readlinkat(dir_fd, path.narrow, buffer, sizeof(buffer));
Victor Stinnera45598a2010-05-14 16:35:39 +00007109 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007110#endif
7111 length = readlink(path.narrow, buffer, sizeof(buffer));
7112 Py_END_ALLOW_THREADS
7113
7114 if (length < 0) {
Victor Stinner292c8352012-10-30 02:17:38 +01007115 return_value = path_error(&path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007116 goto exit;
7117 }
7118
7119 if (PyUnicode_Check(path.object))
7120 return_value = PyUnicode_DecodeFSDefaultAndSize(buffer, length);
7121 else
7122 return_value = PyBytes_FromStringAndSize(buffer, length);
7123exit:
7124 path_cleanup(&path);
7125 return return_value;
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007126}
Larry Hastings9cf065c2012-06-22 16:30:09 -07007127
Guido van Rossumb6775db1994-08-01 11:34:53 +00007128#endif /* HAVE_READLINK */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +00007129
Larry Hastings2f936352014-08-05 14:04:04 +10007130#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
7131
7132static PyObject *
7133win_readlink(PyObject *self, PyObject *args, PyObject *kwargs)
7134{
7135 wchar_t *path;
7136 DWORD n_bytes_returned;
7137 DWORD io_result;
7138 PyObject *po, *result;
7139 int dir_fd;
7140 HANDLE reparse_point_handle;
7141
7142 char target_buffer[MAXIMUM_REPARSE_DATA_BUFFER_SIZE];
7143 REPARSE_DATA_BUFFER *rdb = (REPARSE_DATA_BUFFER *)target_buffer;
7144 wchar_t *print_name;
7145
7146 static char *keywords[] = {"path", "dir_fd", NULL};
7147
7148 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "U|$O&:readlink", keywords,
7149 &po,
7150 dir_fd_unavailable, &dir_fd
7151 ))
7152 return NULL;
7153
7154 path = PyUnicode_AsUnicode(po);
7155 if (path == NULL)
7156 return NULL;
7157
7158 /* First get a handle to the reparse point */
7159 Py_BEGIN_ALLOW_THREADS
7160 reparse_point_handle = CreateFileW(
7161 path,
7162 0,
7163 0,
7164 0,
7165 OPEN_EXISTING,
7166 FILE_FLAG_OPEN_REPARSE_POINT|FILE_FLAG_BACKUP_SEMANTICS,
7167 0);
7168 Py_END_ALLOW_THREADS
7169
7170 if (reparse_point_handle==INVALID_HANDLE_VALUE)
7171 return win32_error_object("readlink", po);
7172
7173 Py_BEGIN_ALLOW_THREADS
7174 /* New call DeviceIoControl to read the reparse point */
7175 io_result = DeviceIoControl(
7176 reparse_point_handle,
7177 FSCTL_GET_REPARSE_POINT,
7178 0, 0, /* in buffer */
7179 target_buffer, sizeof(target_buffer),
7180 &n_bytes_returned,
7181 0 /* we're not using OVERLAPPED_IO */
7182 );
7183 CloseHandle(reparse_point_handle);
7184 Py_END_ALLOW_THREADS
7185
7186 if (io_result==0)
7187 return win32_error_object("readlink", po);
7188
7189 if (rdb->ReparseTag != IO_REPARSE_TAG_SYMLINK)
7190 {
7191 PyErr_SetString(PyExc_ValueError,
7192 "not a symbolic link");
7193 return NULL;
7194 }
7195 print_name = rdb->SymbolicLinkReparseBuffer.PathBuffer +
7196 rdb->SymbolicLinkReparseBuffer.PrintNameOffset;
7197
7198 result = PyUnicode_FromWideChar(print_name,
7199 rdb->SymbolicLinkReparseBuffer.PrintNameLength/2);
7200 return result;
7201}
7202
7203#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
7204
7205
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007206
Larry Hastings9cf065c2012-06-22 16:30:09 -07007207#ifdef HAVE_SYMLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -07007208
7209#if defined(MS_WINDOWS)
7210
7211/* Grab CreateSymbolicLinkW dynamically from kernel32 */
7212static DWORD (CALLBACK *Py_CreateSymbolicLinkW)(LPWSTR, LPWSTR, DWORD) = NULL;
7213static DWORD (CALLBACK *Py_CreateSymbolicLinkA)(LPSTR, LPSTR, DWORD) = NULL;
Victor Stinner31b3b922013-06-05 01:49:17 +02007214
Larry Hastings9cf065c2012-06-22 16:30:09 -07007215static int
Victor Stinner31b3b922013-06-05 01:49:17 +02007216check_CreateSymbolicLink(void)
Larry Hastings9cf065c2012-06-22 16:30:09 -07007217{
7218 HINSTANCE hKernel32;
7219 /* only recheck */
7220 if (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA)
7221 return 1;
7222 hKernel32 = GetModuleHandleW(L"KERNEL32");
7223 *(FARPROC*)&Py_CreateSymbolicLinkW = GetProcAddress(hKernel32,
7224 "CreateSymbolicLinkW");
7225 *(FARPROC*)&Py_CreateSymbolicLinkA = GetProcAddress(hKernel32,
7226 "CreateSymbolicLinkA");
7227 return (Py_CreateSymbolicLinkW && Py_CreateSymbolicLinkA);
7228}
7229
Victor Stinner31b3b922013-06-05 01:49:17 +02007230/* Remove the last portion of the path */
7231static void
7232_dirnameW(WCHAR *path)
7233{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007234 WCHAR *ptr;
7235
7236 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +02007237 for(ptr = path + wcslen(path); ptr != path; ptr--) {
Victor Stinner072318b2013-06-05 02:07:46 +02007238 if (*ptr == L'\\' || *ptr == L'/')
Jason R. Coombs3a092862013-05-27 23:21:28 -04007239 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007240 }
7241 *ptr = 0;
7242}
7243
Victor Stinner31b3b922013-06-05 01:49:17 +02007244/* Remove the last portion of the path */
7245static void
7246_dirnameA(char *path)
7247{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007248 char *ptr;
7249
7250 /* walk the path from the end until a backslash is encountered */
Victor Stinner31b3b922013-06-05 01:49:17 +02007251 for(ptr = path + strlen(path); ptr != path; ptr--) {
7252 if (*ptr == '\\' || *ptr == '/')
Jason R. Coombs3a092862013-05-27 23:21:28 -04007253 break;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007254 }
7255 *ptr = 0;
7256}
7257
Victor Stinner31b3b922013-06-05 01:49:17 +02007258/* Is this path absolute? */
7259static int
7260_is_absW(const WCHAR *path)
7261{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007262 return path[0] == L'\\' || path[0] == L'/' || path[1] == L':';
7263
7264}
7265
Victor Stinner31b3b922013-06-05 01:49:17 +02007266/* Is this path absolute? */
7267static int
7268_is_absA(const char *path)
7269{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007270 return path[0] == '\\' || path[0] == '/' || path[1] == ':';
7271
7272}
7273
Victor Stinner31b3b922013-06-05 01:49:17 +02007274/* join root and rest with a backslash */
7275static void
7276_joinW(WCHAR *dest_path, const WCHAR *root, const WCHAR *rest)
7277{
Victor Stinnere7e7eba2013-06-05 00:35:54 +02007278 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007279
Victor Stinner31b3b922013-06-05 01:49:17 +02007280 if (_is_absW(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007281 wcscpy(dest_path, rest);
7282 return;
7283 }
7284
7285 root_len = wcslen(root);
7286
7287 wcscpy(dest_path, root);
7288 if(root_len) {
Victor Stinner31b3b922013-06-05 01:49:17 +02007289 dest_path[root_len] = L'\\';
7290 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007291 }
7292 wcscpy(dest_path+root_len, rest);
7293}
7294
Victor Stinner31b3b922013-06-05 01:49:17 +02007295/* join root and rest with a backslash */
7296static void
7297_joinA(char *dest_path, const char *root, const char *rest)
7298{
Victor Stinnere7e7eba2013-06-05 00:35:54 +02007299 size_t root_len;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007300
Victor Stinner31b3b922013-06-05 01:49:17 +02007301 if (_is_absA(rest)) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007302 strcpy(dest_path, rest);
7303 return;
7304 }
7305
7306 root_len = strlen(root);
7307
7308 strcpy(dest_path, root);
7309 if(root_len) {
7310 dest_path[root_len] = '\\';
Victor Stinner31b3b922013-06-05 01:49:17 +02007311 root_len++;
Jason R. Coombs3a092862013-05-27 23:21:28 -04007312 }
7313 strcpy(dest_path+root_len, rest);
7314}
7315
Victor Stinner31b3b922013-06-05 01:49:17 +02007316/* Return True if the path at src relative to dest is a directory */
7317static int
7318_check_dirW(WCHAR *src, WCHAR *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -04007319{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007320 WIN32_FILE_ATTRIBUTE_DATA src_info;
7321 WCHAR dest_parent[MAX_PATH];
7322 WCHAR src_resolved[MAX_PATH] = L"";
7323
7324 /* dest_parent = os.path.dirname(dest) */
7325 wcscpy(dest_parent, dest);
7326 _dirnameW(dest_parent);
7327 /* src_resolved = os.path.join(dest_parent, src) */
7328 _joinW(src_resolved, dest_parent, src);
7329 return (
7330 GetFileAttributesExW(src_resolved, GetFileExInfoStandard, &src_info)
7331 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
7332 );
7333}
7334
Victor Stinner31b3b922013-06-05 01:49:17 +02007335/* Return True if the path at src relative to dest is a directory */
7336static int
Serhiy Storchakaef1585e2015-12-25 20:01:53 +02007337_check_dirA(const char *src, char *dest)
Jason R. Coombs3a092862013-05-27 23:21:28 -04007338{
Jason R. Coombs3a092862013-05-27 23:21:28 -04007339 WIN32_FILE_ATTRIBUTE_DATA src_info;
7340 char dest_parent[MAX_PATH];
7341 char src_resolved[MAX_PATH] = "";
7342
7343 /* dest_parent = os.path.dirname(dest) */
7344 strcpy(dest_parent, dest);
Victor Stinner5a436762013-06-05 00:37:12 +02007345 _dirnameA(dest_parent);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007346 /* src_resolved = os.path.join(dest_parent, src) */
Victor Stinner5a436762013-06-05 00:37:12 +02007347 _joinA(src_resolved, dest_parent, src);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007348 return (
7349 GetFileAttributesExA(src_resolved, GetFileExInfoStandard, &src_info)
7350 && src_info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY
7351 );
7352}
Larry Hastings9cf065c2012-06-22 16:30:09 -07007353#endif
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007354
Larry Hastings2f936352014-08-05 14:04:04 +10007355
7356/*[clinic input]
7357os.symlink
7358 src: path_t
7359 dst: path_t
7360 target_is_directory: bool = False
7361 *
7362 dir_fd: dir_fd(requires='symlinkat')=None
7363
7364# "symlink(src, dst, target_is_directory=False, *, dir_fd=None)\n\n\
7365
7366Create a symbolic link pointing to src named dst.
7367
7368target_is_directory is required on Windows if the target is to be
7369 interpreted as a directory. (On Windows, symlink requires
7370 Windows 6.0 or greater, and raises a NotImplementedError otherwise.)
7371 target_is_directory is ignored on non-Windows platforms.
7372
7373If dir_fd is not None, it should be a file descriptor open to a directory,
7374 and path should be relative; path will then be relative to that directory.
7375dir_fd may not be implemented on your platform.
7376 If it is unavailable, using it will raise a NotImplementedError.
7377
7378[clinic start generated code]*/
7379
Larry Hastings2f936352014-08-05 14:04:04 +10007380static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04007381os_symlink_impl(PyModuleDef *module, path_t *src, path_t *dst,
7382 int target_is_directory, int dir_fd)
7383/*[clinic end generated code: output=a01b4bcf32403ccd input=e820ec4472547bc3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007384{
Larry Hastings9cf065c2012-06-22 16:30:09 -07007385#ifdef MS_WINDOWS
7386 DWORD result;
7387#else
7388 int result;
7389#endif
7390
Larry Hastings9cf065c2012-06-22 16:30:09 -07007391#ifdef MS_WINDOWS
7392 if (!check_CreateSymbolicLink()) {
7393 PyErr_SetString(PyExc_NotImplementedError,
7394 "CreateSymbolicLink functions not found");
Larry Hastings2f936352014-08-05 14:04:04 +10007395 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03007396 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007397 if (!win32_can_symlink) {
7398 PyErr_SetString(PyExc_OSError, "symbolic link privilege not held");
Larry Hastings2f936352014-08-05 14:04:04 +10007399 return NULL;
Petri Lehtinen5445a8c2012-10-23 16:12:14 +03007400 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007401#endif
7402
Larry Hastings2f936352014-08-05 14:04:04 +10007403 if ((src->narrow && dst->wide) || (src->wide && dst->narrow)) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07007404 PyErr_SetString(PyExc_ValueError,
7405 "symlink: src and dst must be the same type");
Larry Hastings2f936352014-08-05 14:04:04 +10007406 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07007407 }
7408
7409#ifdef MS_WINDOWS
Jason R. Coombs3a092862013-05-27 23:21:28 -04007410
Larry Hastings9cf065c2012-06-22 16:30:09 -07007411 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007412 if (dst->wide) {
Jason R. Coombs3a092862013-05-27 23:21:28 -04007413 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +10007414 target_is_directory |= _check_dirW(src->wide, dst->wide);
7415 result = Py_CreateSymbolicLinkW(dst->wide, src->wide,
Larry Hastings9cf065c2012-06-22 16:30:09 -07007416 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007417 }
7418 else {
7419 /* if src is a directory, ensure target_is_directory==1 */
Larry Hastings2f936352014-08-05 14:04:04 +10007420 target_is_directory |= _check_dirA(src->narrow, dst->narrow);
7421 result = Py_CreateSymbolicLinkA(dst->narrow, src->narrow,
Larry Hastings9cf065c2012-06-22 16:30:09 -07007422 target_is_directory);
Jason R. Coombs3a092862013-05-27 23:21:28 -04007423 }
Larry Hastings9cf065c2012-06-22 16:30:09 -07007424 Py_END_ALLOW_THREADS
7425
Larry Hastings2f936352014-08-05 14:04:04 +10007426 if (!result)
7427 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007428
7429#else
7430
7431 Py_BEGIN_ALLOW_THREADS
7432#if HAVE_SYMLINKAT
7433 if (dir_fd != DEFAULT_DIR_FD)
Larry Hastings2f936352014-08-05 14:04:04 +10007434 result = symlinkat(src->narrow, dir_fd, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007435 else
7436#endif
Larry Hastings2f936352014-08-05 14:04:04 +10007437 result = symlink(src->narrow, dst->narrow);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007438 Py_END_ALLOW_THREADS
7439
Larry Hastings2f936352014-08-05 14:04:04 +10007440 if (result)
7441 return path_error2(src, dst);
Larry Hastings9cf065c2012-06-22 16:30:09 -07007442#endif
7443
Larry Hastings2f936352014-08-05 14:04:04 +10007444 Py_RETURN_NONE;
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00007445}
7446#endif /* HAVE_SYMLINK */
7447
Larry Hastings9cf065c2012-06-22 16:30:09 -07007448
Brian Curtind40e6f72010-07-08 21:39:08 +00007449
Guido van Rossumbfaf3d61997-12-29 20:02:27 +00007450
Larry Hastings605a62d2012-06-24 04:33:36 -07007451static PyStructSequence_Field times_result_fields[] = {
7452 {"user", "user time"},
7453 {"system", "system time"},
7454 {"children_user", "user time of children"},
7455 {"children_system", "system time of children"},
7456 {"elapsed", "elapsed time since an arbitrary point in the past"},
7457 {NULL}
7458};
7459
7460PyDoc_STRVAR(times_result__doc__,
7461"times_result: Result from os.times().\n\n\
7462This object may be accessed either as a tuple of\n\
7463 (user, system, children_user, children_system, elapsed),\n\
7464or via the attributes user, system, children_user, children_system,\n\
7465and elapsed.\n\
7466\n\
7467See os.times for more information.");
7468
7469static PyStructSequence_Desc times_result_desc = {
7470 "times_result", /* name */
7471 times_result__doc__, /* doc */
7472 times_result_fields,
7473 5
7474};
7475
7476static PyTypeObject TimesResultType;
7477
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007478#ifdef MS_WINDOWS
7479#define HAVE_TIMES /* mandatory, for the method table */
7480#endif
Larry Hastings605a62d2012-06-24 04:33:36 -07007481
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007482#ifdef HAVE_TIMES
Larry Hastings605a62d2012-06-24 04:33:36 -07007483
7484static PyObject *
7485build_times_result(double user, double system,
7486 double children_user, double children_system,
7487 double elapsed)
7488{
7489 PyObject *value = PyStructSequence_New(&TimesResultType);
7490 if (value == NULL)
7491 return NULL;
7492
7493#define SET(i, field) \
7494 { \
7495 PyObject *o = PyFloat_FromDouble(field); \
7496 if (!o) { \
7497 Py_DECREF(value); \
7498 return NULL; \
7499 } \
7500 PyStructSequence_SET_ITEM(value, i, o); \
7501 } \
7502
7503 SET(0, user);
7504 SET(1, system);
7505 SET(2, children_user);
7506 SET(3, children_system);
7507 SET(4, elapsed);
7508
7509#undef SET
7510
7511 return value;
7512}
7513
Larry Hastings605a62d2012-06-24 04:33:36 -07007514
Larry Hastings2f936352014-08-05 14:04:04 +10007515#ifndef MS_WINDOWS
7516#define NEED_TICKS_PER_SECOND
7517static long ticks_per_second = -1;
7518#endif /* MS_WINDOWS */
7519
7520/*[clinic input]
7521os.times
7522
7523Return a collection containing process timing information.
7524
7525The object returned behaves like a named tuple with these fields:
7526 (utime, stime, cutime, cstime, elapsed_time)
7527All fields are floating point numbers.
7528[clinic start generated code]*/
7529
Larry Hastings2f936352014-08-05 14:04:04 +10007530static PyObject *
7531os_times_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007532/*[clinic end generated code: output=df0a63ebe6e6f091 input=2bf9df3d6ab2e48b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007533#ifdef MS_WINDOWS
Guido van Rossum14ed0b21994-09-29 09:50:09 +00007534{
Victor Stinner8c62be82010-05-06 00:08:46 +00007535 FILETIME create, exit, kernel, user;
7536 HANDLE hProc;
7537 hProc = GetCurrentProcess();
7538 GetProcessTimes(hProc, &create, &exit, &kernel, &user);
7539 /* The fields of a FILETIME structure are the hi and lo part
7540 of a 64-bit value expressed in 100 nanosecond units.
7541 1e7 is one second in such units; 1e-7 the inverse.
7542 429.4967296 is 2**32 / 1e7 or 2**32 * 1e-7.
7543 */
Larry Hastings605a62d2012-06-24 04:33:36 -07007544 return build_times_result(
Victor Stinner8c62be82010-05-06 00:08:46 +00007545 (double)(user.dwHighDateTime*429.4967296 +
7546 user.dwLowDateTime*1e-7),
7547 (double)(kernel.dwHighDateTime*429.4967296 +
7548 kernel.dwLowDateTime*1e-7),
7549 (double)0,
7550 (double)0,
7551 (double)0);
Guido van Rossum14ed0b21994-09-29 09:50:09 +00007552}
Larry Hastings2f936352014-08-05 14:04:04 +10007553#else /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007554{
Larry Hastings2f936352014-08-05 14:04:04 +10007555
7556
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007557 struct tms t;
7558 clock_t c;
7559 errno = 0;
7560 c = times(&t);
7561 if (c == (clock_t) -1)
7562 return posix_error();
7563 return build_times_result(
7564 (double)t.tms_utime / ticks_per_second,
7565 (double)t.tms_stime / ticks_per_second,
7566 (double)t.tms_cutime / ticks_per_second,
7567 (double)t.tms_cstime / ticks_per_second,
7568 (double)c / ticks_per_second);
7569}
Larry Hastings2f936352014-08-05 14:04:04 +10007570#endif /* MS_WINDOWS */
Antoine Pitrouf3923e92012-07-24 21:23:53 +02007571#endif /* HAVE_TIMES */
7572
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007573
Martin v. Löwis49ee14d2003-11-10 06:35:36 +00007574#ifdef HAVE_GETSID
Larry Hastings2f936352014-08-05 14:04:04 +10007575/*[clinic input]
7576os.getsid
7577
7578 pid: pid_t
7579 /
7580
7581Call the system call getsid(pid) and return the result.
7582[clinic start generated code]*/
7583
Larry Hastings2f936352014-08-05 14:04:04 +10007584static PyObject *
7585os_getsid_impl(PyModuleDef *module, pid_t pid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007586/*[clinic end generated code: output=a074f80c0e6bfb38 input=eeb2b923a30ce04e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007587{
Victor Stinner8c62be82010-05-06 00:08:46 +00007588 int sid;
Victor Stinner8c62be82010-05-06 00:08:46 +00007589 sid = getsid(pid);
7590 if (sid < 0)
7591 return posix_error();
7592 return PyLong_FromLong((long)sid);
Martin v. Löwis49ee14d2003-11-10 06:35:36 +00007593}
7594#endif /* HAVE_GETSID */
7595
7596
Guido van Rossumb6775db1994-08-01 11:34:53 +00007597#ifdef HAVE_SETSID
Larry Hastings2f936352014-08-05 14:04:04 +10007598/*[clinic input]
7599os.setsid
7600
7601Call the system call setsid().
7602[clinic start generated code]*/
7603
Larry Hastings2f936352014-08-05 14:04:04 +10007604static PyObject *
7605os_setsid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007606/*[clinic end generated code: output=398fc152ae327330 input=5fff45858e2f0776]*/
Guido van Rossumc2670a01992-09-13 20:07:29 +00007607{
Victor Stinner8c62be82010-05-06 00:08:46 +00007608 if (setsid() < 0)
7609 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007610 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +00007611}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007612#endif /* HAVE_SETSID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00007613
Larry Hastings2f936352014-08-05 14:04:04 +10007614
Guido van Rossumb6775db1994-08-01 11:34:53 +00007615#ifdef HAVE_SETPGID
Larry Hastings2f936352014-08-05 14:04:04 +10007616/*[clinic input]
7617os.setpgid
7618
7619 pid: pid_t
7620 pgrp: pid_t
7621 /
7622
7623Call the system call setpgid(pid, pgrp).
7624[clinic start generated code]*/
7625
Larry Hastings2f936352014-08-05 14:04:04 +10007626static PyObject *
7627os_setpgid_impl(PyModuleDef *module, pid_t pid, pid_t pgrp)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007628/*[clinic end generated code: output=7079a8e932912841 input=fceb395eca572e1a]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007629{
Victor Stinner8c62be82010-05-06 00:08:46 +00007630 if (setpgid(pid, pgrp) < 0)
7631 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007632 Py_RETURN_NONE;
Guido van Rossumc2670a01992-09-13 20:07:29 +00007633}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007634#endif /* HAVE_SETPGID */
Guido van Rossumc2670a01992-09-13 20:07:29 +00007635
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007636
Guido van Rossumb6775db1994-08-01 11:34:53 +00007637#ifdef HAVE_TCGETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10007638/*[clinic input]
7639os.tcgetpgrp
7640
7641 fd: int
7642 /
7643
7644Return the process group associated with the terminal specified by fd.
7645[clinic start generated code]*/
7646
Larry Hastings2f936352014-08-05 14:04:04 +10007647static PyObject *
7648os_tcgetpgrp_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007649/*[clinic end generated code: output=ebb6dc5f111c7dc0 input=7f6c18eac10ada86]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007650{
7651 pid_t pgid = tcgetpgrp(fd);
Victor Stinner8c62be82010-05-06 00:08:46 +00007652 if (pgid < 0)
7653 return posix_error();
7654 return PyLong_FromPid(pgid);
Guido van Rossum7066dd71992-09-17 17:54:56 +00007655}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007656#endif /* HAVE_TCGETPGRP */
Guido van Rossum7066dd71992-09-17 17:54:56 +00007657
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007658
Guido van Rossumb6775db1994-08-01 11:34:53 +00007659#ifdef HAVE_TCSETPGRP
Larry Hastings2f936352014-08-05 14:04:04 +10007660/*[clinic input]
7661os.tcsetpgrp
7662
7663 fd: int
7664 pgid: pid_t
7665 /
7666
7667Set the process group associated with the terminal specified by fd.
7668[clinic start generated code]*/
7669
Larry Hastings2f936352014-08-05 14:04:04 +10007670static PyObject *
7671os_tcsetpgrp_impl(PyModuleDef *module, int fd, pid_t pgid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007672/*[clinic end generated code: output=3e4b05177462cd22 input=5bdc997c6a619020]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007673{
Victor Stinner8c62be82010-05-06 00:08:46 +00007674 if (tcsetpgrp(fd, pgid) < 0)
7675 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007676 Py_RETURN_NONE;
Guido van Rossum7066dd71992-09-17 17:54:56 +00007677}
Guido van Rossumb6775db1994-08-01 11:34:53 +00007678#endif /* HAVE_TCSETPGRP */
Guido van Rossum22db57e1992-04-05 14:25:30 +00007679
Guido van Rossum687dd131993-05-17 08:34:16 +00007680/* Functions acting on file descriptors */
7681
Victor Stinnerdaf45552013-08-28 00:53:59 +02007682#ifdef O_CLOEXEC
7683extern int _Py_open_cloexec_works;
7684#endif
7685
Larry Hastings2f936352014-08-05 14:04:04 +10007686
7687/*[clinic input]
7688os.open -> int
7689 path: path_t
7690 flags: int
7691 mode: int = 0o777
7692 *
7693 dir_fd: dir_fd(requires='openat') = None
7694
7695# "open(path, flags, mode=0o777, *, dir_fd=None)\n\n\
7696
7697Open a file for low level IO. Returns a file descriptor (integer).
7698
7699If dir_fd is not None, it should be a file descriptor open to a directory,
7700 and path should be relative; path will then be relative to that directory.
7701dir_fd may not be implemented on your platform.
7702 If it is unavailable, using it will raise a NotImplementedError.
7703[clinic start generated code]*/
7704
Larry Hastings2f936352014-08-05 14:04:04 +10007705static int
Larry Hastings89964c42015-04-14 18:07:59 -04007706os_open_impl(PyModuleDef *module, path_t *path, int flags, int mode,
7707 int dir_fd)
7708/*[clinic end generated code: output=47e8cc63559f5ddd input=ad8623b29acd2934]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007709{
7710 int fd;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007711 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10007712
Victor Stinnerdaf45552013-08-28 00:53:59 +02007713#ifdef O_CLOEXEC
7714 int *atomic_flag_works = &_Py_open_cloexec_works;
7715#elif !defined(MS_WINDOWS)
7716 int *atomic_flag_works = NULL;
7717#endif
Mark Hammondc2e85bd2002-10-03 05:10:39 +00007718
Victor Stinnerdaf45552013-08-28 00:53:59 +02007719#ifdef MS_WINDOWS
7720 flags |= O_NOINHERIT;
7721#elif defined(O_CLOEXEC)
7722 flags |= O_CLOEXEC;
7723#endif
7724
Steve Dower8fc89802015-04-12 00:26:27 -04007725 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007726 do {
7727 Py_BEGIN_ALLOW_THREADS
Larry Hastings9cf065c2012-06-22 16:30:09 -07007728#ifdef MS_WINDOWS
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007729 if (path->wide)
7730 fd = _wopen(path->wide, flags, mode);
7731 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007732#endif
7733#ifdef HAVE_OPENAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007734 if (dir_fd != DEFAULT_DIR_FD)
7735 fd = openat(dir_fd, path->narrow, flags, mode);
7736 else
Larry Hastings9cf065c2012-06-22 16:30:09 -07007737#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007738 fd = open(path->narrow, flags, mode);
7739 Py_END_ALLOW_THREADS
7740 } while (fd < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Steve Dower8fc89802015-04-12 00:26:27 -04007741 _Py_END_SUPPRESS_IPH
Guido van Rossum687dd131993-05-17 08:34:16 +00007742
Victor Stinnerd3ffd322015-09-15 10:11:03 +02007743 if (fd < 0) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007744 if (!async_err)
7745 PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, path->object);
Larry Hastings2f936352014-08-05 14:04:04 +10007746 return -1;
Larry Hastings9cf065c2012-06-22 16:30:09 -07007747 }
7748
Victor Stinnerdaf45552013-08-28 00:53:59 +02007749#ifndef MS_WINDOWS
7750 if (_Py_set_inheritable(fd, 0, atomic_flag_works) < 0) {
7751 close(fd);
Larry Hastings2f936352014-08-05 14:04:04 +10007752 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +02007753 }
7754#endif
7755
Larry Hastings2f936352014-08-05 14:04:04 +10007756 return fd;
7757}
7758
7759
7760/*[clinic input]
7761os.close
7762
7763 fd: int
7764
7765Close a file descriptor.
7766[clinic start generated code]*/
7767
Barry Warsaw53699e91996-12-10 23:23:01 +00007768static PyObject *
Larry Hastings2f936352014-08-05 14:04:04 +10007769os_close_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007770/*[clinic end generated code: output=47bf2ea536445a26 input=2bc42451ca5c3223]*/
Guido van Rossum687dd131993-05-17 08:34:16 +00007771{
Larry Hastings2f936352014-08-05 14:04:04 +10007772 int res;
Victor Stinner8c62be82010-05-06 00:08:46 +00007773 if (!_PyVerify_fd(fd))
7774 return posix_error();
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007775 /* We do not want to retry upon EINTR: see http://lwn.net/Articles/576478/
7776 * and http://linux.derkeiler.com/Mailing-Lists/Kernel/2005-09/3000.html
7777 * for more details.
7778 */
Victor Stinner8c62be82010-05-06 00:08:46 +00007779 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007780 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007781 res = close(fd);
Steve Dower8fc89802015-04-12 00:26:27 -04007782 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007783 Py_END_ALLOW_THREADS
7784 if (res < 0)
7785 return posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10007786 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +00007787}
7788
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007789
Larry Hastings2f936352014-08-05 14:04:04 +10007790/*[clinic input]
7791os.closerange
7792
7793 fd_low: int
7794 fd_high: int
7795 /
7796
7797Closes all file descriptors in [fd_low, fd_high), ignoring errors.
7798[clinic start generated code]*/
7799
Larry Hastings2f936352014-08-05 14:04:04 +10007800static PyObject *
7801os_closerange_impl(PyModuleDef *module, int fd_low, int fd_high)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007802/*[clinic end generated code: output=70e6adb95220ba96 input=5855a3d053ebd4ec]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007803{
7804 int i;
Victor Stinner8c62be82010-05-06 00:08:46 +00007805 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007806 _Py_BEGIN_SUPPRESS_IPH
Larry Hastings2f936352014-08-05 14:04:04 +10007807 for (i = fd_low; i < fd_high; i++)
Victor Stinner8c62be82010-05-06 00:08:46 +00007808 if (_PyVerify_fd(i))
7809 close(i);
Steve Dower8fc89802015-04-12 00:26:27 -04007810 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007811 Py_END_ALLOW_THREADS
7812 Py_RETURN_NONE;
Christian Heimesfdab48e2008-01-20 09:06:41 +00007813}
7814
7815
Larry Hastings2f936352014-08-05 14:04:04 +10007816/*[clinic input]
7817os.dup -> int
7818
7819 fd: int
7820 /
7821
7822Return a duplicate of a file descriptor.
7823[clinic start generated code]*/
7824
Larry Hastings2f936352014-08-05 14:04:04 +10007825static int
7826os_dup_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007827/*[clinic end generated code: output=f4bbac8c7652d05e input=6f10f7ea97f7852a]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007828{
7829 return _Py_dup(fd);
Guido van Rossum687dd131993-05-17 08:34:16 +00007830}
7831
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007832
Larry Hastings2f936352014-08-05 14:04:04 +10007833/*[clinic input]
7834os.dup2
7835 fd: int
7836 fd2: int
7837 inheritable: bool=True
7838
7839Duplicate file descriptor.
7840[clinic start generated code]*/
7841
Larry Hastings2f936352014-08-05 14:04:04 +10007842static PyObject *
7843os_dup2_impl(PyModuleDef *module, int fd, int fd2, int inheritable)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007844/*[clinic end generated code: output=9a099d95881a7923 input=76e96f511be0352f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007845{
Victor Stinnerdaf45552013-08-28 00:53:59 +02007846 int res;
7847#if defined(HAVE_DUP3) && \
7848 !(defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC))
7849 /* dup3() is available on Linux 2.6.27+ and glibc 2.9 */
7850 int dup3_works = -1;
7851#endif
7852
Victor Stinner8c62be82010-05-06 00:08:46 +00007853 if (!_PyVerify_fd_dup2(fd, fd2))
7854 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +02007855
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00007856 /* dup2() can fail with EINTR if the target FD is already open, because it
7857 * then has to be closed. See os_close_impl() for why we don't handle EINTR
7858 * upon close(), and therefore below.
7859 */
Victor Stinnerdaf45552013-08-28 00:53:59 +02007860#ifdef MS_WINDOWS
7861 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007862 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00007863 res = dup2(fd, fd2);
Steve Dower8fc89802015-04-12 00:26:27 -04007864 _Py_END_SUPPRESS_IPH
Victor Stinnerdaf45552013-08-28 00:53:59 +02007865 Py_END_ALLOW_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +00007866 if (res < 0)
7867 return posix_error();
Victor Stinnerdaf45552013-08-28 00:53:59 +02007868
7869 /* Character files like console cannot be make non-inheritable */
7870 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
7871 close(fd2);
7872 return NULL;
7873 }
7874
7875#elif defined(HAVE_FCNTL_H) && defined(F_DUP2FD_CLOEXEC)
7876 Py_BEGIN_ALLOW_THREADS
7877 if (!inheritable)
7878 res = fcntl(fd, F_DUP2FD_CLOEXEC, fd2);
7879 else
7880 res = dup2(fd, fd2);
7881 Py_END_ALLOW_THREADS
7882 if (res < 0)
7883 return posix_error();
7884
7885#else
7886
7887#ifdef HAVE_DUP3
7888 if (!inheritable && dup3_works != 0) {
7889 Py_BEGIN_ALLOW_THREADS
7890 res = dup3(fd, fd2, O_CLOEXEC);
7891 Py_END_ALLOW_THREADS
7892 if (res < 0) {
7893 if (dup3_works == -1)
7894 dup3_works = (errno != ENOSYS);
7895 if (dup3_works)
7896 return posix_error();
7897 }
7898 }
7899
7900 if (inheritable || dup3_works == 0)
7901 {
7902#endif
7903 Py_BEGIN_ALLOW_THREADS
7904 res = dup2(fd, fd2);
7905 Py_END_ALLOW_THREADS
7906 if (res < 0)
7907 return posix_error();
7908
7909 if (!inheritable && _Py_set_inheritable(fd2, 0, NULL) < 0) {
7910 close(fd2);
7911 return NULL;
7912 }
7913#ifdef HAVE_DUP3
7914 }
7915#endif
7916
7917#endif
7918
Larry Hastings2f936352014-08-05 14:04:04 +10007919 Py_RETURN_NONE;
Guido van Rossum687dd131993-05-17 08:34:16 +00007920}
7921
Larry Hastings2f936352014-08-05 14:04:04 +10007922
Ross Lagerwall7807c352011-03-17 20:20:30 +02007923#ifdef HAVE_LOCKF
Larry Hastings2f936352014-08-05 14:04:04 +10007924/*[clinic input]
7925os.lockf
7926
7927 fd: int
7928 An open file descriptor.
7929 command: int
7930 One of F_LOCK, F_TLOCK, F_ULOCK or F_TEST.
7931 length: Py_off_t
7932 The number of bytes to lock, starting at the current position.
7933 /
7934
7935Apply, test or remove a POSIX lock on an open file descriptor.
7936
7937[clinic start generated code]*/
7938
Larry Hastings2f936352014-08-05 14:04:04 +10007939static PyObject *
7940os_lockf_impl(PyModuleDef *module, int fd, int command, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007941/*[clinic end generated code: output=25ff778f9e2fbf1b input=65da41d2106e9b79]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007942{
7943 int res;
Ross Lagerwall7807c352011-03-17 20:20:30 +02007944
7945 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10007946 res = lockf(fd, command, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +02007947 Py_END_ALLOW_THREADS
7948
7949 if (res < 0)
7950 return posix_error();
7951
7952 Py_RETURN_NONE;
7953}
Larry Hastings2f936352014-08-05 14:04:04 +10007954#endif /* HAVE_LOCKF */
Ross Lagerwall7807c352011-03-17 20:20:30 +02007955
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00007956
Larry Hastings2f936352014-08-05 14:04:04 +10007957/*[clinic input]
7958os.lseek -> Py_off_t
7959
7960 fd: int
7961 position: Py_off_t
7962 how: int
7963 /
7964
7965Set the position of a file descriptor. Return the new position.
7966
7967Return the new cursor position in number of bytes
7968relative to the beginning of the file.
7969[clinic start generated code]*/
7970
Larry Hastings2f936352014-08-05 14:04:04 +10007971static Py_off_t
7972os_lseek_impl(PyModuleDef *module, int fd, Py_off_t position, int how)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03007973/*[clinic end generated code: output=65d4ab96d664998c input=902654ad3f96a6d3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10007974{
7975 Py_off_t result;
7976
7977 if (!_PyVerify_fd(fd)) {
7978 posix_error();
7979 return -1;
7980 }
Guido van Rossum687dd131993-05-17 08:34:16 +00007981#ifdef SEEK_SET
Victor Stinner8c62be82010-05-06 00:08:46 +00007982 /* Turn 0, 1, 2 into SEEK_{SET,CUR,END} */
7983 switch (how) {
Larry Hastings2f936352014-08-05 14:04:04 +10007984 case 0: how = SEEK_SET; break;
7985 case 1: how = SEEK_CUR; break;
7986 case 2: how = SEEK_END; break;
Victor Stinner8c62be82010-05-06 00:08:46 +00007987 }
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +00007988#endif /* SEEK_END */
Guido van Rossum94f6f721999-01-06 18:42:14 +00007989
Victor Stinner8c62be82010-05-06 00:08:46 +00007990 if (PyErr_Occurred())
Larry Hastings2f936352014-08-05 14:04:04 +10007991 return -1;
Guido van Rossum94f6f721999-01-06 18:42:14 +00007992
Larry Hastings2f936352014-08-05 14:04:04 +10007993 if (!_PyVerify_fd(fd)) {
7994 posix_error();
7995 return -1;
7996 }
Victor Stinner8c62be82010-05-06 00:08:46 +00007997 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04007998 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner14b9b112013-06-25 00:37:25 +02007999#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008000 result = _lseeki64(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +00008001#else
Larry Hastings2f936352014-08-05 14:04:04 +10008002 result = lseek(fd, position, how);
Fred Drake699f3522000-06-29 21:12:41 +00008003#endif
Steve Dower8fc89802015-04-12 00:26:27 -04008004 _Py_END_SUPPRESS_IPH
Victor Stinner8c62be82010-05-06 00:08:46 +00008005 Py_END_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10008006 if (result < 0)
8007 posix_error();
Guido van Rossum94f6f721999-01-06 18:42:14 +00008008
Larry Hastings2f936352014-08-05 14:04:04 +10008009 return result;
Guido van Rossum687dd131993-05-17 08:34:16 +00008010}
8011
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008012
Larry Hastings2f936352014-08-05 14:04:04 +10008013/*[clinic input]
8014os.read
8015 fd: int
8016 length: Py_ssize_t
8017 /
8018
8019Read from a file descriptor. Returns a bytes object.
8020[clinic start generated code]*/
8021
Larry Hastings2f936352014-08-05 14:04:04 +10008022static PyObject *
8023os_read_impl(PyModuleDef *module, int fd, Py_ssize_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008024/*[clinic end generated code: output=be24f44178455e8b input=1df2eaa27c0bf1d3]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008025{
Victor Stinner8c62be82010-05-06 00:08:46 +00008026 Py_ssize_t n;
8027 PyObject *buffer;
Larry Hastings2f936352014-08-05 14:04:04 +10008028
8029 if (length < 0) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008030 errno = EINVAL;
8031 return posix_error();
8032 }
Larry Hastings2f936352014-08-05 14:04:04 +10008033
8034#ifdef MS_WINDOWS
Victor Stinner66aab0c2015-03-19 22:53:20 +01008035 /* On Windows, the count parameter of read() is an int */
Larry Hastings2f936352014-08-05 14:04:04 +10008036 if (length > INT_MAX)
8037 length = INT_MAX;
Larry Hastings2f936352014-08-05 14:04:04 +10008038#endif
8039
8040 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Victor Stinner8c62be82010-05-06 00:08:46 +00008041 if (buffer == NULL)
8042 return NULL;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008043
Victor Stinner66aab0c2015-03-19 22:53:20 +01008044 n = _Py_read(fd, PyBytes_AS_STRING(buffer), length);
8045 if (n == -1) {
Victor Stinner8c62be82010-05-06 00:08:46 +00008046 Py_DECREF(buffer);
Victor Stinner66aab0c2015-03-19 22:53:20 +01008047 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +00008048 }
Larry Hastings2f936352014-08-05 14:04:04 +10008049
8050 if (n != length)
Victor Stinner8c62be82010-05-06 00:08:46 +00008051 _PyBytes_Resize(&buffer, n);
Larry Hastings2f936352014-08-05 14:04:04 +10008052
Victor Stinner8c62be82010-05-06 00:08:46 +00008053 return buffer;
Guido van Rossum687dd131993-05-17 08:34:16 +00008054}
8055
Ross Lagerwall7807c352011-03-17 20:20:30 +02008056#if (defined(HAVE_SENDFILE) && (defined(__FreeBSD__) || defined(__DragonFly__) \
8057 || defined(__APPLE__))) || defined(HAVE_READV) || defined(HAVE_WRITEV)
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008058static Py_ssize_t
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008059iov_setup(struct iovec **iov, Py_buffer **buf, PyObject *seq, int cnt, int type)
8060{
8061 int i, j;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008062 Py_ssize_t blen, total = 0;
8063
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008064 *iov = PyMem_New(struct iovec, cnt);
8065 if (*iov == NULL) {
8066 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +01008067 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008068 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008069
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008070 *buf = PyMem_New(Py_buffer, cnt);
8071 if (*buf == NULL) {
8072 PyMem_Del(*iov);
8073 PyErr_NoMemory();
Victor Stinner57ddf782014-01-08 15:21:28 +01008074 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008075 }
8076
8077 for (i = 0; i < cnt; i++) {
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008078 PyObject *item = PySequence_GetItem(seq, i);
8079 if (item == NULL)
8080 goto fail;
8081 if (PyObject_GetBuffer(item, &(*buf)[i], type) == -1) {
8082 Py_DECREF(item);
8083 goto fail;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008084 }
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008085 Py_DECREF(item);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008086 (*iov)[i].iov_base = (*buf)[i].buf;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008087 blen = (*buf)[i].len;
8088 (*iov)[i].iov_len = blen;
8089 total += blen;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008090 }
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008091 return total;
Ross Lagerwall9ad63e02011-03-19 09:11:14 +02008092
8093fail:
8094 PyMem_Del(*iov);
8095 for (j = 0; j < i; j++) {
8096 PyBuffer_Release(&(*buf)[j]);
8097 }
8098 PyMem_Del(*buf);
Victor Stinner57ddf782014-01-08 15:21:28 +01008099 return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008100}
8101
8102static void
8103iov_cleanup(struct iovec *iov, Py_buffer *buf, int cnt)
8104{
8105 int i;
8106 PyMem_Del(iov);
8107 for (i = 0; i < cnt; i++) {
8108 PyBuffer_Release(&buf[i]);
8109 }
8110 PyMem_Del(buf);
8111}
8112#endif
8113
Larry Hastings2f936352014-08-05 14:04:04 +10008114
Ross Lagerwall7807c352011-03-17 20:20:30 +02008115#ifdef HAVE_READV
Larry Hastings2f936352014-08-05 14:04:04 +10008116/*[clinic input]
8117os.readv -> Py_ssize_t
8118
8119 fd: int
8120 buffers: object
8121 /
8122
8123Read from a file descriptor fd into an iterable of buffers.
8124
8125The buffers should be mutable buffers accepting bytes.
8126readv will transfer data into each buffer until it is full
8127and then move on to the next buffer in the sequence to hold
8128the rest of the data.
8129
8130readv returns the total number of bytes read,
8131which may be less than the total capacity of all the buffers.
8132[clinic start generated code]*/
8133
Larry Hastings2f936352014-08-05 14:04:04 +10008134static Py_ssize_t
8135os_readv_impl(PyModuleDef *module, int fd, PyObject *buffers)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008136/*[clinic end generated code: output=00fc56ff1800059f input=e679eb5dbfa0357d]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008137{
8138 int cnt;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008139 Py_ssize_t n;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008140 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008141 struct iovec *iov;
8142 Py_buffer *buf;
8143
Larry Hastings2f936352014-08-05 14:04:04 +10008144 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008145 PyErr_SetString(PyExc_TypeError,
8146 "readv() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +10008147 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008148 }
Ross Lagerwall7807c352011-03-17 20:20:30 +02008149
Larry Hastings2f936352014-08-05 14:04:04 +10008150 cnt = PySequence_Size(buffers);
8151
8152 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_WRITABLE) < 0)
8153 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008154
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008155 do {
8156 Py_BEGIN_ALLOW_THREADS
8157 n = readv(fd, iov, cnt);
8158 Py_END_ALLOW_THREADS
8159 } while (n < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Ross Lagerwall7807c352011-03-17 20:20:30 +02008160
8161 iov_cleanup(iov, buf, cnt);
Larry Hastings2f936352014-08-05 14:04:04 +10008162 if (n < 0) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008163 if (!async_err)
8164 posix_error();
Larry Hastings2f936352014-08-05 14:04:04 +10008165 return -1;
8166 }
Victor Stinner57ddf782014-01-08 15:21:28 +01008167
Larry Hastings2f936352014-08-05 14:04:04 +10008168 return n;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008169}
Larry Hastings2f936352014-08-05 14:04:04 +10008170#endif /* HAVE_READV */
8171
Ross Lagerwall7807c352011-03-17 20:20:30 +02008172
8173#ifdef HAVE_PREAD
Larry Hastings2f936352014-08-05 14:04:04 +10008174/*[clinic input]
8175# TODO length should be size_t! but Python doesn't support parsing size_t yet.
8176os.pread
8177
8178 fd: int
8179 length: int
8180 offset: Py_off_t
8181 /
8182
8183Read a number of bytes from a file descriptor starting at a particular offset.
8184
8185Read length bytes from file descriptor fd, starting at offset bytes from
8186the beginning of the file. The file offset remains unchanged.
8187[clinic start generated code]*/
8188
Larry Hastings2f936352014-08-05 14:04:04 +10008189static PyObject *
8190os_pread_impl(PyModuleDef *module, int fd, int length, Py_off_t offset)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008191/*[clinic end generated code: output=90d1fed87f68fa33 input=084948dcbaa35d4c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008192{
Ross Lagerwall7807c352011-03-17 20:20:30 +02008193 Py_ssize_t n;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008194 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008195 PyObject *buffer;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008196
Larry Hastings2f936352014-08-05 14:04:04 +10008197 if (length < 0) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008198 errno = EINVAL;
8199 return posix_error();
8200 }
Larry Hastings2f936352014-08-05 14:04:04 +10008201 buffer = PyBytes_FromStringAndSize((char *)NULL, length);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008202 if (buffer == NULL)
8203 return NULL;
8204 if (!_PyVerify_fd(fd)) {
8205 Py_DECREF(buffer);
8206 return posix_error();
8207 }
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008208
8209 do {
8210 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04008211 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008212 n = pread(fd, PyBytes_AS_STRING(buffer), length, offset);
Steve Dower8fc89802015-04-12 00:26:27 -04008213 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008214 Py_END_ALLOW_THREADS
8215 } while (n < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
8216
Ross Lagerwall7807c352011-03-17 20:20:30 +02008217 if (n < 0) {
8218 Py_DECREF(buffer);
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008219 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008220 }
Larry Hastings2f936352014-08-05 14:04:04 +10008221 if (n != length)
Ross Lagerwall7807c352011-03-17 20:20:30 +02008222 _PyBytes_Resize(&buffer, n);
8223 return buffer;
8224}
Larry Hastings2f936352014-08-05 14:04:04 +10008225#endif /* HAVE_PREAD */
Ross Lagerwall7807c352011-03-17 20:20:30 +02008226
Larry Hastings2f936352014-08-05 14:04:04 +10008227
8228/*[clinic input]
8229os.write -> Py_ssize_t
8230
8231 fd: int
8232 data: Py_buffer
8233 /
8234
8235Write a bytes object to a file descriptor.
8236[clinic start generated code]*/
8237
Larry Hastings2f936352014-08-05 14:04:04 +10008238static Py_ssize_t
8239os_write_impl(PyModuleDef *module, int fd, Py_buffer *data)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008240/*[clinic end generated code: output=58845c93c9ee1dda input=3207e28963234f3c]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008241{
Victor Stinner66aab0c2015-03-19 22:53:20 +01008242 return _Py_write(fd, data->buf, data->len);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008243}
8244
8245#ifdef HAVE_SENDFILE
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008246PyDoc_STRVAR(posix_sendfile__doc__,
Martin Panterbf19d162015-09-09 01:01:13 +00008247"sendfile(out, in, offset, count) -> byteswritten\n\
Martin Panter94994132015-09-09 05:29:24 +00008248sendfile(out, in, offset, count[, headers][, trailers], flags=0)\n\
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008249 -> byteswritten\n\
Martin Panterbf19d162015-09-09 01:01:13 +00008250Copy count bytes from file descriptor in to file descriptor out.");
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008251
Larry Hastings2f936352014-08-05 14:04:04 +10008252/* AC 3.5: don't bother converting, has optional group*/
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008253static PyObject *
8254posix_sendfile(PyObject *self, PyObject *args, PyObject *kwdict)
8255{
8256 int in, out;
8257 Py_ssize_t ret;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008258 int async_err = 0;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008259 off_t offset;
8260
8261#if defined(__FreeBSD__) || defined(__DragonFly__) || defined(__APPLE__)
8262#ifndef __APPLE__
8263 Py_ssize_t len;
8264#endif
8265 PyObject *headers = NULL, *trailers = NULL;
8266 Py_buffer *hbuf, *tbuf;
8267 off_t sbytes;
8268 struct sf_hdtr sf;
8269 int flags = 0;
Martin Panterbf19d162015-09-09 01:01:13 +00008270 /* Beware that "in" clashes with Python's own "in" operator keyword */
Benjamin Petersond8a43b42011-02-26 21:35:16 +00008271 static char *keywords[] = {"out", "in",
8272 "offset", "count",
8273 "headers", "trailers", "flags", NULL};
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008274
Victor Stinner6ce0dbf2013-07-07 16:32:36 +02008275 sf.headers = NULL;
8276 sf.trailers = NULL;
8277
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008278#ifdef __APPLE__
8279 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&O&|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +10008280 keywords, &out, &in, Py_off_t_converter, &offset, Py_off_t_converter, &sbytes,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008281#else
8282 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiO&n|OOi:sendfile",
Larry Hastings2f936352014-08-05 14:04:04 +10008283 keywords, &out, &in, Py_off_t_converter, &offset, &len,
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008284#endif
8285 &headers, &trailers, &flags))
8286 return NULL;
8287 if (headers != NULL) {
8288 if (!PySequence_Check(headers)) {
8289 PyErr_SetString(PyExc_TypeError,
Martin Panter94994132015-09-09 05:29:24 +00008290 "sendfile() headers must be a sequence");
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008291 return NULL;
8292 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008293 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008294 sf.hdr_cnt = PySequence_Size(headers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008295 if (sf.hdr_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +01008296 (i = iov_setup(&(sf.headers), &hbuf,
8297 headers, sf.hdr_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008298 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008299#ifdef __APPLE__
8300 sbytes += i;
8301#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008302 }
8303 }
8304 if (trailers != NULL) {
8305 if (!PySequence_Check(trailers)) {
8306 PyErr_SetString(PyExc_TypeError,
Martin Panter94994132015-09-09 05:29:24 +00008307 "sendfile() trailers must be a sequence");
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008308 return NULL;
8309 } else {
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008310 Py_ssize_t i = 0; /* Avoid uninitialized warning */
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008311 sf.trl_cnt = PySequence_Size(trailers);
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008312 if (sf.trl_cnt > 0 &&
Victor Stinner57ddf782014-01-08 15:21:28 +01008313 (i = iov_setup(&(sf.trailers), &tbuf,
8314 trailers, sf.trl_cnt, PyBUF_SIMPLE)) < 0)
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008315 return NULL;
Giampaolo Rodolàacdad9a2011-03-03 16:10:51 +00008316#ifdef __APPLE__
8317 sbytes += i;
8318#endif
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008319 }
8320 }
8321
Steve Dower8fc89802015-04-12 00:26:27 -04008322 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008323 do {
8324 Py_BEGIN_ALLOW_THREADS
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008325#ifdef __APPLE__
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008326 ret = sendfile(in, out, offset, &sbytes, &sf, flags);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008327#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008328 ret = sendfile(in, out, offset, len, &sf, &sbytes, flags);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008329#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008330 Py_END_ALLOW_THREADS
8331 } while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Steve Dower8fc89802015-04-12 00:26:27 -04008332 _Py_END_SUPPRESS_IPH
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008333
8334 if (sf.headers != NULL)
8335 iov_cleanup(sf.headers, hbuf, sf.hdr_cnt);
8336 if (sf.trailers != NULL)
8337 iov_cleanup(sf.trailers, tbuf, sf.trl_cnt);
8338
8339 if (ret < 0) {
8340 if ((errno == EAGAIN) || (errno == EBUSY)) {
8341 if (sbytes != 0) {
8342 // some data has been sent
8343 goto done;
8344 }
8345 else {
8346 // no data has been sent; upper application is supposed
8347 // to retry on EAGAIN or EBUSY
8348 return posix_error();
8349 }
8350 }
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008351 return (!async_err) ? posix_error() : NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008352 }
8353 goto done;
8354
8355done:
8356 #if !defined(HAVE_LARGEFILE_SUPPORT)
8357 return Py_BuildValue("l", sbytes);
8358 #else
8359 return Py_BuildValue("L", sbytes);
8360 #endif
8361
8362#else
8363 Py_ssize_t count;
8364 PyObject *offobj;
8365 static char *keywords[] = {"out", "in",
8366 "offset", "count", NULL};
8367 if (!PyArg_ParseTupleAndKeywords(args, kwdict, "iiOn:sendfile",
8368 keywords, &out, &in, &offobj, &count))
8369 return NULL;
8370#ifdef linux
8371 if (offobj == Py_None) {
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008372 do {
8373 Py_BEGIN_ALLOW_THREADS
8374 ret = sendfile(out, in, NULL, 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 Rodola'ff1a7352011-04-19 09:47:16 +02008379 return Py_BuildValue("n", ret);
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008380 }
8381#endif
Larry Hastings2f936352014-08-05 14:04:04 +10008382 if (!Py_off_t_converter(offobj, &offset))
Antoine Pitroudcc20b82011-02-26 13:38:35 +00008383 return NULL;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008384
8385 do {
8386 Py_BEGIN_ALLOW_THREADS
8387 ret = sendfile(out, in, &offset, count);
8388 Py_END_ALLOW_THREADS
8389 } while (ret < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008390 if (ret < 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008391 return (!async_err) ? posix_error() : NULL;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +00008392 return Py_BuildValue("n", ret);
8393#endif
8394}
Larry Hastings2f936352014-08-05 14:04:04 +10008395#endif /* HAVE_SENDFILE */
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008396
Larry Hastings2f936352014-08-05 14:04:04 +10008397
8398/*[clinic input]
8399os.fstat
8400
8401 fd : int
8402
8403Perform a stat system call on the given file descriptor.
8404
8405Like stat(), but for an open file descriptor.
8406Equivalent to os.stat(fd).
8407[clinic start generated code]*/
8408
Larry Hastings2f936352014-08-05 14:04:04 +10008409static PyObject *
8410os_fstat_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008411/*[clinic end generated code: output=d71fe98bf042b626 input=27e0e0ebbe5600c9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008412{
Victor Stinner8c62be82010-05-06 00:08:46 +00008413 STRUCT_STAT st;
8414 int res;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008415 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008416
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008417 do {
8418 Py_BEGIN_ALLOW_THREADS
8419 res = FSTAT(fd, &st);
8420 Py_END_ALLOW_THREADS
8421 } while (res != 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Victor Stinner8c62be82010-05-06 00:08:46 +00008422 if (res != 0) {
Martin v. Löwis14694662006-02-03 12:54:16 +00008423#ifdef MS_WINDOWS
Victor Stinnerb024e842012-10-31 22:24:06 +01008424 return PyErr_SetFromWindowsErr(0);
Martin v. Löwis14694662006-02-03 12:54:16 +00008425#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008426 return (!async_err) ? posix_error() : NULL;
Martin v. Löwis14694662006-02-03 12:54:16 +00008427#endif
Victor Stinner8c62be82010-05-06 00:08:46 +00008428 }
Tim Peters5aa91602002-01-30 05:46:57 +00008429
Victor Stinner4195b5c2012-02-08 23:03:19 +01008430 return _pystat_fromstructstat(&st);
Guido van Rossum687dd131993-05-17 08:34:16 +00008431}
8432
Larry Hastings2f936352014-08-05 14:04:04 +10008433
8434/*[clinic input]
8435os.isatty -> bool
8436 fd: int
8437 /
8438
8439Return True if the fd is connected to a terminal.
8440
8441Return True if the file descriptor is an open file descriptor
8442connected to the slave end of a terminal.
8443[clinic start generated code]*/
8444
Larry Hastings2f936352014-08-05 14:04:04 +10008445static int
8446os_isatty_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008447/*[clinic end generated code: output=acec9d3c29d16d33 input=08ce94aa1eaf7b5e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008448{
Steve Dower8fc89802015-04-12 00:26:27 -04008449 int return_value;
Larry Hastings2f936352014-08-05 14:04:04 +10008450 if (!_PyVerify_fd(fd))
8451 return 0;
Steve Dower8fc89802015-04-12 00:26:27 -04008452 _Py_BEGIN_SUPPRESS_IPH
8453 return_value = isatty(fd);
8454 _Py_END_SUPPRESS_IPH
8455 return return_value;
Larry Hastings2f936352014-08-05 14:04:04 +10008456}
8457
8458
Guido van Rossuma4916fa1996-05-23 22:58:55 +00008459#ifdef HAVE_PIPE
Larry Hastings2f936352014-08-05 14:04:04 +10008460/*[clinic input]
8461os.pipe
8462
8463Create a pipe.
8464
8465Returns a tuple of two file descriptors:
8466 (read_fd, write_fd)
8467[clinic start generated code]*/
8468
Larry Hastings2f936352014-08-05 14:04:04 +10008469static PyObject *
8470os_pipe_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008471/*[clinic end generated code: output=6b0cd3f868ec3c40 input=02535e8c8fa6c4d4]*/
Guido van Rossum687dd131993-05-17 08:34:16 +00008472{
Victor Stinner8c62be82010-05-06 00:08:46 +00008473 int fds[2];
Victor Stinnerdaf45552013-08-28 00:53:59 +02008474#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +00008475 HANDLE read, write;
Victor Stinnerdaf45552013-08-28 00:53:59 +02008476 SECURITY_ATTRIBUTES attr;
Victor Stinner8c62be82010-05-06 00:08:46 +00008477 BOOL ok;
Victor Stinnerdaf45552013-08-28 00:53:59 +02008478#else
8479 int res;
8480#endif
8481
8482#ifdef MS_WINDOWS
8483 attr.nLength = sizeof(attr);
8484 attr.lpSecurityDescriptor = NULL;
8485 attr.bInheritHandle = FALSE;
8486
8487 Py_BEGIN_ALLOW_THREADS
8488 ok = CreatePipe(&read, &write, &attr, 0);
8489 if (ok) {
8490 fds[0] = _open_osfhandle((Py_intptr_t)read, _O_RDONLY);
8491 fds[1] = _open_osfhandle((Py_intptr_t)write, _O_WRONLY);
8492 if (fds[0] == -1 || fds[1] == -1) {
8493 CloseHandle(read);
8494 CloseHandle(write);
8495 ok = 0;
8496 }
8497 }
8498 Py_END_ALLOW_THREADS
8499
Victor Stinner8c62be82010-05-06 00:08:46 +00008500 if (!ok)
Victor Stinnerb024e842012-10-31 22:24:06 +01008501 return PyErr_SetFromWindowsErr(0);
Victor Stinnerdaf45552013-08-28 00:53:59 +02008502#else
8503
8504#ifdef HAVE_PIPE2
8505 Py_BEGIN_ALLOW_THREADS
8506 res = pipe2(fds, O_CLOEXEC);
8507 Py_END_ALLOW_THREADS
8508
8509 if (res != 0 && errno == ENOSYS)
8510 {
8511#endif
8512 Py_BEGIN_ALLOW_THREADS
8513 res = pipe(fds);
8514 Py_END_ALLOW_THREADS
8515
8516 if (res == 0) {
8517 if (_Py_set_inheritable(fds[0], 0, NULL) < 0) {
8518 close(fds[0]);
8519 close(fds[1]);
8520 return NULL;
8521 }
8522 if (_Py_set_inheritable(fds[1], 0, NULL) < 0) {
8523 close(fds[0]);
8524 close(fds[1]);
8525 return NULL;
8526 }
8527 }
8528#ifdef HAVE_PIPE2
8529 }
8530#endif
8531
8532 if (res != 0)
8533 return PyErr_SetFromErrno(PyExc_OSError);
8534#endif /* !MS_WINDOWS */
8535 return Py_BuildValue("(ii)", fds[0], fds[1]);
Guido van Rossum687dd131993-05-17 08:34:16 +00008536}
Guido van Rossuma4916fa1996-05-23 22:58:55 +00008537#endif /* HAVE_PIPE */
8538
Larry Hastings2f936352014-08-05 14:04:04 +10008539
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008540#ifdef HAVE_PIPE2
Larry Hastings2f936352014-08-05 14:04:04 +10008541/*[clinic input]
8542os.pipe2
8543
8544 flags: int
8545 /
8546
8547Create a pipe with flags set atomically.
8548
8549Returns a tuple of two file descriptors:
8550 (read_fd, write_fd)
8551
8552flags can be constructed by ORing together one or more of these values:
8553O_NONBLOCK, O_CLOEXEC.
8554[clinic start generated code]*/
8555
Larry Hastings2f936352014-08-05 14:04:04 +10008556static PyObject *
8557os_pipe2_impl(PyModuleDef *module, int flags)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008558/*[clinic end generated code: output=c15b6075d0c6b2e7 input=f261b6e7e63c6817]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008559{
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008560 int fds[2];
8561 int res;
8562
Charles-François Natalidaafdd52011-05-29 20:07:40 +02008563 res = pipe2(fds, flags);
8564 if (res != 0)
8565 return posix_error();
8566 return Py_BuildValue("(ii)", fds[0], fds[1]);
8567}
8568#endif /* HAVE_PIPE2 */
8569
Larry Hastings2f936352014-08-05 14:04:04 +10008570
Ross Lagerwall7807c352011-03-17 20:20:30 +02008571#ifdef HAVE_WRITEV
Larry Hastings2f936352014-08-05 14:04:04 +10008572/*[clinic input]
8573os.writev -> Py_ssize_t
8574 fd: int
8575 buffers: object
8576 /
8577
8578Iterate over buffers, and write the contents of each to a file descriptor.
8579
8580Returns the total number of bytes written.
8581buffers must be a sequence of bytes-like objects.
8582[clinic start generated code]*/
8583
Larry Hastings2f936352014-08-05 14:04:04 +10008584static Py_ssize_t
8585os_writev_impl(PyModuleDef *module, int fd, PyObject *buffers)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008586/*[clinic end generated code: output=a48925dbf2d5c238 input=5b8d17fe4189d2fe]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008587{
8588 int cnt;
8589 Py_ssize_t result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008590 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008591 struct iovec *iov;
8592 Py_buffer *buf;
Larry Hastings2f936352014-08-05 14:04:04 +10008593
8594 if (!PySequence_Check(buffers)) {
Ross Lagerwall7807c352011-03-17 20:20:30 +02008595 PyErr_SetString(PyExc_TypeError,
8596 "writev() arg 2 must be a sequence");
Larry Hastings2f936352014-08-05 14:04:04 +10008597 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008598 }
Larry Hastings2f936352014-08-05 14:04:04 +10008599 cnt = PySequence_Size(buffers);
Ross Lagerwall7807c352011-03-17 20:20:30 +02008600
Larry Hastings2f936352014-08-05 14:04:04 +10008601 if (iov_setup(&iov, &buf, buffers, cnt, PyBUF_SIMPLE) < 0) {
8602 return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008603 }
8604
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008605 do {
8606 Py_BEGIN_ALLOW_THREADS
8607 result = writev(fd, iov, cnt);
8608 Py_END_ALLOW_THREADS
8609 } while (result < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Ross Lagerwall7807c352011-03-17 20:20:30 +02008610
8611 iov_cleanup(iov, buf, cnt);
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008612 if (result < 0 && !async_err)
Larry Hastings2f936352014-08-05 14:04:04 +10008613 posix_error();
Victor Stinner57ddf782014-01-08 15:21:28 +01008614
Georg Brandl306336b2012-06-24 12:55:33 +02008615 return result;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008616}
Larry Hastings2f936352014-08-05 14:04:04 +10008617#endif /* HAVE_WRITEV */
8618
8619
8620#ifdef HAVE_PWRITE
8621/*[clinic input]
8622os.pwrite -> Py_ssize_t
8623
8624 fd: int
8625 buffer: Py_buffer
8626 offset: Py_off_t
8627 /
8628
8629Write bytes to a file descriptor starting at a particular offset.
8630
8631Write buffer to fd, starting at offset bytes from the beginning of
8632the file. Returns the number of bytes writte. Does not change the
8633current file offset.
8634[clinic start generated code]*/
8635
Larry Hastings2f936352014-08-05 14:04:04 +10008636static Py_ssize_t
Larry Hastings89964c42015-04-14 18:07:59 -04008637os_pwrite_impl(PyModuleDef *module, int fd, Py_buffer *buffer,
8638 Py_off_t offset)
8639/*[clinic end generated code: output=93aabdb40e17d325 input=19903f1b3dd26377]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008640{
8641 Py_ssize_t size;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008642 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008643
8644 if (!_PyVerify_fd(fd)) {
8645 posix_error();
8646 return -1;
8647 }
8648
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008649 do {
8650 Py_BEGIN_ALLOW_THREADS
Steve Dower8fc89802015-04-12 00:26:27 -04008651 _Py_BEGIN_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008652 size = pwrite(fd, buffer->buf, (size_t)buffer->len, offset);
Steve Dower8fc89802015-04-12 00:26:27 -04008653 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008654 Py_END_ALLOW_THREADS
8655 } while (size < 0 && errno == EINTR && !(async_err = PyErr_CheckSignals()));
Larry Hastings2f936352014-08-05 14:04:04 +10008656
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008657 if (size < 0 && !async_err)
Larry Hastings2f936352014-08-05 14:04:04 +10008658 posix_error();
8659 return size;
8660}
8661#endif /* HAVE_PWRITE */
8662
8663
8664#ifdef HAVE_MKFIFO
8665/*[clinic input]
8666os.mkfifo
8667
8668 path: path_t
8669 mode: int=0o666
8670 *
8671 dir_fd: dir_fd(requires='mkfifoat')=None
8672
8673Create a "fifo" (a POSIX named pipe).
8674
8675If dir_fd is not None, it should be a file descriptor open to a directory,
8676 and path should be relative; path will then be relative to that directory.
8677dir_fd may not be implemented on your platform.
8678 If it is unavailable, using it will raise a NotImplementedError.
8679[clinic start generated code]*/
8680
Larry Hastings2f936352014-08-05 14:04:04 +10008681static PyObject *
8682os_mkfifo_impl(PyModuleDef *module, path_t *path, int mode, int dir_fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008683/*[clinic end generated code: output=8f5f5e72c630049a input=73032e98a36e0e19]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008684{
8685 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008686 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008687
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008688 do {
8689 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10008690#ifdef HAVE_MKFIFOAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008691 if (dir_fd != DEFAULT_DIR_FD)
8692 result = mkfifoat(dir_fd, path->narrow, mode);
8693 else
Ross Lagerwall7807c352011-03-17 20:20:30 +02008694#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008695 result = mkfifo(path->narrow, mode);
8696 Py_END_ALLOW_THREADS
8697 } while (result != 0 && errno == EINTR &&
8698 !(async_err = PyErr_CheckSignals()));
8699 if (result != 0)
8700 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008701
8702 Py_RETURN_NONE;
8703}
8704#endif /* HAVE_MKFIFO */
8705
8706
8707#if defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV)
8708/*[clinic input]
8709os.mknod
8710
8711 path: path_t
8712 mode: int=0o600
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008713 device: dev_t=0
Larry Hastings2f936352014-08-05 14:04:04 +10008714 *
8715 dir_fd: dir_fd(requires='mknodat')=None
8716
8717Create a node in the file system.
8718
8719Create a node in the file system (file, device special file or named pipe)
8720at path. mode specifies both the permissions to use and the
8721type of node to be created, being combined (bitwise OR) with one of
8722S_IFREG, S_IFCHR, S_IFBLK, and S_IFIFO. If S_IFCHR or S_IFBLK is set on mode,
8723device defines the newly created device special file (probably using
8724os.makedev()). Otherwise device is ignored.
8725
8726If dir_fd is not None, it should be a file descriptor open to a directory,
8727 and path should be relative; path will then be relative to that directory.
8728dir_fd may not be implemented on your platform.
8729 If it is unavailable, using it will raise a NotImplementedError.
8730[clinic start generated code]*/
8731
Larry Hastings2f936352014-08-05 14:04:04 +10008732static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008733os_mknod_impl(PyModuleDef *module, path_t *path, int mode, dev_t device,
8734 int dir_fd)
8735/*[clinic end generated code: output=5151a8a9f754d272 input=ee44531551a4d83b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008736{
8737 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008738 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008739
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008740 do {
8741 Py_BEGIN_ALLOW_THREADS
Larry Hastings2f936352014-08-05 14:04:04 +10008742#ifdef HAVE_MKNODAT
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008743 if (dir_fd != DEFAULT_DIR_FD)
8744 result = mknodat(dir_fd, path->narrow, mode, device);
8745 else
Larry Hastings2f936352014-08-05 14:04:04 +10008746#endif
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008747 result = mknod(path->narrow, mode, device);
8748 Py_END_ALLOW_THREADS
8749 } while (result != 0 && errno == EINTR &&
8750 !(async_err = PyErr_CheckSignals()));
8751 if (result != 0)
8752 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008753
8754 Py_RETURN_NONE;
8755}
8756#endif /* defined(HAVE_MKNOD) && defined(HAVE_MAKEDEV) */
8757
8758
8759#ifdef HAVE_DEVICE_MACROS
8760/*[clinic input]
8761os.major -> unsigned_int
8762
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008763 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008764 /
8765
8766Extracts a device major number from a raw device number.
8767[clinic start generated code]*/
8768
Larry Hastings2f936352014-08-05 14:04:04 +10008769static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008770os_major_impl(PyModuleDef *module, dev_t device)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008771/*[clinic end generated code: output=ba55693ab49bac34 input=1e16a4d30c4d4462]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008772{
8773 return major(device);
8774}
8775
8776
8777/*[clinic input]
8778os.minor -> unsigned_int
8779
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008780 device: dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008781 /
8782
8783Extracts a device minor number from a raw device number.
8784[clinic start generated code]*/
8785
Larry Hastings2f936352014-08-05 14:04:04 +10008786static unsigned int
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008787os_minor_impl(PyModuleDef *module, dev_t device)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008788/*[clinic end generated code: output=2867219ebf274e27 input=0842c6d23f24c65e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008789{
8790 return minor(device);
8791}
8792
8793
8794/*[clinic input]
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008795os.makedev -> dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008796
8797 major: int
8798 minor: int
8799 /
8800
8801Composes a raw device number from the major and minor device numbers.
8802[clinic start generated code]*/
8803
Serhiy Storchakaacdb7c12015-01-18 11:17:39 +02008804static dev_t
Larry Hastings2f936352014-08-05 14:04:04 +10008805os_makedev_impl(PyModuleDef *module, int major, int minor)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008806/*[clinic end generated code: output=7cb6264352437660 input=4b9fd8fc73cbe48f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008807{
8808 return makedev(major, minor);
8809}
8810#endif /* HAVE_DEVICE_MACROS */
8811
8812
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008813#if defined HAVE_FTRUNCATE || defined MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008814/*[clinic input]
8815os.ftruncate
8816
8817 fd: int
8818 length: Py_off_t
8819 /
8820
8821Truncate a file, specified by file descriptor, to a specific length.
8822[clinic start generated code]*/
8823
Larry Hastings2f936352014-08-05 14:04:04 +10008824static PyObject *
8825os_ftruncate_impl(PyModuleDef *module, int fd, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008826/*[clinic end generated code: output=3666f401d76bf834 input=63b43641e52818f2]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008827{
8828 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008829 int async_err = 0;
Larry Hastings2f936352014-08-05 14:04:04 +10008830
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008831 if (!_PyVerify_fd(fd))
8832 return posix_error();
8833
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008834 do {
8835 Py_BEGIN_ALLOW_THREADS
Steve Dowera1c7e722015-04-12 00:26:43 -04008836 _Py_BEGIN_SUPPRESS_IPH
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008837#ifdef MS_WINDOWS
8838 result = _chsize_s(fd, length);
8839#else
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008840 result = ftruncate(fd, length);
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008841#endif
Steve Dowera1c7e722015-04-12 00:26:43 -04008842 _Py_END_SUPPRESS_IPH
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008843 Py_END_ALLOW_THREADS
8844 } while (result != 0 && errno == EINTR &&
8845 !(async_err = PyErr_CheckSignals()));
8846 if (result != 0)
8847 return (!async_err) ? posix_error() : NULL;
Larry Hastings2f936352014-08-05 14:04:04 +10008848 Py_RETURN_NONE;
8849}
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008850#endif /* HAVE_FTRUNCATE || MS_WINDOWS */
Larry Hastings2f936352014-08-05 14:04:04 +10008851
8852
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008853#if defined HAVE_TRUNCATE || defined MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10008854/*[clinic input]
8855os.truncate
8856 path: path_t(allow_fd='PATH_HAVE_FTRUNCATE')
8857 length: Py_off_t
8858
8859Truncate a file, specified by path, to a specific length.
8860
8861On some platforms, path may also be specified as an open file descriptor.
8862 If this functionality is unavailable, using it raises an exception.
8863[clinic start generated code]*/
8864
Larry Hastings2f936352014-08-05 14:04:04 +10008865static PyObject *
8866os_truncate_impl(PyModuleDef *module, path_t *path, Py_off_t length)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03008867/*[clinic end generated code: output=f60a9e08370e9e2e input=77229cf0b50a9b77]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008868{
8869 int result;
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008870#ifdef MS_WINDOWS
8871 int fd;
8872#endif
8873
8874 if (path->fd != -1)
8875 return os_ftruncate_impl(module, path->fd, length);
Larry Hastings2f936352014-08-05 14:04:04 +10008876
8877 Py_BEGIN_ALLOW_THREADS
Steve Dowera1c7e722015-04-12 00:26:43 -04008878 _Py_BEGIN_SUPPRESS_IPH
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008879#ifdef MS_WINDOWS
8880 if (path->wide)
8881 fd = _wopen(path->wide, _O_WRONLY | _O_BINARY | _O_NOINHERIT);
Larry Hastings2f936352014-08-05 14:04:04 +10008882 else
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008883 fd = _open(path->narrow, _O_WRONLY | _O_BINARY | _O_NOINHERIT);
Victor Stinnercc0bbbc2015-04-25 00:21:52 +02008884 if (fd < 0)
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008885 result = -1;
8886 else {
8887 result = _chsize_s(fd, length);
8888 close(fd);
8889 if (result < 0)
8890 errno = result;
8891 }
8892#else
8893 result = truncate(path->narrow, length);
Larry Hastings2f936352014-08-05 14:04:04 +10008894#endif
Steve Dowera1c7e722015-04-12 00:26:43 -04008895 _Py_END_SUPPRESS_IPH
Larry Hastings2f936352014-08-05 14:04:04 +10008896 Py_END_ALLOW_THREADS
8897 if (result < 0)
8898 return path_error(path);
8899
8900 Py_RETURN_NONE;
8901}
Steve Dowerfe0a41a2015-03-20 19:50:46 -07008902#endif /* HAVE_TRUNCATE || MS_WINDOWS */
Larry Hastings2f936352014-08-05 14:04:04 +10008903
Ross Lagerwall7807c352011-03-17 20:20:30 +02008904
Victor Stinnerd6b17692014-09-30 12:20:05 +02008905/* Issue #22396: On 32-bit AIX platform, the prototypes of os.posix_fadvise()
8906 and os.posix_fallocate() in system headers are wrong if _LARGE_FILES is
8907 defined, which is the case in Python on AIX. AIX bug report:
8908 http://www-01.ibm.com/support/docview.wss?uid=isg1IV56170 */
8909#if defined(_AIX) && defined(_LARGE_FILES) && !defined(__64BIT__)
8910# define POSIX_FADVISE_AIX_BUG
8911#endif
8912
Victor Stinnerec39e262014-09-30 12:35:58 +02008913
Victor Stinnerd6b17692014-09-30 12:20:05 +02008914#if defined(HAVE_POSIX_FALLOCATE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +10008915/*[clinic input]
8916os.posix_fallocate
8917
8918 fd: int
8919 offset: Py_off_t
8920 length: Py_off_t
8921 /
8922
8923Ensure a file has allocated at least a particular number of bytes on disk.
8924
8925Ensure that the file specified by fd encompasses a range of bytes
8926starting at offset bytes from the beginning and continuing for length bytes.
8927[clinic start generated code]*/
8928
Larry Hastings2f936352014-08-05 14:04:04 +10008929static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008930os_posix_fallocate_impl(PyModuleDef *module, int fd, Py_off_t offset,
8931 Py_off_t length)
8932/*[clinic end generated code: output=7f6f87a8c751e1b4 input=d7a2ef0ab2ca52fb]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008933{
8934 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008935 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008936
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008937 do {
8938 Py_BEGIN_ALLOW_THREADS
8939 result = posix_fallocate(fd, offset, length);
8940 Py_END_ALLOW_THREADS
8941 } while (result != 0 && errno == EINTR &&
8942 !(async_err = PyErr_CheckSignals()));
8943 if (result != 0)
8944 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008945 Py_RETURN_NONE;
8946}
Victor Stinnerec39e262014-09-30 12:35:58 +02008947#endif /* HAVE_POSIX_FALLOCATE) && !POSIX_FADVISE_AIX_BUG */
Larry Hastings2f936352014-08-05 14:04:04 +10008948
Ross Lagerwall7807c352011-03-17 20:20:30 +02008949
Victor Stinnerd6b17692014-09-30 12:20:05 +02008950#if defined(HAVE_POSIX_FADVISE) && !defined(POSIX_FADVISE_AIX_BUG)
Larry Hastings2f936352014-08-05 14:04:04 +10008951/*[clinic input]
8952os.posix_fadvise
8953
8954 fd: int
8955 offset: Py_off_t
8956 length: Py_off_t
8957 advice: int
8958 /
8959
8960Announce an intention to access data in a specific pattern.
8961
8962Announce an intention to access data in a specific pattern, thus allowing
8963the kernel to make optimizations.
8964The advice applies to the region of the file specified by fd starting at
8965offset and continuing for length bytes.
8966advice is one of POSIX_FADV_NORMAL, POSIX_FADV_SEQUENTIAL,
8967POSIX_FADV_RANDOM, POSIX_FADV_NOREUSE, POSIX_FADV_WILLNEED, or
8968POSIX_FADV_DONTNEED.
8969[clinic start generated code]*/
8970
Larry Hastings2f936352014-08-05 14:04:04 +10008971static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -04008972os_posix_fadvise_impl(PyModuleDef *module, int fd, Py_off_t offset,
8973 Py_off_t length, int advice)
8974/*[clinic end generated code: output=457ce6a67189e10d input=0fbe554edc2f04b5]*/
Larry Hastings2f936352014-08-05 14:04:04 +10008975{
8976 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008977 int async_err = 0;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008978
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00008979 do {
8980 Py_BEGIN_ALLOW_THREADS
8981 result = posix_fadvise(fd, offset, length, advice);
8982 Py_END_ALLOW_THREADS
8983 } while (result != 0 && errno == EINTR &&
8984 !(async_err = PyErr_CheckSignals()));
8985 if (result != 0)
8986 return (!async_err) ? posix_error() : NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +02008987 Py_RETURN_NONE;
8988}
Victor Stinnerec39e262014-09-30 12:35:58 +02008989#endif /* HAVE_POSIX_FADVISE && !POSIX_FADVISE_AIX_BUG */
Ross Lagerwall7807c352011-03-17 20:20:30 +02008990
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00008991#ifdef HAVE_PUTENV
Guido van Rossumec4f4ac1997-06-02 22:20:51 +00008992
Fred Drake762e2061999-08-26 17:23:54 +00008993/* Save putenv() parameters as values here, so we can collect them when they
8994 * get re-set with another call for the same key. */
8995static PyObject *posix_putenv_garbage;
8996
Larry Hastings2f936352014-08-05 14:04:04 +10008997static void
8998posix_putenv_garbage_setitem(PyObject *name, PyObject *value)
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00008999{
Larry Hastings2f936352014-08-05 14:04:04 +10009000 /* Install the first arg and newstr in posix_putenv_garbage;
9001 * this will cause previous value to be collected. This has to
9002 * happen after the real putenv() call because the old value
9003 * was still accessible until then. */
9004 if (PyDict_SetItem(posix_putenv_garbage, name, value))
9005 /* really not much we can do; just leak */
9006 PyErr_Clear();
9007 else
9008 Py_DECREF(value);
9009}
9010
9011
Thomas Hellerf78f12a2007-11-08 19:33:05 +00009012#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10009013/*[clinic input]
9014os.putenv
9015
9016 name: unicode
9017 value: unicode
9018 /
9019
9020Change or add an environment variable.
9021[clinic start generated code]*/
9022
Larry Hastings2f936352014-08-05 14:04:04 +10009023static PyObject *
9024os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009025/*[clinic end generated code: output=a2438cf95e5a0c1c input=ba586581c2e6105f]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009026{
9027 wchar_t *env;
9028
9029 PyObject *unicode = PyUnicode_FromFormat("%U=%U", name, value);
9030 if (unicode == NULL) {
Victor Stinner84ae1182010-05-06 22:05:07 +00009031 PyErr_NoMemory();
Larry Hastings2f936352014-08-05 14:04:04 +10009032 return NULL;
Victor Stinner84ae1182010-05-06 22:05:07 +00009033 }
Larry Hastings2f936352014-08-05 14:04:04 +10009034 if (_MAX_ENV < PyUnicode_GET_LENGTH(unicode)) {
Victor Stinner65170952011-11-22 22:16:17 +01009035 PyErr_Format(PyExc_ValueError,
9036 "the environment variable is longer than %u characters",
9037 _MAX_ENV);
9038 goto error;
9039 }
9040
Larry Hastings2f936352014-08-05 14:04:04 +10009041 env = PyUnicode_AsUnicode(unicode);
9042 if (env == NULL)
Victor Stinnereb5657a2011-09-30 01:44:27 +02009043 goto error;
Larry Hastings2f936352014-08-05 14:04:04 +10009044 if (_wputenv(env)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009045 posix_error();
Victor Stinner84ae1182010-05-06 22:05:07 +00009046 goto error;
Victor Stinner8c62be82010-05-06 00:08:46 +00009047 }
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009048
Larry Hastings2f936352014-08-05 14:04:04 +10009049 posix_putenv_garbage_setitem(name, unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +00009050 Py_RETURN_NONE;
9051
9052error:
Larry Hastings2f936352014-08-05 14:04:04 +10009053 Py_DECREF(unicode);
Victor Stinner84ae1182010-05-06 22:05:07 +00009054 return NULL;
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009055}
Larry Hastings2f936352014-08-05 14:04:04 +10009056#else /* MS_WINDOWS */
9057/*[clinic input]
9058os.putenv
Guido van Rossumb6a47161997-09-15 22:54:34 +00009059
Larry Hastings2f936352014-08-05 14:04:04 +10009060 name: FSConverter
9061 value: FSConverter
9062 /
9063
9064Change or add an environment variable.
9065[clinic start generated code]*/
9066
Larry Hastings2f936352014-08-05 14:04:04 +10009067static PyObject *
9068os_putenv_impl(PyModuleDef *module, PyObject *name, PyObject *value)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009069/*[clinic end generated code: output=a2438cf95e5a0c1c input=a97bc6152f688d31]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009070{
9071 PyObject *bytes = NULL;
9072 char *env;
9073 char *name_string = PyBytes_AsString(name);
9074 char *value_string = PyBytes_AsString(value);
9075
9076 bytes = PyBytes_FromFormat("%s=%s", name_string, value_string);
9077 if (bytes == NULL) {
9078 PyErr_NoMemory();
9079 return NULL;
9080 }
9081
9082 env = PyBytes_AS_STRING(bytes);
9083 if (putenv(env)) {
9084 Py_DECREF(bytes);
9085 return posix_error();
9086 }
9087
9088 posix_putenv_garbage_setitem(name, bytes);
9089 Py_RETURN_NONE;
9090}
9091#endif /* MS_WINDOWS */
9092#endif /* HAVE_PUTENV */
9093
9094
9095#ifdef HAVE_UNSETENV
9096/*[clinic input]
9097os.unsetenv
9098 name: FSConverter
9099 /
9100
9101Delete an environment variable.
9102[clinic start generated code]*/
9103
Larry Hastings2f936352014-08-05 14:04:04 +10009104static PyObject *
9105os_unsetenv_impl(PyModuleDef *module, PyObject *name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009106/*[clinic end generated code: output=25994b57016a2dc9 input=2bb5288a599c7107]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009107{
Victor Stinner984890f2011-11-24 13:53:38 +01009108#ifndef HAVE_BROKEN_UNSETENV
Victor Stinner60b385e2011-11-22 22:01:28 +01009109 int err;
Victor Stinner984890f2011-11-24 13:53:38 +01009110#endif
Victor Stinner84ae1182010-05-06 22:05:07 +00009111
Victor Stinner984890f2011-11-24 13:53:38 +01009112#ifdef HAVE_BROKEN_UNSETENV
9113 unsetenv(PyBytes_AS_STRING(name));
9114#else
Victor Stinner65170952011-11-22 22:16:17 +01009115 err = unsetenv(PyBytes_AS_STRING(name));
Larry Hastings2f936352014-08-05 14:04:04 +10009116 if (err)
Victor Stinner60b385e2011-11-22 22:01:28 +01009117 return posix_error();
Victor Stinner984890f2011-11-24 13:53:38 +01009118#endif
Guido van Rossumc524d952001-10-19 01:31:59 +00009119
Victor Stinner8c62be82010-05-06 00:08:46 +00009120 /* Remove the key from posix_putenv_garbage;
9121 * this will cause it to be collected. This has to
9122 * happen after the real unsetenv() call because the
9123 * old value was still accessible until then.
9124 */
Victor Stinner65170952011-11-22 22:16:17 +01009125 if (PyDict_DelItem(posix_putenv_garbage, name)) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009126 /* really not much we can do; just leak */
9127 PyErr_Clear();
9128 }
Victor Stinner84ae1182010-05-06 22:05:07 +00009129 Py_RETURN_NONE;
Guido van Rossumc524d952001-10-19 01:31:59 +00009130}
Larry Hastings2f936352014-08-05 14:04:04 +10009131#endif /* HAVE_UNSETENV */
Guido van Rossumc524d952001-10-19 01:31:59 +00009132
Larry Hastings2f936352014-08-05 14:04:04 +10009133
9134/*[clinic input]
9135os.strerror
9136
9137 code: int
9138 /
9139
9140Translate an error code to a message string.
9141[clinic start generated code]*/
9142
Larry Hastings2f936352014-08-05 14:04:04 +10009143static PyObject *
9144os_strerror_impl(PyModuleDef *module, int code)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009145/*[clinic end generated code: output=0280c6af51e5c9fe input=75a8673d97915a91]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009146{
9147 char *message = strerror(code);
Victor Stinner8c62be82010-05-06 00:08:46 +00009148 if (message == NULL) {
9149 PyErr_SetString(PyExc_ValueError,
9150 "strerror() argument out of range");
9151 return NULL;
9152 }
Victor Stinner1b579672011-12-17 05:47:23 +01009153 return PyUnicode_DecodeLocale(message, "surrogateescape");
Guido van Rossumb6a47161997-09-15 22:54:34 +00009154}
Guido van Rossumb6a47161997-09-15 22:54:34 +00009155
Guido van Rossumf1af3fe1996-07-23 19:18:10 +00009156
Guido van Rossumc9641791998-08-04 15:26:23 +00009157#ifdef HAVE_SYS_WAIT_H
Fred Drake106c1a02002-04-23 15:58:02 +00009158#ifdef WCOREDUMP
Larry Hastings2f936352014-08-05 14:04:04 +10009159/*[clinic input]
9160os.WCOREDUMP -> bool
9161
9162 status: int
9163 /
9164
9165Return True if the process returning status was dumped to a core file.
9166[clinic start generated code]*/
9167
Larry Hastings2f936352014-08-05 14:04:04 +10009168static int
9169os_WCOREDUMP_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009170/*[clinic end generated code: output=134f70bbe63fbf41 input=8b05e7ab38528d04]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009171{
9172 WAIT_TYPE wait_status;
9173 WAIT_STATUS_INT(wait_status) = status;
9174 return WCOREDUMP(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +00009175}
9176#endif /* WCOREDUMP */
9177
Larry Hastings2f936352014-08-05 14:04:04 +10009178
Fred Drake106c1a02002-04-23 15:58:02 +00009179#ifdef WIFCONTINUED
Larry Hastings2f936352014-08-05 14:04:04 +10009180/*[clinic input]
9181os.WIFCONTINUED -> bool
9182
9183 status: int
9184
9185Return True if a particular process was continued from a job control stop.
9186
9187Return True if the process returning status was continued from a
9188job control stop.
9189[clinic start generated code]*/
9190
Larry Hastings2f936352014-08-05 14:04:04 +10009191static int
9192os_WIFCONTINUED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009193/*[clinic end generated code: output=9cdd26543ebb6dcd input=e777e7d38eb25bd9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009194{
9195 WAIT_TYPE wait_status;
9196 WAIT_STATUS_INT(wait_status) = status;
9197 return WIFCONTINUED(wait_status);
Fred Drake106c1a02002-04-23 15:58:02 +00009198}
9199#endif /* WIFCONTINUED */
9200
Larry Hastings2f936352014-08-05 14:04:04 +10009201
Guido van Rossumc9641791998-08-04 15:26:23 +00009202#ifdef WIFSTOPPED
Larry Hastings2f936352014-08-05 14:04:04 +10009203/*[clinic input]
9204os.WIFSTOPPED -> bool
9205
9206 status: int
9207
9208Return True if the process returning status was stopped.
9209[clinic start generated code]*/
9210
Larry Hastings2f936352014-08-05 14:04:04 +10009211static int
9212os_WIFSTOPPED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009213/*[clinic end generated code: output=73bf35e44994a724 input=043cb7f1289ef904]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009214{
9215 WAIT_TYPE wait_status;
9216 WAIT_STATUS_INT(wait_status) = status;
9217 return WIFSTOPPED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009218}
9219#endif /* WIFSTOPPED */
9220
Larry Hastings2f936352014-08-05 14:04:04 +10009221
Guido van Rossumc9641791998-08-04 15:26:23 +00009222#ifdef WIFSIGNALED
Larry Hastings2f936352014-08-05 14:04:04 +10009223/*[clinic input]
9224os.WIFSIGNALED -> bool
9225
9226 status: int
9227
9228Return True if the process returning status was terminated by a signal.
9229[clinic start generated code]*/
9230
Larry Hastings2f936352014-08-05 14:04:04 +10009231static int
9232os_WIFSIGNALED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009233/*[clinic end generated code: output=2697975771872420 input=d55ba7cc9ce5dc43]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009234{
9235 WAIT_TYPE wait_status;
9236 WAIT_STATUS_INT(wait_status) = status;
9237 return WIFSIGNALED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009238}
9239#endif /* WIFSIGNALED */
9240
Larry Hastings2f936352014-08-05 14:04:04 +10009241
Guido van Rossumc9641791998-08-04 15:26:23 +00009242#ifdef WIFEXITED
Larry Hastings2f936352014-08-05 14:04:04 +10009243/*[clinic input]
9244os.WIFEXITED -> bool
9245
9246 status: int
9247
9248Return True if the process returning status exited via the exit() system call.
9249[clinic start generated code]*/
9250
Larry Hastings2f936352014-08-05 14:04:04 +10009251static int
9252os_WIFEXITED_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009253/*[clinic end generated code: output=ca8f8c61f0b8532e input=d63775a6791586c0]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009254{
9255 WAIT_TYPE wait_status;
9256 WAIT_STATUS_INT(wait_status) = status;
9257 return WIFEXITED(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009258}
9259#endif /* WIFEXITED */
9260
Larry Hastings2f936352014-08-05 14:04:04 +10009261
Guido van Rossum54ecc3d1999-01-27 17:53:11 +00009262#ifdef WEXITSTATUS
Larry Hastings2f936352014-08-05 14:04:04 +10009263/*[clinic input]
9264os.WEXITSTATUS -> int
9265
9266 status: int
9267
9268Return the process return code from status.
9269[clinic start generated code]*/
9270
Larry Hastings2f936352014-08-05 14:04:04 +10009271static int
9272os_WEXITSTATUS_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009273/*[clinic end generated code: output=ea54da23d9e0f6af input=e1fb4944e377585b]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009274{
9275 WAIT_TYPE wait_status;
9276 WAIT_STATUS_INT(wait_status) = status;
9277 return WEXITSTATUS(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009278}
9279#endif /* WEXITSTATUS */
9280
Larry Hastings2f936352014-08-05 14:04:04 +10009281
Guido van Rossumc9641791998-08-04 15:26:23 +00009282#ifdef WTERMSIG
Larry Hastings2f936352014-08-05 14:04:04 +10009283/*[clinic input]
9284os.WTERMSIG -> int
9285
9286 status: int
9287
9288Return the signal that terminated the process that provided the status value.
9289[clinic start generated code]*/
9290
Larry Hastings2f936352014-08-05 14:04:04 +10009291static int
9292os_WTERMSIG_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009293/*[clinic end generated code: output=4d25367026cb852c input=727fd7f84ec3f243]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009294{
9295 WAIT_TYPE wait_status;
9296 WAIT_STATUS_INT(wait_status) = status;
9297 return WTERMSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009298}
9299#endif /* WTERMSIG */
9300
Larry Hastings2f936352014-08-05 14:04:04 +10009301
Guido van Rossumc9641791998-08-04 15:26:23 +00009302#ifdef WSTOPSIG
Larry Hastings2f936352014-08-05 14:04:04 +10009303/*[clinic input]
9304os.WSTOPSIG -> int
9305
9306 status: int
9307
9308Return the signal that stopped the process that provided the status value.
9309[clinic start generated code]*/
9310
Larry Hastings2f936352014-08-05 14:04:04 +10009311static int
9312os_WSTOPSIG_impl(PyModuleDef *module, int status)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009313/*[clinic end generated code: output=54eb9c13b001adb4 input=46ebf1d1b293c5c1]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009314{
9315 WAIT_TYPE wait_status;
9316 WAIT_STATUS_INT(wait_status) = status;
9317 return WSTOPSIG(wait_status);
Guido van Rossumc9641791998-08-04 15:26:23 +00009318}
9319#endif /* WSTOPSIG */
Guido van Rossumc9641791998-08-04 15:26:23 +00009320#endif /* HAVE_SYS_WAIT_H */
9321
9322
Thomas Wouters477c8d52006-05-27 19:21:47 +00009323#if defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossumd5753e11999-10-19 13:29:23 +00009324#ifdef _SCO_DS
9325/* SCO OpenServer 5.0 and later requires _SVID3 before it reveals the
9326 needed definitions in sys/statvfs.h */
9327#define _SVID3
9328#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +00009329#include <sys/statvfs.h>
9330
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009331static PyObject*
9332_pystatvfs_fromstructstatvfs(struct statvfs st) {
Victor Stinner8c62be82010-05-06 00:08:46 +00009333 PyObject *v = PyStructSequence_New(&StatVFSResultType);
9334 if (v == NULL)
9335 return NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009336
9337#if !defined(HAVE_LARGEFILE_SUPPORT)
Victor Stinner8c62be82010-05-06 00:08:46 +00009338 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
9339 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
9340 PyStructSequence_SET_ITEM(v, 2, PyLong_FromLong((long) st.f_blocks));
9341 PyStructSequence_SET_ITEM(v, 3, PyLong_FromLong((long) st.f_bfree));
9342 PyStructSequence_SET_ITEM(v, 4, PyLong_FromLong((long) st.f_bavail));
9343 PyStructSequence_SET_ITEM(v, 5, PyLong_FromLong((long) st.f_files));
9344 PyStructSequence_SET_ITEM(v, 6, PyLong_FromLong((long) st.f_ffree));
9345 PyStructSequence_SET_ITEM(v, 7, PyLong_FromLong((long) st.f_favail));
9346 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
9347 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009348#else
Victor Stinner8c62be82010-05-06 00:08:46 +00009349 PyStructSequence_SET_ITEM(v, 0, PyLong_FromLong((long) st.f_bsize));
9350 PyStructSequence_SET_ITEM(v, 1, PyLong_FromLong((long) st.f_frsize));
9351 PyStructSequence_SET_ITEM(v, 2,
9352 PyLong_FromLongLong((PY_LONG_LONG) st.f_blocks));
9353 PyStructSequence_SET_ITEM(v, 3,
9354 PyLong_FromLongLong((PY_LONG_LONG) st.f_bfree));
9355 PyStructSequence_SET_ITEM(v, 4,
9356 PyLong_FromLongLong((PY_LONG_LONG) st.f_bavail));
9357 PyStructSequence_SET_ITEM(v, 5,
9358 PyLong_FromLongLong((PY_LONG_LONG) st.f_files));
9359 PyStructSequence_SET_ITEM(v, 6,
9360 PyLong_FromLongLong((PY_LONG_LONG) st.f_ffree));
9361 PyStructSequence_SET_ITEM(v, 7,
9362 PyLong_FromLongLong((PY_LONG_LONG) st.f_favail));
9363 PyStructSequence_SET_ITEM(v, 8, PyLong_FromLong((long) st.f_flag));
9364 PyStructSequence_SET_ITEM(v, 9, PyLong_FromLong((long) st.f_namemax));
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009365#endif
Victor Stinnerf0a7bac2013-10-30 18:55:24 +01009366 if (PyErr_Occurred()) {
9367 Py_DECREF(v);
9368 return NULL;
9369 }
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009370
Victor Stinner8c62be82010-05-06 00:08:46 +00009371 return v;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009372}
9373
Larry Hastings2f936352014-08-05 14:04:04 +10009374
9375/*[clinic input]
9376os.fstatvfs
9377 fd: int
9378 /
9379
9380Perform an fstatvfs system call on the given fd.
9381
9382Equivalent to statvfs(fd).
9383[clinic start generated code]*/
9384
Larry Hastings2f936352014-08-05 14:04:04 +10009385static PyObject *
9386os_fstatvfs_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009387/*[clinic end generated code: output=584a94a754497ac0 input=d8122243ac50975e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009388{
9389 int result;
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009390 int async_err = 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009391 struct statvfs st;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009392
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009393 do {
9394 Py_BEGIN_ALLOW_THREADS
9395 result = fstatvfs(fd, &st);
9396 Py_END_ALLOW_THREADS
9397 } while (result != 0 && errno == EINTR &&
9398 !(async_err = PyErr_CheckSignals()));
Larry Hastings2f936352014-08-05 14:04:04 +10009399 if (result != 0)
Charles-François Natali6e6c59b2015-02-07 13:27:50 +00009400 return (!async_err) ? posix_error() : NULL;
Guido van Rossum98bf58f2001-10-18 20:34:25 +00009401
Victor Stinner8c62be82010-05-06 00:08:46 +00009402 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +00009403}
Larry Hastings2f936352014-08-05 14:04:04 +10009404#endif /* defined(HAVE_FSTATVFS) && defined(HAVE_SYS_STATVFS_H) */
Guido van Rossum94f6f721999-01-06 18:42:14 +00009405
9406
Thomas Wouters477c8d52006-05-27 19:21:47 +00009407#if defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H)
Guido van Rossum94f6f721999-01-06 18:42:14 +00009408#include <sys/statvfs.h>
Larry Hastings2f936352014-08-05 14:04:04 +10009409/*[clinic input]
9410os.statvfs
Guido van Rossum94f6f721999-01-06 18:42:14 +00009411
Larry Hastings2f936352014-08-05 14:04:04 +10009412 path: path_t(allow_fd='PATH_HAVE_FSTATVFS')
9413
9414Perform a statvfs system call on the given path.
9415
9416path may always be specified as a string.
9417On some platforms, path may also be specified as an open file descriptor.
9418 If this functionality is unavailable, using it raises an exception.
9419[clinic start generated code]*/
9420
Larry Hastings2f936352014-08-05 14:04:04 +10009421static PyObject *
9422os_statvfs_impl(PyModuleDef *module, path_t *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009423/*[clinic end generated code: output=5ced07a2cf931f41 input=3f5c35791c669bd9]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009424{
9425 int result;
9426 struct statvfs st;
Larry Hastings9cf065c2012-06-22 16:30:09 -07009427
9428 Py_BEGIN_ALLOW_THREADS
9429#ifdef HAVE_FSTATVFS
Larry Hastings2f936352014-08-05 14:04:04 +10009430 if (path->fd != -1) {
Larry Hastings9cf065c2012-06-22 16:30:09 -07009431#ifdef __APPLE__
9432 /* handle weak-linking on Mac OS X 10.3 */
9433 if (fstatvfs == NULL) {
Larry Hastings2f936352014-08-05 14:04:04 +10009434 fd_specified("statvfs", path->fd);
9435 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -07009436 }
9437#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009438 result = fstatvfs(path->fd, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009439 }
9440 else
9441#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009442 result = statvfs(path->narrow, &st);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009443 Py_END_ALLOW_THREADS
9444
9445 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +10009446 return path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -07009447 }
9448
Larry Hastings2f936352014-08-05 14:04:04 +10009449 return _pystatvfs_fromstructstatvfs(st);
Guido van Rossum94f6f721999-01-06 18:42:14 +00009450}
Larry Hastings2f936352014-08-05 14:04:04 +10009451#endif /* defined(HAVE_STATVFS) && defined(HAVE_SYS_STATVFS_H) */
9452
Guido van Rossum94f6f721999-01-06 18:42:14 +00009453
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009454#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +10009455/*[clinic input]
9456os._getdiskusage
9457
9458 path: Py_UNICODE
9459
9460Return disk usage statistics about the given path as a (total, free) tuple.
9461[clinic start generated code]*/
9462
Larry Hastings2f936352014-08-05 14:04:04 +10009463static PyObject *
9464os__getdiskusage_impl(PyModuleDef *module, Py_UNICODE *path)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009465/*[clinic end generated code: output=60a9cf33449db1dd input=6458133aed893c78]*/
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009466{
9467 BOOL retval;
9468 ULARGE_INTEGER _, total, free;
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009469
9470 Py_BEGIN_ALLOW_THREADS
Victor Stinner6139c1b2011-11-09 22:14:14 +01009471 retval = GetDiskFreeSpaceExW(path, &_, &total, &free);
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009472 Py_END_ALLOW_THREADS
9473 if (retval == 0)
9474 return PyErr_SetFromWindowsErr(0);
9475
9476 return Py_BuildValue("(LL)", total.QuadPart, free.QuadPart);
9477}
Larry Hastings2f936352014-08-05 14:04:04 +10009478#endif /* MS_WINDOWS */
Giampaolo Rodola'210e7ca2011-07-01 13:55:36 +02009479
9480
Fred Drakec9680921999-12-13 16:37:25 +00009481/* This is used for fpathconf(), pathconf(), confstr() and sysconf().
9482 * It maps strings representing configuration variable names to
9483 * integer values, allowing those functions to be called with the
Thomas Wouters7e474022000-07-16 12:04:32 +00009484 * magic names instead of polluting the module's namespace with tons of
Fred Drake12c6e2d1999-12-14 21:25:03 +00009485 * rarely-used constants. There are three separate tables that use
9486 * these definitions.
Fred Drakebec628d1999-12-15 18:31:10 +00009487 *
9488 * This code is always included, even if none of the interfaces that
9489 * need it are included. The #if hackery needed to avoid it would be
9490 * sufficiently pervasive that it's not worth the loss of readability.
Fred Drakec9680921999-12-13 16:37:25 +00009491 */
9492struct constdef {
Serhiy Storchaka2d06e842015-12-25 19:53:18 +02009493 const char *name;
Serhiy Storchaka56f6e762015-09-06 21:25:30 +03009494 int value;
Fred Drakec9680921999-12-13 16:37:25 +00009495};
9496
Fred Drake12c6e2d1999-12-14 21:25:03 +00009497static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009498conv_confname(PyObject *arg, int *valuep, struct constdef *table,
Guido van Rossum7d5baac2007-08-27 23:24:46 +00009499 size_t tablesize)
Fred Drake12c6e2d1999-12-14 21:25:03 +00009500{
Christian Heimes217cfd12007-12-02 14:31:20 +00009501 if (PyLong_Check(arg)) {
Serhiy Storchaka56f6e762015-09-06 21:25:30 +03009502 int value = _PyLong_AsInt(arg);
9503 if (value == -1 && PyErr_Occurred())
9504 return 0;
9505 *valuep = value;
Stefan Krah0e803b32010-11-26 16:16:47 +00009506 return 1;
Fred Drake12c6e2d1999-12-14 21:25:03 +00009507 }
Guido van Rossumbce56a62007-05-10 18:04:33 +00009508 else {
Stefan Krah0e803b32010-11-26 16:16:47 +00009509 /* look up the value in the table using a binary search */
9510 size_t lo = 0;
9511 size_t mid;
9512 size_t hi = tablesize;
9513 int cmp;
9514 const char *confname;
9515 if (!PyUnicode_Check(arg)) {
9516 PyErr_SetString(PyExc_TypeError,
9517 "configuration names must be strings or integers");
9518 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009519 }
Stefan Krah0e803b32010-11-26 16:16:47 +00009520 confname = _PyUnicode_AsString(arg);
9521 if (confname == NULL)
9522 return 0;
9523 while (lo < hi) {
9524 mid = (lo + hi) / 2;
9525 cmp = strcmp(confname, table[mid].name);
9526 if (cmp < 0)
9527 hi = mid;
9528 else if (cmp > 0)
9529 lo = mid + 1;
9530 else {
9531 *valuep = table[mid].value;
9532 return 1;
9533 }
9534 }
9535 PyErr_SetString(PyExc_ValueError, "unrecognized configuration name");
9536 return 0;
Victor Stinner8c62be82010-05-06 00:08:46 +00009537 }
Fred Drake12c6e2d1999-12-14 21:25:03 +00009538}
9539
9540
9541#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
9542static struct constdef posix_constants_pathconf[] = {
Fred Draked86ed291999-12-15 15:34:33 +00009543#ifdef _PC_ABI_AIO_XFER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009544 {"PC_ABI_AIO_XFER_MAX", _PC_ABI_AIO_XFER_MAX},
Fred Draked86ed291999-12-15 15:34:33 +00009545#endif
9546#ifdef _PC_ABI_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009547 {"PC_ABI_ASYNC_IO", _PC_ABI_ASYNC_IO},
Fred Draked86ed291999-12-15 15:34:33 +00009548#endif
Fred Drakec9680921999-12-13 16:37:25 +00009549#ifdef _PC_ASYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009550 {"PC_ASYNC_IO", _PC_ASYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009551#endif
9552#ifdef _PC_CHOWN_RESTRICTED
Victor Stinner8c62be82010-05-06 00:08:46 +00009553 {"PC_CHOWN_RESTRICTED", _PC_CHOWN_RESTRICTED},
Fred Drakec9680921999-12-13 16:37:25 +00009554#endif
9555#ifdef _PC_FILESIZEBITS
Victor Stinner8c62be82010-05-06 00:08:46 +00009556 {"PC_FILESIZEBITS", _PC_FILESIZEBITS},
Fred Drakec9680921999-12-13 16:37:25 +00009557#endif
9558#ifdef _PC_LAST
Victor Stinner8c62be82010-05-06 00:08:46 +00009559 {"PC_LAST", _PC_LAST},
Fred Drakec9680921999-12-13 16:37:25 +00009560#endif
9561#ifdef _PC_LINK_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009562 {"PC_LINK_MAX", _PC_LINK_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009563#endif
9564#ifdef _PC_MAX_CANON
Victor Stinner8c62be82010-05-06 00:08:46 +00009565 {"PC_MAX_CANON", _PC_MAX_CANON},
Fred Drakec9680921999-12-13 16:37:25 +00009566#endif
9567#ifdef _PC_MAX_INPUT
Victor Stinner8c62be82010-05-06 00:08:46 +00009568 {"PC_MAX_INPUT", _PC_MAX_INPUT},
Fred Drakec9680921999-12-13 16:37:25 +00009569#endif
9570#ifdef _PC_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009571 {"PC_NAME_MAX", _PC_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009572#endif
9573#ifdef _PC_NO_TRUNC
Victor Stinner8c62be82010-05-06 00:08:46 +00009574 {"PC_NO_TRUNC", _PC_NO_TRUNC},
Fred Drakec9680921999-12-13 16:37:25 +00009575#endif
9576#ifdef _PC_PATH_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009577 {"PC_PATH_MAX", _PC_PATH_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009578#endif
9579#ifdef _PC_PIPE_BUF
Victor Stinner8c62be82010-05-06 00:08:46 +00009580 {"PC_PIPE_BUF", _PC_PIPE_BUF},
Fred Drakec9680921999-12-13 16:37:25 +00009581#endif
9582#ifdef _PC_PRIO_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009583 {"PC_PRIO_IO", _PC_PRIO_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009584#endif
9585#ifdef _PC_SOCK_MAXBUF
Victor Stinner8c62be82010-05-06 00:08:46 +00009586 {"PC_SOCK_MAXBUF", _PC_SOCK_MAXBUF},
Fred Drakec9680921999-12-13 16:37:25 +00009587#endif
9588#ifdef _PC_SYNC_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009589 {"PC_SYNC_IO", _PC_SYNC_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009590#endif
9591#ifdef _PC_VDISABLE
Victor Stinner8c62be82010-05-06 00:08:46 +00009592 {"PC_VDISABLE", _PC_VDISABLE},
Fred Drakec9680921999-12-13 16:37:25 +00009593#endif
Jesus Cea7e9065c2010-10-25 13:02:04 +00009594#ifdef _PC_ACL_ENABLED
9595 {"PC_ACL_ENABLED", _PC_ACL_ENABLED},
9596#endif
9597#ifdef _PC_MIN_HOLE_SIZE
9598 {"PC_MIN_HOLE_SIZE", _PC_MIN_HOLE_SIZE},
9599#endif
9600#ifdef _PC_ALLOC_SIZE_MIN
9601 {"PC_ALLOC_SIZE_MIN", _PC_ALLOC_SIZE_MIN},
9602#endif
9603#ifdef _PC_REC_INCR_XFER_SIZE
9604 {"PC_REC_INCR_XFER_SIZE", _PC_REC_INCR_XFER_SIZE},
9605#endif
9606#ifdef _PC_REC_MAX_XFER_SIZE
9607 {"PC_REC_MAX_XFER_SIZE", _PC_REC_MAX_XFER_SIZE},
9608#endif
9609#ifdef _PC_REC_MIN_XFER_SIZE
9610 {"PC_REC_MIN_XFER_SIZE", _PC_REC_MIN_XFER_SIZE},
9611#endif
9612#ifdef _PC_REC_XFER_ALIGN
9613 {"PC_REC_XFER_ALIGN", _PC_REC_XFER_ALIGN},
9614#endif
9615#ifdef _PC_SYMLINK_MAX
9616 {"PC_SYMLINK_MAX", _PC_SYMLINK_MAX},
9617#endif
9618#ifdef _PC_XATTR_ENABLED
9619 {"PC_XATTR_ENABLED", _PC_XATTR_ENABLED},
9620#endif
9621#ifdef _PC_XATTR_EXISTS
9622 {"PC_XATTR_EXISTS", _PC_XATTR_EXISTS},
9623#endif
9624#ifdef _PC_TIMESTAMP_RESOLUTION
9625 {"PC_TIMESTAMP_RESOLUTION", _PC_TIMESTAMP_RESOLUTION},
9626#endif
Fred Drakec9680921999-12-13 16:37:25 +00009627};
9628
Fred Drakec9680921999-12-13 16:37:25 +00009629static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009630conv_path_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +00009631{
9632 return conv_confname(arg, valuep, posix_constants_pathconf,
9633 sizeof(posix_constants_pathconf)
9634 / sizeof(struct constdef));
9635}
9636#endif
9637
Larry Hastings2f936352014-08-05 14:04:04 +10009638
Fred Drakec9680921999-12-13 16:37:25 +00009639#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009640/*[clinic input]
9641os.fpathconf -> long
9642
9643 fd: int
9644 name: path_confname
9645 /
9646
9647Return the configuration limit name for the file descriptor fd.
9648
9649If there is no limit, return -1.
9650[clinic start generated code]*/
9651
Larry Hastings2f936352014-08-05 14:04:04 +10009652static long
9653os_fpathconf_impl(PyModuleDef *module, int fd, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009654/*[clinic end generated code: output=082b2922d4441de7 input=5942a024d3777810]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009655{
9656 long limit;
9657
9658 errno = 0;
9659 limit = fpathconf(fd, name);
9660 if (limit == -1 && errno != 0)
9661 posix_error();
9662
9663 return limit;
9664}
9665#endif /* HAVE_FPATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +00009666
9667
9668#ifdef HAVE_PATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009669/*[clinic input]
9670os.pathconf -> long
9671 path: path_t(allow_fd='PATH_HAVE_FPATHCONF')
9672 name: path_confname
9673
9674Return the configuration limit name for the file or directory path.
9675
9676If there is no limit, return -1.
9677On some platforms, path may also be specified as an open file descriptor.
9678 If this functionality is unavailable, using it raises an exception.
9679[clinic start generated code]*/
9680
Larry Hastings2f936352014-08-05 14:04:04 +10009681static long
9682os_pathconf_impl(PyModuleDef *module, path_t *path, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009683/*[clinic end generated code: output=3713029e9501f5ab input=bc3e2a985af27e5e]*/
Larry Hastings2f936352014-08-05 14:04:04 +10009684{
Victor Stinner8c62be82010-05-06 00:08:46 +00009685 long limit;
Fred Drakec9680921999-12-13 16:37:25 +00009686
Victor Stinner8c62be82010-05-06 00:08:46 +00009687 errno = 0;
Georg Brandl306336b2012-06-24 12:55:33 +02009688#ifdef HAVE_FPATHCONF
Larry Hastings2f936352014-08-05 14:04:04 +10009689 if (path->fd != -1)
9690 limit = fpathconf(path->fd, name);
Georg Brandl306336b2012-06-24 12:55:33 +02009691 else
9692#endif
Larry Hastings2f936352014-08-05 14:04:04 +10009693 limit = pathconf(path->narrow, name);
Victor Stinner8c62be82010-05-06 00:08:46 +00009694 if (limit == -1 && errno != 0) {
9695 if (errno == EINVAL)
Stefan Krah99439262010-11-26 12:58:05 +00009696 /* could be a path or name problem */
9697 posix_error();
Fred Drakec9680921999-12-13 16:37:25 +00009698 else
Larry Hastings2f936352014-08-05 14:04:04 +10009699 path_error(path);
Victor Stinner8c62be82010-05-06 00:08:46 +00009700 }
Larry Hastings2f936352014-08-05 14:04:04 +10009701
9702 return limit;
Fred Drakec9680921999-12-13 16:37:25 +00009703}
Larry Hastings2f936352014-08-05 14:04:04 +10009704#endif /* HAVE_PATHCONF */
Fred Drakec9680921999-12-13 16:37:25 +00009705
9706#ifdef HAVE_CONFSTR
9707static struct constdef posix_constants_confstr[] = {
Fred Draked86ed291999-12-15 15:34:33 +00009708#ifdef _CS_ARCHITECTURE
Victor Stinner8c62be82010-05-06 00:08:46 +00009709 {"CS_ARCHITECTURE", _CS_ARCHITECTURE},
Fred Draked86ed291999-12-15 15:34:33 +00009710#endif
Mark Dickinson876d7c82010-04-16 12:47:52 +00009711#ifdef _CS_GNU_LIBC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009712 {"CS_GNU_LIBC_VERSION", _CS_GNU_LIBC_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +00009713#endif
9714#ifdef _CS_GNU_LIBPTHREAD_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009715 {"CS_GNU_LIBPTHREAD_VERSION", _CS_GNU_LIBPTHREAD_VERSION},
Mark Dickinson876d7c82010-04-16 12:47:52 +00009716#endif
Fred Draked86ed291999-12-15 15:34:33 +00009717#ifdef _CS_HOSTNAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009718 {"CS_HOSTNAME", _CS_HOSTNAME},
Fred Draked86ed291999-12-15 15:34:33 +00009719#endif
9720#ifdef _CS_HW_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +00009721 {"CS_HW_PROVIDER", _CS_HW_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +00009722#endif
9723#ifdef _CS_HW_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +00009724 {"CS_HW_SERIAL", _CS_HW_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +00009725#endif
9726#ifdef _CS_INITTAB_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009727 {"CS_INITTAB_NAME", _CS_INITTAB_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009728#endif
Fred Drakec9680921999-12-13 16:37:25 +00009729#ifdef _CS_LFS64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009730 {"CS_LFS64_CFLAGS", _CS_LFS64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009731#endif
9732#ifdef _CS_LFS64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009733 {"CS_LFS64_LDFLAGS", _CS_LFS64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009734#endif
9735#ifdef _CS_LFS64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009736 {"CS_LFS64_LIBS", _CS_LFS64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009737#endif
9738#ifdef _CS_LFS64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009739 {"CS_LFS64_LINTFLAGS", _CS_LFS64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009740#endif
9741#ifdef _CS_LFS_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009742 {"CS_LFS_CFLAGS", _CS_LFS_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009743#endif
9744#ifdef _CS_LFS_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009745 {"CS_LFS_LDFLAGS", _CS_LFS_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009746#endif
9747#ifdef _CS_LFS_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009748 {"CS_LFS_LIBS", _CS_LFS_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009749#endif
9750#ifdef _CS_LFS_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009751 {"CS_LFS_LINTFLAGS", _CS_LFS_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009752#endif
Fred Draked86ed291999-12-15 15:34:33 +00009753#ifdef _CS_MACHINE
Victor Stinner8c62be82010-05-06 00:08:46 +00009754 {"CS_MACHINE", _CS_MACHINE},
Fred Draked86ed291999-12-15 15:34:33 +00009755#endif
Fred Drakec9680921999-12-13 16:37:25 +00009756#ifdef _CS_PATH
Victor Stinner8c62be82010-05-06 00:08:46 +00009757 {"CS_PATH", _CS_PATH},
Fred Drakec9680921999-12-13 16:37:25 +00009758#endif
Fred Draked86ed291999-12-15 15:34:33 +00009759#ifdef _CS_RELEASE
Victor Stinner8c62be82010-05-06 00:08:46 +00009760 {"CS_RELEASE", _CS_RELEASE},
Fred Draked86ed291999-12-15 15:34:33 +00009761#endif
9762#ifdef _CS_SRPC_DOMAIN
Victor Stinner8c62be82010-05-06 00:08:46 +00009763 {"CS_SRPC_DOMAIN", _CS_SRPC_DOMAIN},
Fred Draked86ed291999-12-15 15:34:33 +00009764#endif
9765#ifdef _CS_SYSNAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009766 {"CS_SYSNAME", _CS_SYSNAME},
Fred Draked86ed291999-12-15 15:34:33 +00009767#endif
9768#ifdef _CS_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009769 {"CS_VERSION", _CS_VERSION},
Fred Draked86ed291999-12-15 15:34:33 +00009770#endif
Fred Drakec9680921999-12-13 16:37:25 +00009771#ifdef _CS_XBS5_ILP32_OFF32_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009772 {"CS_XBS5_ILP32_OFF32_CFLAGS", _CS_XBS5_ILP32_OFF32_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009773#endif
9774#ifdef _CS_XBS5_ILP32_OFF32_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009775 {"CS_XBS5_ILP32_OFF32_LDFLAGS", _CS_XBS5_ILP32_OFF32_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009776#endif
9777#ifdef _CS_XBS5_ILP32_OFF32_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009778 {"CS_XBS5_ILP32_OFF32_LIBS", _CS_XBS5_ILP32_OFF32_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009779#endif
9780#ifdef _CS_XBS5_ILP32_OFF32_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009781 {"CS_XBS5_ILP32_OFF32_LINTFLAGS", _CS_XBS5_ILP32_OFF32_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009782#endif
9783#ifdef _CS_XBS5_ILP32_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009784 {"CS_XBS5_ILP32_OFFBIG_CFLAGS", _CS_XBS5_ILP32_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009785#endif
9786#ifdef _CS_XBS5_ILP32_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009787 {"CS_XBS5_ILP32_OFFBIG_LDFLAGS", _CS_XBS5_ILP32_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009788#endif
9789#ifdef _CS_XBS5_ILP32_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009790 {"CS_XBS5_ILP32_OFFBIG_LIBS", _CS_XBS5_ILP32_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009791#endif
9792#ifdef _CS_XBS5_ILP32_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009793 {"CS_XBS5_ILP32_OFFBIG_LINTFLAGS", _CS_XBS5_ILP32_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009794#endif
9795#ifdef _CS_XBS5_LP64_OFF64_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009796 {"CS_XBS5_LP64_OFF64_CFLAGS", _CS_XBS5_LP64_OFF64_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009797#endif
9798#ifdef _CS_XBS5_LP64_OFF64_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009799 {"CS_XBS5_LP64_OFF64_LDFLAGS", _CS_XBS5_LP64_OFF64_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009800#endif
9801#ifdef _CS_XBS5_LP64_OFF64_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009802 {"CS_XBS5_LP64_OFF64_LIBS", _CS_XBS5_LP64_OFF64_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009803#endif
9804#ifdef _CS_XBS5_LP64_OFF64_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009805 {"CS_XBS5_LP64_OFF64_LINTFLAGS", _CS_XBS5_LP64_OFF64_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009806#endif
9807#ifdef _CS_XBS5_LPBIG_OFFBIG_CFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009808 {"CS_XBS5_LPBIG_OFFBIG_CFLAGS", _CS_XBS5_LPBIG_OFFBIG_CFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009809#endif
9810#ifdef _CS_XBS5_LPBIG_OFFBIG_LDFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009811 {"CS_XBS5_LPBIG_OFFBIG_LDFLAGS", _CS_XBS5_LPBIG_OFFBIG_LDFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009812#endif
9813#ifdef _CS_XBS5_LPBIG_OFFBIG_LIBS
Victor Stinner8c62be82010-05-06 00:08:46 +00009814 {"CS_XBS5_LPBIG_OFFBIG_LIBS", _CS_XBS5_LPBIG_OFFBIG_LIBS},
Fred Drakec9680921999-12-13 16:37:25 +00009815#endif
9816#ifdef _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS
Victor Stinner8c62be82010-05-06 00:08:46 +00009817 {"CS_XBS5_LPBIG_OFFBIG_LINTFLAGS", _CS_XBS5_LPBIG_OFFBIG_LINTFLAGS},
Fred Drakec9680921999-12-13 16:37:25 +00009818#endif
Fred Draked86ed291999-12-15 15:34:33 +00009819#ifdef _MIPS_CS_AVAIL_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009820 {"MIPS_CS_AVAIL_PROCESSORS", _MIPS_CS_AVAIL_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009821#endif
9822#ifdef _MIPS_CS_BASE
Victor Stinner8c62be82010-05-06 00:08:46 +00009823 {"MIPS_CS_BASE", _MIPS_CS_BASE},
Fred Draked86ed291999-12-15 15:34:33 +00009824#endif
9825#ifdef _MIPS_CS_HOSTID
Victor Stinner8c62be82010-05-06 00:08:46 +00009826 {"MIPS_CS_HOSTID", _MIPS_CS_HOSTID},
Fred Draked86ed291999-12-15 15:34:33 +00009827#endif
9828#ifdef _MIPS_CS_HW_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009829 {"MIPS_CS_HW_NAME", _MIPS_CS_HW_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009830#endif
9831#ifdef _MIPS_CS_NUM_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009832 {"MIPS_CS_NUM_PROCESSORS", _MIPS_CS_NUM_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009833#endif
9834#ifdef _MIPS_CS_OSREL_MAJ
Victor Stinner8c62be82010-05-06 00:08:46 +00009835 {"MIPS_CS_OSREL_MAJ", _MIPS_CS_OSREL_MAJ},
Fred Draked86ed291999-12-15 15:34:33 +00009836#endif
9837#ifdef _MIPS_CS_OSREL_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +00009838 {"MIPS_CS_OSREL_MIN", _MIPS_CS_OSREL_MIN},
Fred Draked86ed291999-12-15 15:34:33 +00009839#endif
9840#ifdef _MIPS_CS_OSREL_PATCH
Victor Stinner8c62be82010-05-06 00:08:46 +00009841 {"MIPS_CS_OSREL_PATCH", _MIPS_CS_OSREL_PATCH},
Fred Draked86ed291999-12-15 15:34:33 +00009842#endif
9843#ifdef _MIPS_CS_OS_NAME
Victor Stinner8c62be82010-05-06 00:08:46 +00009844 {"MIPS_CS_OS_NAME", _MIPS_CS_OS_NAME},
Fred Draked86ed291999-12-15 15:34:33 +00009845#endif
9846#ifdef _MIPS_CS_OS_PROVIDER
Victor Stinner8c62be82010-05-06 00:08:46 +00009847 {"MIPS_CS_OS_PROVIDER", _MIPS_CS_OS_PROVIDER},
Fred Draked86ed291999-12-15 15:34:33 +00009848#endif
9849#ifdef _MIPS_CS_PROCESSORS
Victor Stinner8c62be82010-05-06 00:08:46 +00009850 {"MIPS_CS_PROCESSORS", _MIPS_CS_PROCESSORS},
Fred Draked86ed291999-12-15 15:34:33 +00009851#endif
9852#ifdef _MIPS_CS_SERIAL
Victor Stinner8c62be82010-05-06 00:08:46 +00009853 {"MIPS_CS_SERIAL", _MIPS_CS_SERIAL},
Fred Draked86ed291999-12-15 15:34:33 +00009854#endif
9855#ifdef _MIPS_CS_VENDOR
Victor Stinner8c62be82010-05-06 00:08:46 +00009856 {"MIPS_CS_VENDOR", _MIPS_CS_VENDOR},
Fred Draked86ed291999-12-15 15:34:33 +00009857#endif
Fred Drakec9680921999-12-13 16:37:25 +00009858};
9859
9860static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +00009861conv_confstr_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +00009862{
9863 return conv_confname(arg, valuep, posix_constants_confstr,
9864 sizeof(posix_constants_confstr)
9865 / sizeof(struct constdef));
9866}
9867
Larry Hastings2f936352014-08-05 14:04:04 +10009868
9869/*[clinic input]
9870os.confstr
9871
9872 name: confstr_confname
9873 /
9874
9875Return a string-valued system configuration variable.
9876[clinic start generated code]*/
9877
Larry Hastings2f936352014-08-05 14:04:04 +10009878static PyObject *
9879os_confstr_impl(PyModuleDef *module, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +03009880/*[clinic end generated code: output=6ff79c9eed8c2daf input=18fb4d0567242e65]*/
Fred Drakec9680921999-12-13 16:37:25 +00009881{
9882 PyObject *result = NULL;
Victor Stinnercb043522010-09-10 23:49:04 +00009883 char buffer[255];
Victor Stinnerdd3a6a52013-06-25 23:13:47 +02009884 size_t len;
Fred Drakec9680921999-12-13 16:37:25 +00009885
Victor Stinnercb043522010-09-10 23:49:04 +00009886 errno = 0;
9887 len = confstr(name, buffer, sizeof(buffer));
9888 if (len == 0) {
9889 if (errno) {
9890 posix_error();
9891 return NULL;
Fred Drakec9680921999-12-13 16:37:25 +00009892 }
9893 else {
Victor Stinnercb043522010-09-10 23:49:04 +00009894 Py_RETURN_NONE;
Fred Drakec9680921999-12-13 16:37:25 +00009895 }
9896 }
Victor Stinnercb043522010-09-10 23:49:04 +00009897
Victor Stinnerdd3a6a52013-06-25 23:13:47 +02009898 if (len >= sizeof(buffer)) {
Victor Stinnercbc18f32014-12-05 22:51:51 +01009899 size_t len2;
Victor Stinnercb043522010-09-10 23:49:04 +00009900 char *buf = PyMem_Malloc(len);
9901 if (buf == NULL)
9902 return PyErr_NoMemory();
Victor Stinnercbc18f32014-12-05 22:51:51 +01009903 len2 = confstr(name, buf, len);
9904 assert(len == len2);
Christian Heimes8714cfd2015-04-21 10:57:41 +02009905 result = PyUnicode_DecodeFSDefaultAndSize(buf, len2-1);
Victor Stinnercb043522010-09-10 23:49:04 +00009906 PyMem_Free(buf);
9907 }
9908 else
9909 result = PyUnicode_DecodeFSDefaultAndSize(buffer, len-1);
Fred Drakec9680921999-12-13 16:37:25 +00009910 return result;
9911}
Larry Hastings2f936352014-08-05 14:04:04 +10009912#endif /* HAVE_CONFSTR */
Fred Drakec9680921999-12-13 16:37:25 +00009913
9914
9915#ifdef HAVE_SYSCONF
9916static struct constdef posix_constants_sysconf[] = {
9917#ifdef _SC_2_CHAR_TERM
Victor Stinner8c62be82010-05-06 00:08:46 +00009918 {"SC_2_CHAR_TERM", _SC_2_CHAR_TERM},
Fred Drakec9680921999-12-13 16:37:25 +00009919#endif
9920#ifdef _SC_2_C_BIND
Victor Stinner8c62be82010-05-06 00:08:46 +00009921 {"SC_2_C_BIND", _SC_2_C_BIND},
Fred Drakec9680921999-12-13 16:37:25 +00009922#endif
9923#ifdef _SC_2_C_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009924 {"SC_2_C_DEV", _SC_2_C_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009925#endif
9926#ifdef _SC_2_C_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009927 {"SC_2_C_VERSION", _SC_2_C_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +00009928#endif
9929#ifdef _SC_2_FORT_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009930 {"SC_2_FORT_DEV", _SC_2_FORT_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009931#endif
9932#ifdef _SC_2_FORT_RUN
Victor Stinner8c62be82010-05-06 00:08:46 +00009933 {"SC_2_FORT_RUN", _SC_2_FORT_RUN},
Fred Drakec9680921999-12-13 16:37:25 +00009934#endif
9935#ifdef _SC_2_LOCALEDEF
Victor Stinner8c62be82010-05-06 00:08:46 +00009936 {"SC_2_LOCALEDEF", _SC_2_LOCALEDEF},
Fred Drakec9680921999-12-13 16:37:25 +00009937#endif
9938#ifdef _SC_2_SW_DEV
Victor Stinner8c62be82010-05-06 00:08:46 +00009939 {"SC_2_SW_DEV", _SC_2_SW_DEV},
Fred Drakec9680921999-12-13 16:37:25 +00009940#endif
9941#ifdef _SC_2_UPE
Victor Stinner8c62be82010-05-06 00:08:46 +00009942 {"SC_2_UPE", _SC_2_UPE},
Fred Drakec9680921999-12-13 16:37:25 +00009943#endif
9944#ifdef _SC_2_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +00009945 {"SC_2_VERSION", _SC_2_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +00009946#endif
Fred Draked86ed291999-12-15 15:34:33 +00009947#ifdef _SC_ABI_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009948 {"SC_ABI_ASYNCHRONOUS_IO", _SC_ABI_ASYNCHRONOUS_IO},
Fred Draked86ed291999-12-15 15:34:33 +00009949#endif
9950#ifdef _SC_ACL
Victor Stinner8c62be82010-05-06 00:08:46 +00009951 {"SC_ACL", _SC_ACL},
Fred Draked86ed291999-12-15 15:34:33 +00009952#endif
Fred Drakec9680921999-12-13 16:37:25 +00009953#ifdef _SC_AIO_LISTIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009954 {"SC_AIO_LISTIO_MAX", _SC_AIO_LISTIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009955#endif
Fred Drakec9680921999-12-13 16:37:25 +00009956#ifdef _SC_AIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009957 {"SC_AIO_MAX", _SC_AIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009958#endif
9959#ifdef _SC_AIO_PRIO_DELTA_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009960 {"SC_AIO_PRIO_DELTA_MAX", _SC_AIO_PRIO_DELTA_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009961#endif
9962#ifdef _SC_ARG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009963 {"SC_ARG_MAX", _SC_ARG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009964#endif
9965#ifdef _SC_ASYNCHRONOUS_IO
Victor Stinner8c62be82010-05-06 00:08:46 +00009966 {"SC_ASYNCHRONOUS_IO", _SC_ASYNCHRONOUS_IO},
Fred Drakec9680921999-12-13 16:37:25 +00009967#endif
9968#ifdef _SC_ATEXIT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009969 {"SC_ATEXIT_MAX", _SC_ATEXIT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009970#endif
Fred Draked86ed291999-12-15 15:34:33 +00009971#ifdef _SC_AUDIT
Victor Stinner8c62be82010-05-06 00:08:46 +00009972 {"SC_AUDIT", _SC_AUDIT},
Fred Draked86ed291999-12-15 15:34:33 +00009973#endif
Fred Drakec9680921999-12-13 16:37:25 +00009974#ifdef _SC_AVPHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +00009975 {"SC_AVPHYS_PAGES", _SC_AVPHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +00009976#endif
9977#ifdef _SC_BC_BASE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009978 {"SC_BC_BASE_MAX", _SC_BC_BASE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009979#endif
9980#ifdef _SC_BC_DIM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009981 {"SC_BC_DIM_MAX", _SC_BC_DIM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009982#endif
9983#ifdef _SC_BC_SCALE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009984 {"SC_BC_SCALE_MAX", _SC_BC_SCALE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009985#endif
9986#ifdef _SC_BC_STRING_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009987 {"SC_BC_STRING_MAX", _SC_BC_STRING_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009988#endif
Fred Draked86ed291999-12-15 15:34:33 +00009989#ifdef _SC_CAP
Victor Stinner8c62be82010-05-06 00:08:46 +00009990 {"SC_CAP", _SC_CAP},
Fred Draked86ed291999-12-15 15:34:33 +00009991#endif
Fred Drakec9680921999-12-13 16:37:25 +00009992#ifdef _SC_CHARCLASS_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009993 {"SC_CHARCLASS_NAME_MAX", _SC_CHARCLASS_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +00009994#endif
9995#ifdef _SC_CHAR_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +00009996 {"SC_CHAR_BIT", _SC_CHAR_BIT},
Fred Drakec9680921999-12-13 16:37:25 +00009997#endif
9998#ifdef _SC_CHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +00009999 {"SC_CHAR_MAX", _SC_CHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010000#endif
10001#ifdef _SC_CHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010002 {"SC_CHAR_MIN", _SC_CHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010003#endif
10004#ifdef _SC_CHILD_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010005 {"SC_CHILD_MAX", _SC_CHILD_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010006#endif
10007#ifdef _SC_CLK_TCK
Victor Stinner8c62be82010-05-06 00:08:46 +000010008 {"SC_CLK_TCK", _SC_CLK_TCK},
Fred Drakec9680921999-12-13 16:37:25 +000010009#endif
10010#ifdef _SC_COHER_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010011 {"SC_COHER_BLKSZ", _SC_COHER_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010012#endif
10013#ifdef _SC_COLL_WEIGHTS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010014 {"SC_COLL_WEIGHTS_MAX", _SC_COLL_WEIGHTS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010015#endif
10016#ifdef _SC_DCACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000010017 {"SC_DCACHE_ASSOC", _SC_DCACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000010018#endif
10019#ifdef _SC_DCACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010020 {"SC_DCACHE_BLKSZ", _SC_DCACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010021#endif
10022#ifdef _SC_DCACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010023 {"SC_DCACHE_LINESZ", _SC_DCACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000010024#endif
10025#ifdef _SC_DCACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010026 {"SC_DCACHE_SZ", _SC_DCACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000010027#endif
10028#ifdef _SC_DCACHE_TBLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010029 {"SC_DCACHE_TBLKSZ", _SC_DCACHE_TBLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010030#endif
10031#ifdef _SC_DELAYTIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010032 {"SC_DELAYTIMER_MAX", _SC_DELAYTIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010033#endif
10034#ifdef _SC_EQUIV_CLASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010035 {"SC_EQUIV_CLASS_MAX", _SC_EQUIV_CLASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010036#endif
10037#ifdef _SC_EXPR_NEST_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010038 {"SC_EXPR_NEST_MAX", _SC_EXPR_NEST_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010039#endif
10040#ifdef _SC_FSYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000010041 {"SC_FSYNC", _SC_FSYNC},
Fred Drakec9680921999-12-13 16:37:25 +000010042#endif
10043#ifdef _SC_GETGR_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010044 {"SC_GETGR_R_SIZE_MAX", _SC_GETGR_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010045#endif
10046#ifdef _SC_GETPW_R_SIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010047 {"SC_GETPW_R_SIZE_MAX", _SC_GETPW_R_SIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010048#endif
10049#ifdef _SC_ICACHE_ASSOC
Victor Stinner8c62be82010-05-06 00:08:46 +000010050 {"SC_ICACHE_ASSOC", _SC_ICACHE_ASSOC},
Fred Drakec9680921999-12-13 16:37:25 +000010051#endif
10052#ifdef _SC_ICACHE_BLKSZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010053 {"SC_ICACHE_BLKSZ", _SC_ICACHE_BLKSZ},
Fred Drakec9680921999-12-13 16:37:25 +000010054#endif
10055#ifdef _SC_ICACHE_LINESZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010056 {"SC_ICACHE_LINESZ", _SC_ICACHE_LINESZ},
Fred Drakec9680921999-12-13 16:37:25 +000010057#endif
10058#ifdef _SC_ICACHE_SZ
Victor Stinner8c62be82010-05-06 00:08:46 +000010059 {"SC_ICACHE_SZ", _SC_ICACHE_SZ},
Fred Drakec9680921999-12-13 16:37:25 +000010060#endif
Fred Draked86ed291999-12-15 15:34:33 +000010061#ifdef _SC_INF
Victor Stinner8c62be82010-05-06 00:08:46 +000010062 {"SC_INF", _SC_INF},
Fred Draked86ed291999-12-15 15:34:33 +000010063#endif
Fred Drakec9680921999-12-13 16:37:25 +000010064#ifdef _SC_INT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010065 {"SC_INT_MAX", _SC_INT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010066#endif
10067#ifdef _SC_INT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010068 {"SC_INT_MIN", _SC_INT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010069#endif
10070#ifdef _SC_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010071 {"SC_IOV_MAX", _SC_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010072#endif
Fred Draked86ed291999-12-15 15:34:33 +000010073#ifdef _SC_IP_SECOPTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010074 {"SC_IP_SECOPTS", _SC_IP_SECOPTS},
Fred Draked86ed291999-12-15 15:34:33 +000010075#endif
Fred Drakec9680921999-12-13 16:37:25 +000010076#ifdef _SC_JOB_CONTROL
Victor Stinner8c62be82010-05-06 00:08:46 +000010077 {"SC_JOB_CONTROL", _SC_JOB_CONTROL},
Fred Drakec9680921999-12-13 16:37:25 +000010078#endif
Fred Draked86ed291999-12-15 15:34:33 +000010079#ifdef _SC_KERN_POINTERS
Victor Stinner8c62be82010-05-06 00:08:46 +000010080 {"SC_KERN_POINTERS", _SC_KERN_POINTERS},
Fred Draked86ed291999-12-15 15:34:33 +000010081#endif
10082#ifdef _SC_KERN_SIM
Victor Stinner8c62be82010-05-06 00:08:46 +000010083 {"SC_KERN_SIM", _SC_KERN_SIM},
Fred Draked86ed291999-12-15 15:34:33 +000010084#endif
Fred Drakec9680921999-12-13 16:37:25 +000010085#ifdef _SC_LINE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010086 {"SC_LINE_MAX", _SC_LINE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010087#endif
10088#ifdef _SC_LOGIN_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010089 {"SC_LOGIN_NAME_MAX", _SC_LOGIN_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010090#endif
10091#ifdef _SC_LOGNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010092 {"SC_LOGNAME_MAX", _SC_LOGNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010093#endif
10094#ifdef _SC_LONG_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010095 {"SC_LONG_BIT", _SC_LONG_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000010096#endif
Fred Draked86ed291999-12-15 15:34:33 +000010097#ifdef _SC_MAC
Victor Stinner8c62be82010-05-06 00:08:46 +000010098 {"SC_MAC", _SC_MAC},
Fred Draked86ed291999-12-15 15:34:33 +000010099#endif
Fred Drakec9680921999-12-13 16:37:25 +000010100#ifdef _SC_MAPPED_FILES
Victor Stinner8c62be82010-05-06 00:08:46 +000010101 {"SC_MAPPED_FILES", _SC_MAPPED_FILES},
Fred Drakec9680921999-12-13 16:37:25 +000010102#endif
10103#ifdef _SC_MAXPID
Victor Stinner8c62be82010-05-06 00:08:46 +000010104 {"SC_MAXPID", _SC_MAXPID},
Fred Drakec9680921999-12-13 16:37:25 +000010105#endif
10106#ifdef _SC_MB_LEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010107 {"SC_MB_LEN_MAX", _SC_MB_LEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010108#endif
10109#ifdef _SC_MEMLOCK
Victor Stinner8c62be82010-05-06 00:08:46 +000010110 {"SC_MEMLOCK", _SC_MEMLOCK},
Fred Drakec9680921999-12-13 16:37:25 +000010111#endif
10112#ifdef _SC_MEMLOCK_RANGE
Victor Stinner8c62be82010-05-06 00:08:46 +000010113 {"SC_MEMLOCK_RANGE", _SC_MEMLOCK_RANGE},
Fred Drakec9680921999-12-13 16:37:25 +000010114#endif
10115#ifdef _SC_MEMORY_PROTECTION
Victor Stinner8c62be82010-05-06 00:08:46 +000010116 {"SC_MEMORY_PROTECTION", _SC_MEMORY_PROTECTION},
Fred Drakec9680921999-12-13 16:37:25 +000010117#endif
10118#ifdef _SC_MESSAGE_PASSING
Victor Stinner8c62be82010-05-06 00:08:46 +000010119 {"SC_MESSAGE_PASSING", _SC_MESSAGE_PASSING},
Fred Drakec9680921999-12-13 16:37:25 +000010120#endif
Fred Draked86ed291999-12-15 15:34:33 +000010121#ifdef _SC_MMAP_FIXED_ALIGNMENT
Victor Stinner8c62be82010-05-06 00:08:46 +000010122 {"SC_MMAP_FIXED_ALIGNMENT", _SC_MMAP_FIXED_ALIGNMENT},
Fred Draked86ed291999-12-15 15:34:33 +000010123#endif
Fred Drakec9680921999-12-13 16:37:25 +000010124#ifdef _SC_MQ_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010125 {"SC_MQ_OPEN_MAX", _SC_MQ_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010126#endif
10127#ifdef _SC_MQ_PRIO_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010128 {"SC_MQ_PRIO_MAX", _SC_MQ_PRIO_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010129#endif
Fred Draked86ed291999-12-15 15:34:33 +000010130#ifdef _SC_NACLS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010131 {"SC_NACLS_MAX", _SC_NACLS_MAX},
Fred Draked86ed291999-12-15 15:34:33 +000010132#endif
Fred Drakec9680921999-12-13 16:37:25 +000010133#ifdef _SC_NGROUPS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010134 {"SC_NGROUPS_MAX", _SC_NGROUPS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010135#endif
10136#ifdef _SC_NL_ARGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010137 {"SC_NL_ARGMAX", _SC_NL_ARGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010138#endif
10139#ifdef _SC_NL_LANGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010140 {"SC_NL_LANGMAX", _SC_NL_LANGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010141#endif
10142#ifdef _SC_NL_MSGMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010143 {"SC_NL_MSGMAX", _SC_NL_MSGMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010144#endif
10145#ifdef _SC_NL_NMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010146 {"SC_NL_NMAX", _SC_NL_NMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010147#endif
10148#ifdef _SC_NL_SETMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010149 {"SC_NL_SETMAX", _SC_NL_SETMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010150#endif
10151#ifdef _SC_NL_TEXTMAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010152 {"SC_NL_TEXTMAX", _SC_NL_TEXTMAX},
Fred Drakec9680921999-12-13 16:37:25 +000010153#endif
10154#ifdef _SC_NPROCESSORS_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000010155 {"SC_NPROCESSORS_CONF", _SC_NPROCESSORS_CONF},
Fred Drakec9680921999-12-13 16:37:25 +000010156#endif
10157#ifdef _SC_NPROCESSORS_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000010158 {"SC_NPROCESSORS_ONLN", _SC_NPROCESSORS_ONLN},
Fred Drakec9680921999-12-13 16:37:25 +000010159#endif
Fred Draked86ed291999-12-15 15:34:33 +000010160#ifdef _SC_NPROC_CONF
Victor Stinner8c62be82010-05-06 00:08:46 +000010161 {"SC_NPROC_CONF", _SC_NPROC_CONF},
Fred Draked86ed291999-12-15 15:34:33 +000010162#endif
10163#ifdef _SC_NPROC_ONLN
Victor Stinner8c62be82010-05-06 00:08:46 +000010164 {"SC_NPROC_ONLN", _SC_NPROC_ONLN},
Fred Draked86ed291999-12-15 15:34:33 +000010165#endif
Fred Drakec9680921999-12-13 16:37:25 +000010166#ifdef _SC_NZERO
Victor Stinner8c62be82010-05-06 00:08:46 +000010167 {"SC_NZERO", _SC_NZERO},
Fred Drakec9680921999-12-13 16:37:25 +000010168#endif
10169#ifdef _SC_OPEN_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010170 {"SC_OPEN_MAX", _SC_OPEN_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010171#endif
10172#ifdef _SC_PAGESIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010173 {"SC_PAGESIZE", _SC_PAGESIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010174#endif
10175#ifdef _SC_PAGE_SIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010176 {"SC_PAGE_SIZE", _SC_PAGE_SIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010177#endif
10178#ifdef _SC_PASS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010179 {"SC_PASS_MAX", _SC_PASS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010180#endif
10181#ifdef _SC_PHYS_PAGES
Victor Stinner8c62be82010-05-06 00:08:46 +000010182 {"SC_PHYS_PAGES", _SC_PHYS_PAGES},
Fred Drakec9680921999-12-13 16:37:25 +000010183#endif
10184#ifdef _SC_PII
Victor Stinner8c62be82010-05-06 00:08:46 +000010185 {"SC_PII", _SC_PII},
Fred Drakec9680921999-12-13 16:37:25 +000010186#endif
10187#ifdef _SC_PII_INTERNET
Victor Stinner8c62be82010-05-06 00:08:46 +000010188 {"SC_PII_INTERNET", _SC_PII_INTERNET},
Fred Drakec9680921999-12-13 16:37:25 +000010189#endif
10190#ifdef _SC_PII_INTERNET_DGRAM
Victor Stinner8c62be82010-05-06 00:08:46 +000010191 {"SC_PII_INTERNET_DGRAM", _SC_PII_INTERNET_DGRAM},
Fred Drakec9680921999-12-13 16:37:25 +000010192#endif
10193#ifdef _SC_PII_INTERNET_STREAM
Victor Stinner8c62be82010-05-06 00:08:46 +000010194 {"SC_PII_INTERNET_STREAM", _SC_PII_INTERNET_STREAM},
Fred Drakec9680921999-12-13 16:37:25 +000010195#endif
10196#ifdef _SC_PII_OSI
Victor Stinner8c62be82010-05-06 00:08:46 +000010197 {"SC_PII_OSI", _SC_PII_OSI},
Fred Drakec9680921999-12-13 16:37:25 +000010198#endif
10199#ifdef _SC_PII_OSI_CLTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010200 {"SC_PII_OSI_CLTS", _SC_PII_OSI_CLTS},
Fred Drakec9680921999-12-13 16:37:25 +000010201#endif
10202#ifdef _SC_PII_OSI_COTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010203 {"SC_PII_OSI_COTS", _SC_PII_OSI_COTS},
Fred Drakec9680921999-12-13 16:37:25 +000010204#endif
10205#ifdef _SC_PII_OSI_M
Victor Stinner8c62be82010-05-06 00:08:46 +000010206 {"SC_PII_OSI_M", _SC_PII_OSI_M},
Fred Drakec9680921999-12-13 16:37:25 +000010207#endif
10208#ifdef _SC_PII_SOCKET
Victor Stinner8c62be82010-05-06 00:08:46 +000010209 {"SC_PII_SOCKET", _SC_PII_SOCKET},
Fred Drakec9680921999-12-13 16:37:25 +000010210#endif
10211#ifdef _SC_PII_XTI
Victor Stinner8c62be82010-05-06 00:08:46 +000010212 {"SC_PII_XTI", _SC_PII_XTI},
Fred Drakec9680921999-12-13 16:37:25 +000010213#endif
10214#ifdef _SC_POLL
Victor Stinner8c62be82010-05-06 00:08:46 +000010215 {"SC_POLL", _SC_POLL},
Fred Drakec9680921999-12-13 16:37:25 +000010216#endif
10217#ifdef _SC_PRIORITIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000010218 {"SC_PRIORITIZED_IO", _SC_PRIORITIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000010219#endif
10220#ifdef _SC_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000010221 {"SC_PRIORITY_SCHEDULING", _SC_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000010222#endif
10223#ifdef _SC_REALTIME_SIGNALS
Victor Stinner8c62be82010-05-06 00:08:46 +000010224 {"SC_REALTIME_SIGNALS", _SC_REALTIME_SIGNALS},
Fred Drakec9680921999-12-13 16:37:25 +000010225#endif
10226#ifdef _SC_RE_DUP_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010227 {"SC_RE_DUP_MAX", _SC_RE_DUP_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010228#endif
10229#ifdef _SC_RTSIG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010230 {"SC_RTSIG_MAX", _SC_RTSIG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010231#endif
10232#ifdef _SC_SAVED_IDS
Victor Stinner8c62be82010-05-06 00:08:46 +000010233 {"SC_SAVED_IDS", _SC_SAVED_IDS},
Fred Drakec9680921999-12-13 16:37:25 +000010234#endif
10235#ifdef _SC_SCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010236 {"SC_SCHAR_MAX", _SC_SCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010237#endif
10238#ifdef _SC_SCHAR_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010239 {"SC_SCHAR_MIN", _SC_SCHAR_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010240#endif
10241#ifdef _SC_SELECT
Victor Stinner8c62be82010-05-06 00:08:46 +000010242 {"SC_SELECT", _SC_SELECT},
Fred Drakec9680921999-12-13 16:37:25 +000010243#endif
10244#ifdef _SC_SEMAPHORES
Victor Stinner8c62be82010-05-06 00:08:46 +000010245 {"SC_SEMAPHORES", _SC_SEMAPHORES},
Fred Drakec9680921999-12-13 16:37:25 +000010246#endif
10247#ifdef _SC_SEM_NSEMS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010248 {"SC_SEM_NSEMS_MAX", _SC_SEM_NSEMS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010249#endif
10250#ifdef _SC_SEM_VALUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010251 {"SC_SEM_VALUE_MAX", _SC_SEM_VALUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010252#endif
10253#ifdef _SC_SHARED_MEMORY_OBJECTS
Victor Stinner8c62be82010-05-06 00:08:46 +000010254 {"SC_SHARED_MEMORY_OBJECTS", _SC_SHARED_MEMORY_OBJECTS},
Fred Drakec9680921999-12-13 16:37:25 +000010255#endif
10256#ifdef _SC_SHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010257 {"SC_SHRT_MAX", _SC_SHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010258#endif
10259#ifdef _SC_SHRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010260 {"SC_SHRT_MIN", _SC_SHRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010261#endif
10262#ifdef _SC_SIGQUEUE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010263 {"SC_SIGQUEUE_MAX", _SC_SIGQUEUE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010264#endif
10265#ifdef _SC_SIGRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010266 {"SC_SIGRT_MAX", _SC_SIGRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010267#endif
10268#ifdef _SC_SIGRT_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010269 {"SC_SIGRT_MIN", _SC_SIGRT_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010270#endif
Fred Draked86ed291999-12-15 15:34:33 +000010271#ifdef _SC_SOFTPOWER
Victor Stinner8c62be82010-05-06 00:08:46 +000010272 {"SC_SOFTPOWER", _SC_SOFTPOWER},
Fred Draked86ed291999-12-15 15:34:33 +000010273#endif
Fred Drakec9680921999-12-13 16:37:25 +000010274#ifdef _SC_SPLIT_CACHE
Victor Stinner8c62be82010-05-06 00:08:46 +000010275 {"SC_SPLIT_CACHE", _SC_SPLIT_CACHE},
Fred Drakec9680921999-12-13 16:37:25 +000010276#endif
10277#ifdef _SC_SSIZE_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010278 {"SC_SSIZE_MAX", _SC_SSIZE_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010279#endif
10280#ifdef _SC_STACK_PROT
Victor Stinner8c62be82010-05-06 00:08:46 +000010281 {"SC_STACK_PROT", _SC_STACK_PROT},
Fred Drakec9680921999-12-13 16:37:25 +000010282#endif
10283#ifdef _SC_STREAM_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010284 {"SC_STREAM_MAX", _SC_STREAM_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010285#endif
10286#ifdef _SC_SYNCHRONIZED_IO
Victor Stinner8c62be82010-05-06 00:08:46 +000010287 {"SC_SYNCHRONIZED_IO", _SC_SYNCHRONIZED_IO},
Fred Drakec9680921999-12-13 16:37:25 +000010288#endif
10289#ifdef _SC_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000010290 {"SC_THREADS", _SC_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000010291#endif
10292#ifdef _SC_THREAD_ATTR_STACKADDR
Victor Stinner8c62be82010-05-06 00:08:46 +000010293 {"SC_THREAD_ATTR_STACKADDR", _SC_THREAD_ATTR_STACKADDR},
Fred Drakec9680921999-12-13 16:37:25 +000010294#endif
10295#ifdef _SC_THREAD_ATTR_STACKSIZE
Victor Stinner8c62be82010-05-06 00:08:46 +000010296 {"SC_THREAD_ATTR_STACKSIZE", _SC_THREAD_ATTR_STACKSIZE},
Fred Drakec9680921999-12-13 16:37:25 +000010297#endif
10298#ifdef _SC_THREAD_DESTRUCTOR_ITERATIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000010299 {"SC_THREAD_DESTRUCTOR_ITERATIONS", _SC_THREAD_DESTRUCTOR_ITERATIONS},
Fred Drakec9680921999-12-13 16:37:25 +000010300#endif
10301#ifdef _SC_THREAD_KEYS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010302 {"SC_THREAD_KEYS_MAX", _SC_THREAD_KEYS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010303#endif
10304#ifdef _SC_THREAD_PRIORITY_SCHEDULING
Victor Stinner8c62be82010-05-06 00:08:46 +000010305 {"SC_THREAD_PRIORITY_SCHEDULING", _SC_THREAD_PRIORITY_SCHEDULING},
Fred Drakec9680921999-12-13 16:37:25 +000010306#endif
10307#ifdef _SC_THREAD_PRIO_INHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010308 {"SC_THREAD_PRIO_INHERIT", _SC_THREAD_PRIO_INHERIT},
Fred Drakec9680921999-12-13 16:37:25 +000010309#endif
10310#ifdef _SC_THREAD_PRIO_PROTECT
Victor Stinner8c62be82010-05-06 00:08:46 +000010311 {"SC_THREAD_PRIO_PROTECT", _SC_THREAD_PRIO_PROTECT},
Fred Drakec9680921999-12-13 16:37:25 +000010312#endif
10313#ifdef _SC_THREAD_PROCESS_SHARED
Victor Stinner8c62be82010-05-06 00:08:46 +000010314 {"SC_THREAD_PROCESS_SHARED", _SC_THREAD_PROCESS_SHARED},
Fred Drakec9680921999-12-13 16:37:25 +000010315#endif
10316#ifdef _SC_THREAD_SAFE_FUNCTIONS
Victor Stinner8c62be82010-05-06 00:08:46 +000010317 {"SC_THREAD_SAFE_FUNCTIONS", _SC_THREAD_SAFE_FUNCTIONS},
Fred Drakec9680921999-12-13 16:37:25 +000010318#endif
10319#ifdef _SC_THREAD_STACK_MIN
Victor Stinner8c62be82010-05-06 00:08:46 +000010320 {"SC_THREAD_STACK_MIN", _SC_THREAD_STACK_MIN},
Fred Drakec9680921999-12-13 16:37:25 +000010321#endif
10322#ifdef _SC_THREAD_THREADS_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010323 {"SC_THREAD_THREADS_MAX", _SC_THREAD_THREADS_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010324#endif
10325#ifdef _SC_TIMERS
Victor Stinner8c62be82010-05-06 00:08:46 +000010326 {"SC_TIMERS", _SC_TIMERS},
Fred Drakec9680921999-12-13 16:37:25 +000010327#endif
10328#ifdef _SC_TIMER_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010329 {"SC_TIMER_MAX", _SC_TIMER_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010330#endif
10331#ifdef _SC_TTY_NAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010332 {"SC_TTY_NAME_MAX", _SC_TTY_NAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010333#endif
10334#ifdef _SC_TZNAME_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010335 {"SC_TZNAME_MAX", _SC_TZNAME_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010336#endif
10337#ifdef _SC_T_IOV_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010338 {"SC_T_IOV_MAX", _SC_T_IOV_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010339#endif
10340#ifdef _SC_UCHAR_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010341 {"SC_UCHAR_MAX", _SC_UCHAR_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010342#endif
10343#ifdef _SC_UINT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010344 {"SC_UINT_MAX", _SC_UINT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010345#endif
10346#ifdef _SC_UIO_MAXIOV
Victor Stinner8c62be82010-05-06 00:08:46 +000010347 {"SC_UIO_MAXIOV", _SC_UIO_MAXIOV},
Fred Drakec9680921999-12-13 16:37:25 +000010348#endif
10349#ifdef _SC_ULONG_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010350 {"SC_ULONG_MAX", _SC_ULONG_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010351#endif
10352#ifdef _SC_USHRT_MAX
Victor Stinner8c62be82010-05-06 00:08:46 +000010353 {"SC_USHRT_MAX", _SC_USHRT_MAX},
Fred Drakec9680921999-12-13 16:37:25 +000010354#endif
10355#ifdef _SC_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010356 {"SC_VERSION", _SC_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010357#endif
10358#ifdef _SC_WORD_BIT
Victor Stinner8c62be82010-05-06 00:08:46 +000010359 {"SC_WORD_BIT", _SC_WORD_BIT},
Fred Drakec9680921999-12-13 16:37:25 +000010360#endif
10361#ifdef _SC_XBS5_ILP32_OFF32
Victor Stinner8c62be82010-05-06 00:08:46 +000010362 {"SC_XBS5_ILP32_OFF32", _SC_XBS5_ILP32_OFF32},
Fred Drakec9680921999-12-13 16:37:25 +000010363#endif
10364#ifdef _SC_XBS5_ILP32_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000010365 {"SC_XBS5_ILP32_OFFBIG", _SC_XBS5_ILP32_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000010366#endif
10367#ifdef _SC_XBS5_LP64_OFF64
Victor Stinner8c62be82010-05-06 00:08:46 +000010368 {"SC_XBS5_LP64_OFF64", _SC_XBS5_LP64_OFF64},
Fred Drakec9680921999-12-13 16:37:25 +000010369#endif
10370#ifdef _SC_XBS5_LPBIG_OFFBIG
Victor Stinner8c62be82010-05-06 00:08:46 +000010371 {"SC_XBS5_LPBIG_OFFBIG", _SC_XBS5_LPBIG_OFFBIG},
Fred Drakec9680921999-12-13 16:37:25 +000010372#endif
10373#ifdef _SC_XOPEN_CRYPT
Victor Stinner8c62be82010-05-06 00:08:46 +000010374 {"SC_XOPEN_CRYPT", _SC_XOPEN_CRYPT},
Fred Drakec9680921999-12-13 16:37:25 +000010375#endif
10376#ifdef _SC_XOPEN_ENH_I18N
Victor Stinner8c62be82010-05-06 00:08:46 +000010377 {"SC_XOPEN_ENH_I18N", _SC_XOPEN_ENH_I18N},
Fred Drakec9680921999-12-13 16:37:25 +000010378#endif
10379#ifdef _SC_XOPEN_LEGACY
Victor Stinner8c62be82010-05-06 00:08:46 +000010380 {"SC_XOPEN_LEGACY", _SC_XOPEN_LEGACY},
Fred Drakec9680921999-12-13 16:37:25 +000010381#endif
10382#ifdef _SC_XOPEN_REALTIME
Victor Stinner8c62be82010-05-06 00:08:46 +000010383 {"SC_XOPEN_REALTIME", _SC_XOPEN_REALTIME},
Fred Drakec9680921999-12-13 16:37:25 +000010384#endif
10385#ifdef _SC_XOPEN_REALTIME_THREADS
Victor Stinner8c62be82010-05-06 00:08:46 +000010386 {"SC_XOPEN_REALTIME_THREADS", _SC_XOPEN_REALTIME_THREADS},
Fred Drakec9680921999-12-13 16:37:25 +000010387#endif
10388#ifdef _SC_XOPEN_SHM
Victor Stinner8c62be82010-05-06 00:08:46 +000010389 {"SC_XOPEN_SHM", _SC_XOPEN_SHM},
Fred Drakec9680921999-12-13 16:37:25 +000010390#endif
10391#ifdef _SC_XOPEN_UNIX
Victor Stinner8c62be82010-05-06 00:08:46 +000010392 {"SC_XOPEN_UNIX", _SC_XOPEN_UNIX},
Fred Drakec9680921999-12-13 16:37:25 +000010393#endif
10394#ifdef _SC_XOPEN_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010395 {"SC_XOPEN_VERSION", _SC_XOPEN_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010396#endif
10397#ifdef _SC_XOPEN_XCU_VERSION
Victor Stinner8c62be82010-05-06 00:08:46 +000010398 {"SC_XOPEN_XCU_VERSION", _SC_XOPEN_XCU_VERSION},
Fred Drakec9680921999-12-13 16:37:25 +000010399#endif
10400#ifdef _SC_XOPEN_XPG2
Victor Stinner8c62be82010-05-06 00:08:46 +000010401 {"SC_XOPEN_XPG2", _SC_XOPEN_XPG2},
Fred Drakec9680921999-12-13 16:37:25 +000010402#endif
10403#ifdef _SC_XOPEN_XPG3
Victor Stinner8c62be82010-05-06 00:08:46 +000010404 {"SC_XOPEN_XPG3", _SC_XOPEN_XPG3},
Fred Drakec9680921999-12-13 16:37:25 +000010405#endif
10406#ifdef _SC_XOPEN_XPG4
Victor Stinner8c62be82010-05-06 00:08:46 +000010407 {"SC_XOPEN_XPG4", _SC_XOPEN_XPG4},
Fred Drakec9680921999-12-13 16:37:25 +000010408#endif
10409};
10410
10411static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010412conv_sysconf_confname(PyObject *arg, int *valuep)
Fred Drakec9680921999-12-13 16:37:25 +000010413{
10414 return conv_confname(arg, valuep, posix_constants_sysconf,
10415 sizeof(posix_constants_sysconf)
10416 / sizeof(struct constdef));
10417}
10418
Larry Hastings2f936352014-08-05 14:04:04 +100010419
10420/*[clinic input]
10421os.sysconf -> long
10422 name: sysconf_confname
10423 /
10424
10425Return an integer-valued system configuration variable.
10426[clinic start generated code]*/
10427
Larry Hastings2f936352014-08-05 14:04:04 +100010428static long
10429os_sysconf_impl(PyModuleDef *module, int name)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010430/*[clinic end generated code: output=ed567306f58d69c4 input=279e3430a33f29e4]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010431{
10432 long value;
10433
10434 errno = 0;
10435 value = sysconf(name);
10436 if (value == -1 && errno != 0)
10437 posix_error();
10438 return value;
10439}
10440#endif /* HAVE_SYSCONF */
Fred Drakec9680921999-12-13 16:37:25 +000010441
10442
Fred Drakebec628d1999-12-15 18:31:10 +000010443/* This code is used to ensure that the tables of configuration value names
Serhiy Storchaka56a6d852014-12-01 18:28:43 +020010444 * are in sorted order as required by conv_confname(), and also to build
Fred Drakebec628d1999-12-15 18:31:10 +000010445 * the exported dictionaries that are used to publish information about the
10446 * names available on the host platform.
10447 *
10448 * Sorting the table at runtime ensures that the table is properly ordered
10449 * when used, even for platforms we're not able to test on. It also makes
10450 * it easier to add additional entries to the tables.
Fred Draked86ed291999-12-15 15:34:33 +000010451 */
Fred Drakebec628d1999-12-15 18:31:10 +000010452
10453static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010454cmp_constdefs(const void *v1, const void *v2)
Fred Drakebec628d1999-12-15 18:31:10 +000010455{
10456 const struct constdef *c1 =
Victor Stinner8c62be82010-05-06 00:08:46 +000010457 (const struct constdef *) v1;
Fred Drakebec628d1999-12-15 18:31:10 +000010458 const struct constdef *c2 =
Victor Stinner8c62be82010-05-06 00:08:46 +000010459 (const struct constdef *) v2;
Fred Drakebec628d1999-12-15 18:31:10 +000010460
10461 return strcmp(c1->name, c2->name);
10462}
10463
10464static int
Fredrik Lundhff7df9d2000-07-08 22:48:53 +000010465setup_confname_table(struct constdef *table, size_t tablesize,
Victor Stinner8c62be82010-05-06 00:08:46 +000010466 char *tablename, PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000010467{
Fred Drakebec628d1999-12-15 18:31:10 +000010468 PyObject *d = NULL;
Barry Warsaw3155db32000-04-13 15:20:40 +000010469 size_t i;
Fred Drakebec628d1999-12-15 18:31:10 +000010470
10471 qsort(table, tablesize, sizeof(struct constdef), cmp_constdefs);
10472 d = PyDict_New();
Barry Warsaw3155db32000-04-13 15:20:40 +000010473 if (d == NULL)
Victor Stinner8c62be82010-05-06 00:08:46 +000010474 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010475
Barry Warsaw3155db32000-04-13 15:20:40 +000010476 for (i=0; i < tablesize; ++i) {
Victor Stinner8c62be82010-05-06 00:08:46 +000010477 PyObject *o = PyLong_FromLong(table[i].value);
10478 if (o == NULL || PyDict_SetItemString(d, table[i].name, o) == -1) {
10479 Py_XDECREF(o);
10480 Py_DECREF(d);
10481 return -1;
10482 }
10483 Py_DECREF(o);
Fred Draked86ed291999-12-15 15:34:33 +000010484 }
Fred Drake4d1e64b2002-04-15 19:40:07 +000010485 return PyModule_AddObject(module, tablename, d);
Fred Draked86ed291999-12-15 15:34:33 +000010486}
10487
Fred Drakebec628d1999-12-15 18:31:10 +000010488/* Return -1 on failure, 0 on success. */
10489static int
Fred Drake4d1e64b2002-04-15 19:40:07 +000010490setup_confname_tables(PyObject *module)
Fred Draked86ed291999-12-15 15:34:33 +000010491{
10492#if defined(HAVE_FPATHCONF) || defined(HAVE_PATHCONF)
Fred Drakebec628d1999-12-15 18:31:10 +000010493 if (setup_confname_table(posix_constants_pathconf,
Fred Draked86ed291999-12-15 15:34:33 +000010494 sizeof(posix_constants_pathconf)
10495 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010496 "pathconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010497 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010498#endif
10499#ifdef HAVE_CONFSTR
Fred Drakebec628d1999-12-15 18:31:10 +000010500 if (setup_confname_table(posix_constants_confstr,
Fred Draked86ed291999-12-15 15:34:33 +000010501 sizeof(posix_constants_confstr)
10502 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010503 "confstr_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010504 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010505#endif
10506#ifdef HAVE_SYSCONF
Fred Drakebec628d1999-12-15 18:31:10 +000010507 if (setup_confname_table(posix_constants_sysconf,
Fred Draked86ed291999-12-15 15:34:33 +000010508 sizeof(posix_constants_sysconf)
10509 / sizeof(struct constdef),
Fred Drake4d1e64b2002-04-15 19:40:07 +000010510 "sysconf_names", module))
Stefan Krah0e803b32010-11-26 16:16:47 +000010511 return -1;
Fred Draked86ed291999-12-15 15:34:33 +000010512#endif
Fred Drakebec628d1999-12-15 18:31:10 +000010513 return 0;
Fred Draked86ed291999-12-15 15:34:33 +000010514}
Fred Draked86ed291999-12-15 15:34:33 +000010515
10516
Larry Hastings2f936352014-08-05 14:04:04 +100010517/*[clinic input]
10518os.abort
10519
10520Abort the interpreter immediately.
10521
10522This function 'dumps core' or otherwise fails in the hardest way possible
10523on the hosting operating system. This function never returns.
10524[clinic start generated code]*/
10525
Larry Hastings2f936352014-08-05 14:04:04 +100010526static PyObject *
10527os_abort_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010528/*[clinic end generated code: output=486bb96647c299b3 input=cf2c7d98bc504047]*/
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010529{
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010530 abort();
10531 /*NOTREACHED*/
10532 Py_FatalError("abort() called from Python code didn't abort!");
10533 return NULL;
10534}
Fred Drakebec628d1999-12-15 18:31:10 +000010535
Martin v. Löwis6238d2b2002-06-30 15:26:10 +000010536#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100010537/* AC 3.5: change to path_t? but that might change exceptions */
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000010538PyDoc_STRVAR(win32_startfile__doc__,
Larry Hastings2f936352014-08-05 14:04:04 +100010539"startfile(filepath [, operation])\n\
10540\n\
10541Start a file with its associated application.\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000010542\n\
Georg Brandlf4f44152006-02-18 22:29:33 +000010543When \"operation\" is not specified or \"open\", this acts like\n\
10544double-clicking the file in Explorer, or giving the file name as an\n\
10545argument to the DOS \"start\" command: the file is opened with whatever\n\
10546application (if any) its extension is associated.\n\
10547When another \"operation\" is given, it specifies what should be done with\n\
10548the file. A typical operation is \"print\".\n\
Tim Petersf58a7aa2000-09-22 10:05:54 +000010549\n\
10550startfile returns as soon as the associated application is launched.\n\
10551There is no option to wait for the application to close, and no way\n\
10552to retrieve the application's exit status.\n\
10553\n\
10554The filepath is relative to the current directory. If you want to use\n\
10555an absolute path, make sure the first character is not a slash (\"/\");\n\
Martin v. Löwis14f8b4c2002-06-13 20:33:02 +000010556the underlying Win32 ShellExecute function doesn't work if it is.");
Tim Petersf58a7aa2000-09-22 10:05:54 +000010557
Steve Dower7d0e0c92015-01-24 08:18:24 -080010558/* Grab ShellExecute dynamically from shell32 */
10559static int has_ShellExecute = -1;
10560static HINSTANCE (CALLBACK *Py_ShellExecuteA)(HWND, LPCSTR, LPCSTR, LPCSTR,
10561 LPCSTR, INT);
10562static HINSTANCE (CALLBACK *Py_ShellExecuteW)(HWND, LPCWSTR, LPCWSTR, LPCWSTR,
10563 LPCWSTR, INT);
10564static int
10565check_ShellExecute()
10566{
10567 HINSTANCE hShell32;
10568
10569 /* only recheck */
10570 if (-1 == has_ShellExecute) {
10571 Py_BEGIN_ALLOW_THREADS
10572 hShell32 = LoadLibraryW(L"SHELL32");
10573 Py_END_ALLOW_THREADS
10574 if (hShell32) {
10575 *(FARPROC*)&Py_ShellExecuteA = GetProcAddress(hShell32,
10576 "ShellExecuteA");
10577 *(FARPROC*)&Py_ShellExecuteW = GetProcAddress(hShell32,
10578 "ShellExecuteW");
10579 has_ShellExecute = Py_ShellExecuteA &&
10580 Py_ShellExecuteW;
10581 } else {
10582 has_ShellExecute = 0;
10583 }
10584 }
10585 return has_ShellExecute;
10586}
10587
10588
Tim Petersf58a7aa2000-09-22 10:05:54 +000010589static PyObject *
10590win32_startfile(PyObject *self, PyObject *args)
10591{
Victor Stinner8c62be82010-05-06 00:08:46 +000010592 PyObject *ofilepath;
10593 char *filepath;
10594 char *operation = NULL;
Victor Stinnereb5657a2011-09-30 01:44:27 +020010595 wchar_t *wpath, *woperation;
Victor Stinner8c62be82010-05-06 00:08:46 +000010596 HINSTANCE rc;
Hirokazu Yamamoto8223c242009-05-17 04:21:53 +000010597
Victor Stinnereb5657a2011-09-30 01:44:27 +020010598 PyObject *unipath, *uoperation = NULL;
Steve Dower7d0e0c92015-01-24 08:18:24 -080010599
10600 if(!check_ShellExecute()) {
10601 /* If the OS doesn't have ShellExecute, return a
10602 NotImplementedError. */
10603 return PyErr_Format(PyExc_NotImplementedError,
10604 "startfile not available on this platform");
10605 }
10606
Victor Stinner8c62be82010-05-06 00:08:46 +000010607 if (!PyArg_ParseTuple(args, "U|s:startfile",
10608 &unipath, &operation)) {
10609 PyErr_Clear();
10610 goto normal;
10611 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000010612
Victor Stinner8c62be82010-05-06 00:08:46 +000010613 if (operation) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020010614 uoperation = PyUnicode_DecodeASCII(operation,
Victor Stinner8c62be82010-05-06 00:08:46 +000010615 strlen(operation), NULL);
Victor Stinnereb5657a2011-09-30 01:44:27 +020010616 if (!uoperation) {
Victor Stinner8c62be82010-05-06 00:08:46 +000010617 PyErr_Clear();
10618 operation = NULL;
10619 goto normal;
10620 }
10621 }
Hirokazu Yamamoto892a37a2009-06-28 11:07:03 +000010622
Victor Stinnereb5657a2011-09-30 01:44:27 +020010623 wpath = PyUnicode_AsUnicode(unipath);
10624 if (wpath == NULL)
10625 goto normal;
10626 if (uoperation) {
10627 woperation = PyUnicode_AsUnicode(uoperation);
10628 if (woperation == NULL)
10629 goto normal;
10630 }
10631 else
10632 woperation = NULL;
10633
Victor Stinner8c62be82010-05-06 00:08:46 +000010634 Py_BEGIN_ALLOW_THREADS
Steve Dower7d0e0c92015-01-24 08:18:24 -080010635 rc = Py_ShellExecuteW((HWND)0, woperation, wpath,
10636 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000010637 Py_END_ALLOW_THREADS
10638
Victor Stinnereb5657a2011-09-30 01:44:27 +020010639 Py_XDECREF(uoperation);
Victor Stinner8c62be82010-05-06 00:08:46 +000010640 if (rc <= (HINSTANCE)32) {
Victor Stinnereb5657a2011-09-30 01:44:27 +020010641 win32_error_object("startfile", unipath);
10642 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000010643 }
10644 Py_INCREF(Py_None);
10645 return Py_None;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000010646
10647normal:
Victor Stinner8c62be82010-05-06 00:08:46 +000010648 if (!PyArg_ParseTuple(args, "O&|s:startfile",
10649 PyUnicode_FSConverter, &ofilepath,
10650 &operation))
10651 return NULL;
Victor Stinner1ab6c2d2011-11-15 22:27:41 +010010652 if (win32_warn_bytes_api()) {
10653 Py_DECREF(ofilepath);
10654 return NULL;
10655 }
Victor Stinner8c62be82010-05-06 00:08:46 +000010656 filepath = PyBytes_AsString(ofilepath);
10657 Py_BEGIN_ALLOW_THREADS
Steve Dower7d0e0c92015-01-24 08:18:24 -080010658 rc = Py_ShellExecuteA((HWND)0, operation, filepath,
10659 NULL, NULL, SW_SHOWNORMAL);
Victor Stinner8c62be82010-05-06 00:08:46 +000010660 Py_END_ALLOW_THREADS
10661 if (rc <= (HINSTANCE)32) {
10662 PyObject *errval = win32_error("startfile", filepath);
10663 Py_DECREF(ofilepath);
10664 return errval;
10665 }
10666 Py_DECREF(ofilepath);
10667 Py_INCREF(Py_None);
10668 return Py_None;
Tim Petersf58a7aa2000-09-22 10:05:54 +000010669}
Larry Hastings2f936352014-08-05 14:04:04 +100010670#endif /* MS_WINDOWS */
10671
Fred Drake5ab8eaf1999-12-09 21:13:07 +000010672
Martin v. Löwis438b5342002-12-27 10:16:42 +000010673#ifdef HAVE_GETLOADAVG
Larry Hastings2f936352014-08-05 14:04:04 +100010674/*[clinic input]
10675os.getloadavg
10676
10677Return average recent system load information.
10678
10679Return the number of processes in the system run queue averaged over
10680the last 1, 5, and 15 minutes as a tuple of three floats.
10681Raises OSError if the load average was unobtainable.
10682[clinic start generated code]*/
10683
Larry Hastings2f936352014-08-05 14:04:04 +100010684static PyObject *
10685os_getloadavg_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010686/*[clinic end generated code: output=2b64c5b675d74c14 input=3d6d826b76d8a34e]*/
Martin v. Löwis438b5342002-12-27 10:16:42 +000010687{
10688 double loadavg[3];
Martin v. Löwis438b5342002-12-27 10:16:42 +000010689 if (getloadavg(loadavg, 3)!=3) {
Stefan Krah0e803b32010-11-26 16:16:47 +000010690 PyErr_SetString(PyExc_OSError, "Load averages are unobtainable");
10691 return NULL;
Martin v. Löwis438b5342002-12-27 10:16:42 +000010692 } else
Stefan Krah0e803b32010-11-26 16:16:47 +000010693 return Py_BuildValue("ddd", loadavg[0], loadavg[1], loadavg[2]);
Martin v. Löwis438b5342002-12-27 10:16:42 +000010694}
Larry Hastings2f936352014-08-05 14:04:04 +100010695#endif /* HAVE_GETLOADAVG */
Martin v. Löwis438b5342002-12-27 10:16:42 +000010696
Larry Hastings2f936352014-08-05 14:04:04 +100010697
10698/*[clinic input]
10699os.device_encoding
10700 fd: int
10701
10702Return a string describing the encoding of a terminal's file descriptor.
10703
10704The file descriptor must be attached to a terminal.
10705If the device is not a terminal, return None.
10706[clinic start generated code]*/
10707
Larry Hastings2f936352014-08-05 14:04:04 +100010708static PyObject *
10709os_device_encoding_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010710/*[clinic end generated code: output=34f14e33468419c1 input=9e1d4a42b66df312]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010711{
Brett Cannonefb00c02012-02-29 18:31:31 -050010712 return _Py_device_encoding(fd);
Martin v. Löwisd1cd4d42007-08-11 14:02:14 +000010713}
10714
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010715
Larry Hastings2f936352014-08-05 14:04:04 +100010716#ifdef HAVE_SETRESUID
10717/*[clinic input]
10718os.setresuid
10719
10720 ruid: uid_t
10721 euid: uid_t
10722 suid: uid_t
10723 /
10724
10725Set the current process's real, effective, and saved user ids.
10726[clinic start generated code]*/
10727
Larry Hastings2f936352014-08-05 14:04:04 +100010728static PyObject *
10729os_setresuid_impl(PyModuleDef *module, uid_t ruid, uid_t euid, uid_t suid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010730/*[clinic end generated code: output=92cc330812c6ed0f input=9e33cb79a82792f3]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010731{
Victor Stinner8c62be82010-05-06 00:08:46 +000010732 if (setresuid(ruid, euid, suid) < 0)
10733 return posix_error();
10734 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010735}
Larry Hastings2f936352014-08-05 14:04:04 +100010736#endif /* HAVE_SETRESUID */
10737
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010738
10739#ifdef HAVE_SETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100010740/*[clinic input]
10741os.setresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010742
Larry Hastings2f936352014-08-05 14:04:04 +100010743 rgid: gid_t
10744 egid: gid_t
10745 sgid: gid_t
10746 /
10747
10748Set the current process's real, effective, and saved group ids.
10749[clinic start generated code]*/
10750
Larry Hastings2f936352014-08-05 14:04:04 +100010751static PyObject *
10752os_setresgid_impl(PyModuleDef *module, gid_t rgid, gid_t egid, gid_t sgid)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010753/*[clinic end generated code: output=e91dc4842a604429 input=33e9e0785ef426b1]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010754{
Victor Stinner8c62be82010-05-06 00:08:46 +000010755 if (setresgid(rgid, egid, sgid) < 0)
10756 return posix_error();
10757 Py_RETURN_NONE;
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010758}
Larry Hastings2f936352014-08-05 14:04:04 +100010759#endif /* HAVE_SETRESGID */
10760
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010761
10762#ifdef HAVE_GETRESUID
Larry Hastings2f936352014-08-05 14:04:04 +100010763/*[clinic input]
10764os.getresuid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010765
Larry Hastings2f936352014-08-05 14:04:04 +100010766Return a tuple of the current process's real, effective, and saved user ids.
10767[clinic start generated code]*/
10768
Larry Hastings2f936352014-08-05 14:04:04 +100010769static PyObject *
10770os_getresuid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010771/*[clinic end generated code: output=9ddef62faae8e477 input=41ccfa8e1f6517ad]*/
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010772{
Victor Stinner8c62be82010-05-06 00:08:46 +000010773 uid_t ruid, euid, suid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010774 if (getresuid(&ruid, &euid, &suid) < 0)
10775 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020010776 return Py_BuildValue("(NNN)", _PyLong_FromUid(ruid),
10777 _PyLong_FromUid(euid),
10778 _PyLong_FromUid(suid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010779}
Larry Hastings2f936352014-08-05 14:04:04 +100010780#endif /* HAVE_GETRESUID */
10781
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010782
10783#ifdef HAVE_GETRESGID
Larry Hastings2f936352014-08-05 14:04:04 +100010784/*[clinic input]
10785os.getresgid
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010786
Larry Hastings2f936352014-08-05 14:04:04 +100010787Return a tuple of the current process's real, effective, and saved group ids.
10788[clinic start generated code]*/
10789
Larry Hastings2f936352014-08-05 14:04:04 +100010790static PyObject *
10791os_getresgid_impl(PyModuleDef *module)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010792/*[clinic end generated code: output=e1a553cbcf16234c input=517e68db9ca32df6]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010793{
10794 gid_t rgid, egid, sgid;
Victor Stinner8c62be82010-05-06 00:08:46 +000010795 if (getresgid(&rgid, &egid, &sgid) < 0)
10796 return posix_error();
Serhiy Storchaka7cf55992013-02-10 21:56:49 +020010797 return Py_BuildValue("(NNN)", _PyLong_FromGid(rgid),
10798 _PyLong_FromGid(egid),
10799 _PyLong_FromGid(sgid));
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010800}
Larry Hastings2f936352014-08-05 14:04:04 +100010801#endif /* HAVE_GETRESGID */
10802
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000010803
Benjamin Peterson9428d532011-09-14 11:45:52 -040010804#ifdef USE_XATTRS
Larry Hastings2f936352014-08-05 14:04:04 +100010805/*[clinic input]
10806os.getxattr
Benjamin Peterson799bd802011-08-31 22:15:17 -040010807
Larry Hastings2f936352014-08-05 14:04:04 +100010808 path: path_t(allow_fd=True)
10809 attribute: path_t
10810 *
10811 follow_symlinks: bool = True
10812
10813Return the value of extended attribute attribute on path.
10814
10815path may be either a string or an open file descriptor.
10816If follow_symlinks is False, and the last element of the path is a symbolic
10817 link, getxattr will examine the symbolic link itself instead of the file
10818 the link points to.
10819
10820[clinic start generated code]*/
10821
Larry Hastings2f936352014-08-05 14:04:04 +100010822static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010823os_getxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10824 int follow_symlinks)
10825/*[clinic end generated code: output=cf2cede74bd5d412 input=8c8ea3bab78d89c2]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010826{
10827 Py_ssize_t i;
10828 PyObject *buffer = NULL;
10829
10830 if (fd_and_follow_symlinks_invalid("getxattr", path->fd, follow_symlinks))
10831 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010832
Larry Hastings9cf065c2012-06-22 16:30:09 -070010833 for (i = 0; ; i++) {
10834 void *ptr;
10835 ssize_t result;
Serhiy Storchaka2d06e842015-12-25 19:53:18 +020010836 static const Py_ssize_t buffer_sizes[] = {128, XATTR_SIZE_MAX, 0};
Larry Hastings9cf065c2012-06-22 16:30:09 -070010837 Py_ssize_t buffer_size = buffer_sizes[i];
10838 if (!buffer_size) {
Larry Hastings2f936352014-08-05 14:04:04 +100010839 path_error(path);
10840 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010841 }
10842 buffer = PyBytes_FromStringAndSize(NULL, buffer_size);
10843 if (!buffer)
Larry Hastings2f936352014-08-05 14:04:04 +100010844 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010845 ptr = PyBytes_AS_STRING(buffer);
Benjamin Peterson799bd802011-08-31 22:15:17 -040010846
Larry Hastings9cf065c2012-06-22 16:30:09 -070010847 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100010848 if (path->fd >= 0)
10849 result = fgetxattr(path->fd, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010850 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100010851 result = getxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010852 else
Larry Hastings2f936352014-08-05 14:04:04 +100010853 result = lgetxattr(path->narrow, attribute->narrow, ptr, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010854 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010855
Larry Hastings9cf065c2012-06-22 16:30:09 -070010856 if (result < 0) {
10857 Py_DECREF(buffer);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010858 if (errno == ERANGE)
10859 continue;
Larry Hastings2f936352014-08-05 14:04:04 +100010860 path_error(path);
10861 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010862 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010863
Larry Hastings9cf065c2012-06-22 16:30:09 -070010864 if (result != buffer_size) {
10865 /* Can only shrink. */
10866 _PyBytes_Resize(&buffer, result);
10867 }
10868 break;
10869 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010870
Larry Hastings9cf065c2012-06-22 16:30:09 -070010871 return buffer;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010872}
10873
Larry Hastings2f936352014-08-05 14:04:04 +100010874
10875/*[clinic input]
10876os.setxattr
10877
10878 path: path_t(allow_fd=True)
10879 attribute: path_t
10880 value: Py_buffer
10881 flags: int = 0
10882 *
10883 follow_symlinks: bool = True
10884
10885Set extended attribute attribute on path to value.
10886
10887path may be either a string or an open file descriptor.
10888If follow_symlinks is False, and the last element of the path is a symbolic
10889 link, setxattr will modify the symbolic link itself instead of the file
10890 the link points to.
10891
10892[clinic start generated code]*/
10893
Benjamin Peterson799bd802011-08-31 22:15:17 -040010894static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010895os_setxattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10896 Py_buffer *value, int flags, int follow_symlinks)
10897/*[clinic end generated code: output=1b395ef82880fea0 input=f0d26833992015c2]*/
Benjamin Peterson799bd802011-08-31 22:15:17 -040010898{
Larry Hastings2f936352014-08-05 14:04:04 +100010899 ssize_t result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010900
Larry Hastings2f936352014-08-05 14:04:04 +100010901 if (fd_and_follow_symlinks_invalid("setxattr", path->fd, follow_symlinks))
Benjamin Peterson799bd802011-08-31 22:15:17 -040010902 return NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010903
Benjamin Peterson799bd802011-08-31 22:15:17 -040010904 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100010905 if (path->fd > -1)
10906 result = fsetxattr(path->fd, attribute->narrow,
10907 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010908 else if (follow_symlinks)
Larry Hastings2f936352014-08-05 14:04:04 +100010909 result = setxattr(path->narrow, attribute->narrow,
10910 value->buf, value->len, flags);
Larry Hastings9cf065c2012-06-22 16:30:09 -070010911 else
Larry Hastings2f936352014-08-05 14:04:04 +100010912 result = lsetxattr(path->narrow, attribute->narrow,
10913 value->buf, value->len, flags);
Benjamin Peterson799bd802011-08-31 22:15:17 -040010914 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010915
Larry Hastings9cf065c2012-06-22 16:30:09 -070010916 if (result) {
Larry Hastings2f936352014-08-05 14:04:04 +100010917 path_error(path);
10918 return NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010919 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040010920
Larry Hastings2f936352014-08-05 14:04:04 +100010921 Py_RETURN_NONE;
10922}
10923
10924
10925/*[clinic input]
10926os.removexattr
10927
10928 path: path_t(allow_fd=True)
10929 attribute: path_t
10930 *
10931 follow_symlinks: bool = True
10932
10933Remove extended attribute attribute on path.
10934
10935path may be either a string or an open file descriptor.
10936If follow_symlinks is False, and the last element of the path is a symbolic
10937 link, removexattr will modify the symbolic link itself instead of the file
10938 the link points to.
10939
10940[clinic start generated code]*/
10941
Larry Hastings2f936352014-08-05 14:04:04 +100010942static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040010943os_removexattr_impl(PyModuleDef *module, path_t *path, path_t *attribute,
10944 int follow_symlinks)
10945/*[clinic end generated code: output=f92bb39ab992650d input=cdb54834161e3329]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010946{
10947 ssize_t result;
10948
10949 if (fd_and_follow_symlinks_invalid("removexattr", path->fd, follow_symlinks))
10950 return NULL;
10951
10952 Py_BEGIN_ALLOW_THREADS;
10953 if (path->fd > -1)
10954 result = fremovexattr(path->fd, attribute->narrow);
10955 else if (follow_symlinks)
10956 result = removexattr(path->narrow, attribute->narrow);
10957 else
10958 result = lremovexattr(path->narrow, attribute->narrow);
10959 Py_END_ALLOW_THREADS;
10960
10961 if (result) {
10962 return path_error(path);
10963 }
10964
10965 Py_RETURN_NONE;
10966}
10967
10968
10969/*[clinic input]
10970os.listxattr
10971
10972 path: path_t(allow_fd=True, nullable=True) = None
10973 *
10974 follow_symlinks: bool = True
10975
10976Return a list of extended attributes on path.
10977
10978path may be either None, a string, or an open file descriptor.
10979if path is None, listxattr will examine the current directory.
10980If follow_symlinks is False, and the last element of the path is a symbolic
10981 link, listxattr will examine the symbolic link itself instead of the file
10982 the link points to.
10983[clinic start generated code]*/
10984
Larry Hastings2f936352014-08-05 14:04:04 +100010985static PyObject *
10986os_listxattr_impl(PyModuleDef *module, path_t *path, int follow_symlinks)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030010987/*[clinic end generated code: output=a87ad6ce56e42a4f input=08cca53ac0b07c13]*/
Larry Hastings2f936352014-08-05 14:04:04 +100010988{
Larry Hastings9cf065c2012-06-22 16:30:09 -070010989 Py_ssize_t i;
10990 PyObject *result = NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100010991 const char *name;
Larry Hastings9cf065c2012-06-22 16:30:09 -070010992 char *buffer = NULL;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010993
Larry Hastings2f936352014-08-05 14:04:04 +100010994 if (fd_and_follow_symlinks_invalid("listxattr", path->fd, follow_symlinks))
Larry Hastings9cf065c2012-06-22 16:30:09 -070010995 goto exit;
Benjamin Peterson799bd802011-08-31 22:15:17 -040010996
Larry Hastings2f936352014-08-05 14:04:04 +100010997 name = path->narrow ? path->narrow : ".";
10998
Larry Hastings9cf065c2012-06-22 16:30:09 -070010999 for (i = 0; ; i++) {
11000 char *start, *trace, *end;
11001 ssize_t length;
Serhiy Storchaka2d06e842015-12-25 19:53:18 +020011002 static const Py_ssize_t buffer_sizes[] = { 256, XATTR_LIST_MAX, 0 };
Larry Hastings9cf065c2012-06-22 16:30:09 -070011003 Py_ssize_t buffer_size = buffer_sizes[i];
11004 if (!buffer_size) {
Christian Heimes3b9493b2012-09-23 16:11:15 +020011005 /* ERANGE */
Larry Hastings2f936352014-08-05 14:04:04 +100011006 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070011007 break;
11008 }
11009 buffer = PyMem_MALLOC(buffer_size);
11010 if (!buffer) {
11011 PyErr_NoMemory();
11012 break;
11013 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040011014
Larry Hastings9cf065c2012-06-22 16:30:09 -070011015 Py_BEGIN_ALLOW_THREADS;
Larry Hastings2f936352014-08-05 14:04:04 +100011016 if (path->fd > -1)
11017 length = flistxattr(path->fd, buffer, buffer_size);
Larry Hastings9cf065c2012-06-22 16:30:09 -070011018 else if (follow_symlinks)
11019 length = listxattr(name, buffer, buffer_size);
11020 else
11021 length = llistxattr(name, buffer, buffer_size);
11022 Py_END_ALLOW_THREADS;
Benjamin Peterson799bd802011-08-31 22:15:17 -040011023
Larry Hastings9cf065c2012-06-22 16:30:09 -070011024 if (length < 0) {
Antoine Pitrou7f987392013-05-13 19:46:29 +020011025 if (errno == ERANGE) {
11026 PyMem_FREE(buffer);
Benjamin Petersondedac522013-05-13 19:55:40 -050011027 buffer = NULL;
Larry Hastings9cf065c2012-06-22 16:30:09 -070011028 continue;
Antoine Pitrou7f987392013-05-13 19:46:29 +020011029 }
Larry Hastings2f936352014-08-05 14:04:04 +100011030 path_error(path);
Larry Hastings9cf065c2012-06-22 16:30:09 -070011031 break;
11032 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040011033
Larry Hastings9cf065c2012-06-22 16:30:09 -070011034 result = PyList_New(0);
11035 if (!result) {
11036 goto exit;
11037 }
Benjamin Peterson799bd802011-08-31 22:15:17 -040011038
Larry Hastings9cf065c2012-06-22 16:30:09 -070011039 end = buffer + length;
11040 for (trace = start = buffer; trace != end; trace++) {
11041 if (!*trace) {
11042 int error;
11043 PyObject *attribute = PyUnicode_DecodeFSDefaultAndSize(start,
11044 trace - start);
11045 if (!attribute) {
11046 Py_DECREF(result);
11047 result = NULL;
11048 goto exit;
11049 }
11050 error = PyList_Append(result, attribute);
11051 Py_DECREF(attribute);
11052 if (error) {
11053 Py_DECREF(result);
11054 result = NULL;
11055 goto exit;
11056 }
11057 start = trace + 1;
11058 }
11059 }
11060 break;
11061 }
11062exit:
Larry Hastings9cf065c2012-06-22 16:30:09 -070011063 if (buffer)
11064 PyMem_FREE(buffer);
11065 return result;
Benjamin Peterson799bd802011-08-31 22:15:17 -040011066}
Benjamin Peterson9428d532011-09-14 11:45:52 -040011067#endif /* USE_XATTRS */
Benjamin Peterson799bd802011-08-31 22:15:17 -040011068
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011069
Larry Hastings2f936352014-08-05 14:04:04 +100011070/*[clinic input]
11071os.urandom
11072
11073 size: Py_ssize_t
11074 /
11075
11076Return a bytes object containing random bytes suitable for cryptographic use.
11077[clinic start generated code]*/
11078
Larry Hastings2f936352014-08-05 14:04:04 +100011079static PyObject *
11080os_urandom_impl(PyModuleDef *module, Py_ssize_t size)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011081/*[clinic end generated code: output=e0011f021501f03b input=4067cdb1b6776c29]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011082{
11083 PyObject *bytes;
11084 int result;
11085
Georg Brandl2fb477c2012-02-21 00:33:36 +010011086 if (size < 0)
11087 return PyErr_Format(PyExc_ValueError,
11088 "negative argument not allowed");
Larry Hastings2f936352014-08-05 14:04:04 +100011089 bytes = PyBytes_FromStringAndSize(NULL, size);
11090 if (bytes == NULL)
Georg Brandl2fb477c2012-02-21 00:33:36 +010011091 return NULL;
11092
Larry Hastings2f936352014-08-05 14:04:04 +100011093 result = _PyOS_URandom(PyBytes_AS_STRING(bytes),
11094 PyBytes_GET_SIZE(bytes));
11095 if (result == -1) {
11096 Py_DECREF(bytes);
Georg Brandl2fb477c2012-02-21 00:33:36 +010011097 return NULL;
11098 }
Larry Hastings2f936352014-08-05 14:04:04 +100011099 return bytes;
Georg Brandl2fb477c2012-02-21 00:33:36 +010011100}
11101
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011102/* Terminal size querying */
11103
11104static PyTypeObject TerminalSizeType;
11105
11106PyDoc_STRVAR(TerminalSize_docstring,
11107 "A tuple of (columns, lines) for holding terminal window size");
11108
11109static PyStructSequence_Field TerminalSize_fields[] = {
11110 {"columns", "width of the terminal window in characters"},
11111 {"lines", "height of the terminal window in characters"},
11112 {NULL, NULL}
11113};
11114
11115static PyStructSequence_Desc TerminalSize_desc = {
11116 "os.terminal_size",
11117 TerminalSize_docstring,
11118 TerminalSize_fields,
11119 2,
11120};
11121
11122#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
Larry Hastings2f936352014-08-05 14:04:04 +100011123/* AC 3.5: fd should accept None */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011124PyDoc_STRVAR(termsize__doc__,
11125 "Return the size of the terminal window as (columns, lines).\n" \
11126 "\n" \
11127 "The optional argument fd (default standard output) specifies\n" \
11128 "which file descriptor should be queried.\n" \
11129 "\n" \
11130 "If the file descriptor is not connected to a terminal, an OSError\n" \
11131 "is thrown.\n" \
11132 "\n" \
11133 "This function will only be defined if an implementation is\n" \
11134 "available for this system.\n" \
11135 "\n" \
11136 "shutil.get_terminal_size is the high-level function which should \n" \
11137 "normally be used, os.get_terminal_size is the low-level implementation.");
11138
11139static PyObject*
11140get_terminal_size(PyObject *self, PyObject *args)
11141{
11142 int columns, lines;
11143 PyObject *termsize;
11144
11145 int fd = fileno(stdout);
11146 /* Under some conditions stdout may not be connected and
11147 * fileno(stdout) may point to an invalid file descriptor. For example
11148 * GUI apps don't have valid standard streams by default.
11149 *
11150 * If this happens, and the optional fd argument is not present,
11151 * the ioctl below will fail returning EBADF. This is what we want.
11152 */
11153
11154 if (!PyArg_ParseTuple(args, "|i", &fd))
11155 return NULL;
11156
11157#ifdef TERMSIZE_USE_IOCTL
11158 {
11159 struct winsize w;
11160 if (ioctl(fd, TIOCGWINSZ, &w))
11161 return PyErr_SetFromErrno(PyExc_OSError);
11162 columns = w.ws_col;
11163 lines = w.ws_row;
11164 }
11165#endif /* TERMSIZE_USE_IOCTL */
11166
11167#ifdef TERMSIZE_USE_CONIO
11168 {
11169 DWORD nhandle;
11170 HANDLE handle;
11171 CONSOLE_SCREEN_BUFFER_INFO csbi;
11172 switch (fd) {
11173 case 0: nhandle = STD_INPUT_HANDLE;
11174 break;
11175 case 1: nhandle = STD_OUTPUT_HANDLE;
11176 break;
11177 case 2: nhandle = STD_ERROR_HANDLE;
11178 break;
11179 default:
11180 return PyErr_Format(PyExc_ValueError, "bad file descriptor");
11181 }
11182 handle = GetStdHandle(nhandle);
11183 if (handle == NULL)
11184 return PyErr_Format(PyExc_OSError, "handle cannot be retrieved");
11185 if (handle == INVALID_HANDLE_VALUE)
11186 return PyErr_SetFromWindowsErr(0);
11187
11188 if (!GetConsoleScreenBufferInfo(handle, &csbi))
11189 return PyErr_SetFromWindowsErr(0);
11190
11191 columns = csbi.srWindow.Right - csbi.srWindow.Left + 1;
11192 lines = csbi.srWindow.Bottom - csbi.srWindow.Top + 1;
11193 }
11194#endif /* TERMSIZE_USE_CONIO */
11195
11196 termsize = PyStructSequence_New(&TerminalSizeType);
11197 if (termsize == NULL)
11198 return NULL;
11199 PyStructSequence_SET_ITEM(termsize, 0, PyLong_FromLong(columns));
11200 PyStructSequence_SET_ITEM(termsize, 1, PyLong_FromLong(lines));
11201 if (PyErr_Occurred()) {
11202 Py_DECREF(termsize);
11203 return NULL;
11204 }
11205 return termsize;
11206}
11207#endif /* defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL) */
11208
Larry Hastings2f936352014-08-05 14:04:04 +100011209
11210/*[clinic input]
11211os.cpu_count
11212
Charles-François Natali80d62e62015-08-13 20:37:08 +010011213Return the number of CPUs in the system; return None if indeterminable.
11214
11215This number is not equivalent to the number of CPUs the current process can
11216use. The number of usable CPUs can be obtained with
11217``len(os.sched_getaffinity(0))``
Larry Hastings2f936352014-08-05 14:04:04 +100011218[clinic start generated code]*/
11219
Larry Hastings2f936352014-08-05 14:04:04 +100011220static PyObject *
11221os_cpu_count_impl(PyModuleDef *module)
Charles-François Natali80d62e62015-08-13 20:37:08 +010011222/*[clinic end generated code: output=c59ee7f6bce832b8 input=e7c8f4ba6dbbadd3]*/
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011223{
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020011224 int ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011225#ifdef MS_WINDOWS
11226 SYSTEM_INFO sysinfo;
11227 GetSystemInfo(&sysinfo);
11228 ncpu = sysinfo.dwNumberOfProcessors;
11229#elif defined(__hpux)
11230 ncpu = mpctl(MPC_GETNUMSPUS, NULL, NULL);
11231#elif defined(HAVE_SYSCONF) && defined(_SC_NPROCESSORS_ONLN)
11232 ncpu = sysconf(_SC_NPROCESSORS_ONLN);
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011233#elif defined(__DragonFly__) || \
11234 defined(__OpenBSD__) || \
11235 defined(__FreeBSD__) || \
Charles-Francois Natalid59087d2013-05-20 17:31:06 +020011236 defined(__NetBSD__) || \
11237 defined(__APPLE__)
Charles-Francois Natali7c4f8da2013-05-20 17:40:32 +020011238 int mib[2];
11239 size_t len = sizeof(ncpu);
11240 mib[0] = CTL_HW;
11241 mib[1] = HW_NCPU;
11242 if (sysctl(mib, 2, &ncpu, &len, NULL, 0) != 0)
11243 ncpu = 0;
Charles-Francois Natali44feda32013-05-20 14:40:46 +020011244#endif
11245 if (ncpu >= 1)
11246 return PyLong_FromLong(ncpu);
11247 else
11248 Py_RETURN_NONE;
11249}
11250
Victor Stinnerdaf45552013-08-28 00:53:59 +020011251
Larry Hastings2f936352014-08-05 14:04:04 +100011252/*[clinic input]
11253os.get_inheritable -> bool
11254
11255 fd: int
11256 /
11257
11258Get the close-on-exe flag of the specified file descriptor.
11259[clinic start generated code]*/
11260
Larry Hastings2f936352014-08-05 14:04:04 +100011261static int
11262os_get_inheritable_impl(PyModuleDef *module, int fd)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011263/*[clinic end generated code: output=36110bb36efaa21e input=89ac008dc9ab6b95]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011264{
Steve Dower8fc89802015-04-12 00:26:27 -040011265 int return_value;
11266 if (!_PyVerify_fd(fd)) {
Larry Hastings2f936352014-08-05 14:04:04 +100011267 posix_error();
11268 return -1;
11269 }
11270
Steve Dower8fc89802015-04-12 00:26:27 -040011271 _Py_BEGIN_SUPPRESS_IPH
11272 return_value = _Py_get_inheritable(fd);
11273 _Py_END_SUPPRESS_IPH
11274 return return_value;
Larry Hastings2f936352014-08-05 14:04:04 +100011275}
11276
11277
11278/*[clinic input]
11279os.set_inheritable
11280 fd: int
11281 inheritable: int
11282 /
11283
11284Set the inheritable flag of the specified file descriptor.
11285[clinic start generated code]*/
11286
Larry Hastings2f936352014-08-05 14:04:04 +100011287static PyObject *
11288os_set_inheritable_impl(PyModuleDef *module, int fd, int inheritable)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011289/*[clinic end generated code: output=2ac5c6ce8623f045 input=9ceaead87a1e2402]*/
Victor Stinnerdaf45552013-08-28 00:53:59 +020011290{
Steve Dower8fc89802015-04-12 00:26:27 -040011291 int result;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011292 if (!_PyVerify_fd(fd))
11293 return posix_error();
11294
Steve Dower8fc89802015-04-12 00:26:27 -040011295 _Py_BEGIN_SUPPRESS_IPH
11296 result = _Py_set_inheritable(fd, inheritable, NULL);
11297 _Py_END_SUPPRESS_IPH
11298 if (result < 0)
Victor Stinnerdaf45552013-08-28 00:53:59 +020011299 return NULL;
11300 Py_RETURN_NONE;
11301}
11302
11303
11304#ifdef MS_WINDOWS
Larry Hastings2f936352014-08-05 14:04:04 +100011305/*[clinic input]
11306os.get_handle_inheritable -> bool
11307 handle: Py_intptr_t
11308 /
Victor Stinnerdaf45552013-08-28 00:53:59 +020011309
Larry Hastings2f936352014-08-05 14:04:04 +100011310Get the close-on-exe flag of the specified file descriptor.
11311[clinic start generated code]*/
11312
Larry Hastings2f936352014-08-05 14:04:04 +100011313static int
11314os_get_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle)
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030011315/*[clinic end generated code: output=3b7b3e1b43f312b6 input=5f7759443aae3dc5]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011316{
11317 DWORD flags;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011318
11319 if (!GetHandleInformation((HANDLE)handle, &flags)) {
11320 PyErr_SetFromWindowsErr(0);
Larry Hastings2f936352014-08-05 14:04:04 +100011321 return -1;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011322 }
11323
Larry Hastings2f936352014-08-05 14:04:04 +100011324 return flags & HANDLE_FLAG_INHERIT;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011325}
11326
Victor Stinnerdaf45552013-08-28 00:53:59 +020011327
Larry Hastings2f936352014-08-05 14:04:04 +100011328/*[clinic input]
11329os.set_handle_inheritable
11330 handle: Py_intptr_t
11331 inheritable: bool
11332 /
11333
11334Set the inheritable flag of the specified handle.
11335[clinic start generated code]*/
11336
Larry Hastings2f936352014-08-05 14:04:04 +100011337static PyObject *
Larry Hastings89964c42015-04-14 18:07:59 -040011338os_set_handle_inheritable_impl(PyModuleDef *module, Py_intptr_t handle,
11339 int inheritable)
11340/*[clinic end generated code: output=d2e111a96c9eb296 input=e64b2b2730469def]*/
Larry Hastings2f936352014-08-05 14:04:04 +100011341{
11342 DWORD flags = inheritable ? HANDLE_FLAG_INHERIT : 0;
Victor Stinnerdaf45552013-08-28 00:53:59 +020011343 if (!SetHandleInformation((HANDLE)handle, HANDLE_FLAG_INHERIT, flags)) {
11344 PyErr_SetFromWindowsErr(0);
11345 return NULL;
11346 }
11347 Py_RETURN_NONE;
11348}
Larry Hastings2f936352014-08-05 14:04:04 +100011349#endif /* MS_WINDOWS */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010011350
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011351#ifndef MS_WINDOWS
11352PyDoc_STRVAR(get_blocking__doc__,
11353 "get_blocking(fd) -> bool\n" \
11354 "\n" \
11355 "Get the blocking mode of the file descriptor:\n" \
11356 "False if the O_NONBLOCK flag is set, True if the flag is cleared.");
11357
11358static PyObject*
11359posix_get_blocking(PyObject *self, PyObject *args)
11360{
11361 int fd;
11362 int blocking;
11363
11364 if (!PyArg_ParseTuple(args, "i:get_blocking", &fd))
11365 return NULL;
11366
11367 if (!_PyVerify_fd(fd))
11368 return posix_error();
11369
Steve Dower8fc89802015-04-12 00:26:27 -040011370 _Py_BEGIN_SUPPRESS_IPH
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011371 blocking = _Py_get_blocking(fd);
Steve Dower8fc89802015-04-12 00:26:27 -040011372 _Py_END_SUPPRESS_IPH
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011373 if (blocking < 0)
11374 return NULL;
11375 return PyBool_FromLong(blocking);
11376}
11377
11378PyDoc_STRVAR(set_blocking__doc__,
11379 "set_blocking(fd, blocking)\n" \
11380 "\n" \
11381 "Set the blocking mode of the specified file descriptor.\n" \
11382 "Set the O_NONBLOCK flag if blocking is False,\n" \
11383 "clear the O_NONBLOCK flag otherwise.");
11384
11385static PyObject*
11386posix_set_blocking(PyObject *self, PyObject *args)
11387{
Steve Dower8fc89802015-04-12 00:26:27 -040011388 int fd, blocking, result;
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011389
11390 if (!PyArg_ParseTuple(args, "ii:set_blocking", &fd, &blocking))
11391 return NULL;
11392
11393 if (!_PyVerify_fd(fd))
11394 return posix_error();
11395
Steve Dower8fc89802015-04-12 00:26:27 -040011396 _Py_BEGIN_SUPPRESS_IPH
11397 result = _Py_set_blocking(fd, blocking);
11398 _Py_END_SUPPRESS_IPH
11399 if (result < 0)
Victor Stinner1db9e7b2014-07-29 22:32:47 +020011400 return NULL;
11401 Py_RETURN_NONE;
11402}
11403#endif /* !MS_WINDOWS */
11404
11405
Victor Stinner6036e442015-03-08 01:58:04 +010011406PyDoc_STRVAR(posix_scandir__doc__,
11407"scandir(path='.') -> iterator of DirEntry objects for given path");
11408
11409static char *follow_symlinks_keywords[] = {"follow_symlinks", NULL};
11410
11411typedef struct {
11412 PyObject_HEAD
11413 PyObject *name;
11414 PyObject *path;
11415 PyObject *stat;
11416 PyObject *lstat;
11417#ifdef MS_WINDOWS
11418 struct _Py_stat_struct win32_lstat;
11419 __int64 win32_file_index;
11420 int got_file_index;
11421#else /* POSIX */
Victor Stinner35a97c02015-03-08 02:59:09 +010011422#ifdef HAVE_DIRENT_D_TYPE
Victor Stinner6036e442015-03-08 01:58:04 +010011423 unsigned char d_type;
Victor Stinner35a97c02015-03-08 02:59:09 +010011424#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011425 ino_t d_ino;
11426#endif
11427} DirEntry;
11428
11429static void
11430DirEntry_dealloc(DirEntry *entry)
11431{
11432 Py_XDECREF(entry->name);
11433 Py_XDECREF(entry->path);
11434 Py_XDECREF(entry->stat);
11435 Py_XDECREF(entry->lstat);
11436 Py_TYPE(entry)->tp_free((PyObject *)entry);
11437}
11438
11439/* Forward reference */
11440static int
11441DirEntry_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits);
11442
11443/* Set exception and return -1 on error, 0 for False, 1 for True */
11444static int
11445DirEntry_is_symlink(DirEntry *self)
11446{
11447#ifdef MS_WINDOWS
11448 return (self->win32_lstat.st_mode & S_IFMT) == S_IFLNK;
Victor Stinner35a97c02015-03-08 02:59:09 +010011449#elif defined(HAVE_DIRENT_D_TYPE)
11450 /* POSIX */
Victor Stinner6036e442015-03-08 01:58:04 +010011451 if (self->d_type != DT_UNKNOWN)
11452 return self->d_type == DT_LNK;
11453 else
11454 return DirEntry_test_mode(self, 0, S_IFLNK);
Victor Stinner35a97c02015-03-08 02:59:09 +010011455#else
11456 /* POSIX without d_type */
11457 return DirEntry_test_mode(self, 0, S_IFLNK);
Victor Stinner6036e442015-03-08 01:58:04 +010011458#endif
11459}
11460
11461static PyObject *
11462DirEntry_py_is_symlink(DirEntry *self)
11463{
11464 int result;
11465
11466 result = DirEntry_is_symlink(self);
11467 if (result == -1)
11468 return NULL;
11469 return PyBool_FromLong(result);
11470}
11471
11472static PyObject *
11473DirEntry_fetch_stat(DirEntry *self, int follow_symlinks)
11474{
11475 int result;
11476 struct _Py_stat_struct st;
11477
11478#ifdef MS_WINDOWS
11479 wchar_t *path;
11480
11481 path = PyUnicode_AsUnicode(self->path);
11482 if (!path)
11483 return NULL;
11484
11485 if (follow_symlinks)
11486 result = win32_stat_w(path, &st);
11487 else
11488 result = win32_lstat_w(path, &st);
11489
11490 if (result != 0) {
11491 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
11492 0, self->path);
11493 }
11494#else /* POSIX */
11495 PyObject *bytes;
11496 char *path;
11497
11498 if (!PyUnicode_FSConverter(self->path, &bytes))
11499 return NULL;
11500 path = PyBytes_AS_STRING(bytes);
11501
11502 if (follow_symlinks)
11503 result = STAT(path, &st);
11504 else
11505 result = LSTAT(path, &st);
11506 Py_DECREF(bytes);
11507
11508 if (result != 0)
11509 return PyErr_SetFromErrnoWithFilenameObject(PyExc_OSError, self->path);
11510#endif
11511
11512 return _pystat_fromstructstat(&st);
11513}
11514
11515static PyObject *
11516DirEntry_get_lstat(DirEntry *self)
11517{
11518 if (!self->lstat) {
11519#ifdef MS_WINDOWS
11520 self->lstat = _pystat_fromstructstat(&self->win32_lstat);
11521#else /* POSIX */
11522 self->lstat = DirEntry_fetch_stat(self, 0);
11523#endif
11524 }
11525 Py_XINCREF(self->lstat);
11526 return self->lstat;
11527}
11528
11529static PyObject *
11530DirEntry_get_stat(DirEntry *self, int follow_symlinks)
11531{
11532 if (!follow_symlinks)
11533 return DirEntry_get_lstat(self);
11534
11535 if (!self->stat) {
11536 int result = DirEntry_is_symlink(self);
11537 if (result == -1)
11538 return NULL;
11539 else if (result)
11540 self->stat = DirEntry_fetch_stat(self, 1);
11541 else
11542 self->stat = DirEntry_get_lstat(self);
11543 }
11544
11545 Py_XINCREF(self->stat);
11546 return self->stat;
11547}
11548
11549static PyObject *
11550DirEntry_stat(DirEntry *self, PyObject *args, PyObject *kwargs)
11551{
11552 int follow_symlinks = 1;
11553
11554 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.stat",
11555 follow_symlinks_keywords, &follow_symlinks))
11556 return NULL;
11557
11558 return DirEntry_get_stat(self, follow_symlinks);
11559}
11560
11561/* Set exception and return -1 on error, 0 for False, 1 for True */
11562static int
11563DirEntry_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits)
11564{
11565 PyObject *stat = NULL;
11566 PyObject *st_mode = NULL;
11567 long mode;
11568 int result;
Victor Stinner35a97c02015-03-08 02:59:09 +010011569#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011570 int is_symlink;
11571 int need_stat;
Victor Stinner35a97c02015-03-08 02:59:09 +010011572#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011573#ifdef MS_WINDOWS
11574 unsigned long dir_bits;
11575#endif
Victor Stinner35a97c02015-03-08 02:59:09 +010011576 _Py_IDENTIFIER(st_mode);
Victor Stinner6036e442015-03-08 01:58:04 +010011577
11578#ifdef MS_WINDOWS
11579 is_symlink = (self->win32_lstat.st_mode & S_IFMT) == S_IFLNK;
11580 need_stat = follow_symlinks && is_symlink;
Victor Stinner35a97c02015-03-08 02:59:09 +010011581#elif defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011582 is_symlink = self->d_type == DT_LNK;
11583 need_stat = self->d_type == DT_UNKNOWN || (follow_symlinks && is_symlink);
11584#endif
11585
Victor Stinner35a97c02015-03-08 02:59:09 +010011586#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011587 if (need_stat) {
Victor Stinner35a97c02015-03-08 02:59:09 +010011588#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011589 stat = DirEntry_get_stat(self, follow_symlinks);
11590 if (!stat) {
11591 if (PyErr_ExceptionMatches(PyExc_FileNotFoundError)) {
11592 /* If file doesn't exist (anymore), then return False
11593 (i.e., say it's not a file/directory) */
11594 PyErr_Clear();
11595 return 0;
11596 }
11597 goto error;
11598 }
11599 st_mode = _PyObject_GetAttrId(stat, &PyId_st_mode);
11600 if (!st_mode)
11601 goto error;
11602
11603 mode = PyLong_AsLong(st_mode);
11604 if (mode == -1 && PyErr_Occurred())
11605 goto error;
11606 Py_CLEAR(st_mode);
11607 Py_CLEAR(stat);
11608 result = (mode & S_IFMT) == mode_bits;
Victor Stinner35a97c02015-03-08 02:59:09 +010011609#if defined(MS_WINDOWS) || defined(HAVE_DIRENT_D_TYPE)
Victor Stinner6036e442015-03-08 01:58:04 +010011610 }
11611 else if (is_symlink) {
11612 assert(mode_bits != S_IFLNK);
11613 result = 0;
11614 }
11615 else {
11616 assert(mode_bits == S_IFDIR || mode_bits == S_IFREG);
11617#ifdef MS_WINDOWS
11618 dir_bits = self->win32_lstat.st_file_attributes & FILE_ATTRIBUTE_DIRECTORY;
11619 if (mode_bits == S_IFDIR)
11620 result = dir_bits != 0;
11621 else
11622 result = dir_bits == 0;
11623#else /* POSIX */
11624 if (mode_bits == S_IFDIR)
11625 result = self->d_type == DT_DIR;
11626 else
11627 result = self->d_type == DT_REG;
11628#endif
11629 }
Victor Stinner35a97c02015-03-08 02:59:09 +010011630#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011631
11632 return result;
11633
11634error:
11635 Py_XDECREF(st_mode);
11636 Py_XDECREF(stat);
11637 return -1;
11638}
11639
11640static PyObject *
11641DirEntry_py_test_mode(DirEntry *self, int follow_symlinks, unsigned short mode_bits)
11642{
11643 int result;
11644
11645 result = DirEntry_test_mode(self, follow_symlinks, mode_bits);
11646 if (result == -1)
11647 return NULL;
11648 return PyBool_FromLong(result);
11649}
11650
11651static PyObject *
11652DirEntry_is_dir(DirEntry *self, PyObject *args, PyObject *kwargs)
11653{
11654 int follow_symlinks = 1;
11655
11656 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.is_dir",
11657 follow_symlinks_keywords, &follow_symlinks))
11658 return NULL;
11659
11660 return DirEntry_py_test_mode(self, follow_symlinks, S_IFDIR);
11661}
11662
11663static PyObject *
11664DirEntry_is_file(DirEntry *self, PyObject *args, PyObject *kwargs)
11665{
11666 int follow_symlinks = 1;
11667
11668 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|$p:DirEntry.is_file",
11669 follow_symlinks_keywords, &follow_symlinks))
11670 return NULL;
11671
11672 return DirEntry_py_test_mode(self, follow_symlinks, S_IFREG);
11673}
11674
11675static PyObject *
11676DirEntry_inode(DirEntry *self)
11677{
11678#ifdef MS_WINDOWS
11679 if (!self->got_file_index) {
11680 wchar_t *path;
11681 struct _Py_stat_struct stat;
11682
11683 path = PyUnicode_AsUnicode(self->path);
11684 if (!path)
11685 return NULL;
11686
11687 if (win32_lstat_w(path, &stat) != 0) {
11688 return PyErr_SetExcFromWindowsErrWithFilenameObject(PyExc_OSError,
11689 0, self->path);
11690 }
11691
11692 self->win32_file_index = stat.st_ino;
11693 self->got_file_index = 1;
11694 }
11695 return PyLong_FromLongLong((PY_LONG_LONG)self->win32_file_index);
11696#else /* POSIX */
11697#ifdef HAVE_LARGEFILE_SUPPORT
11698 return PyLong_FromLongLong((PY_LONG_LONG)self->d_ino);
11699#else
11700 return PyLong_FromLong((long)self->d_ino);
11701#endif
11702#endif
11703}
11704
11705static PyObject *
11706DirEntry_repr(DirEntry *self)
11707{
11708 return PyUnicode_FromFormat("<DirEntry %R>", self->name);
11709}
11710
11711static PyMemberDef DirEntry_members[] = {
11712 {"name", T_OBJECT_EX, offsetof(DirEntry, name), READONLY,
11713 "the entry's base filename, relative to scandir() \"path\" argument"},
11714 {"path", T_OBJECT_EX, offsetof(DirEntry, path), READONLY,
11715 "the entry's full path name; equivalent to os.path.join(scandir_path, entry.name)"},
11716 {NULL}
11717};
11718
11719static PyMethodDef DirEntry_methods[] = {
11720 {"is_dir", (PyCFunction)DirEntry_is_dir, METH_VARARGS | METH_KEYWORDS,
11721 "return True if the entry is a directory; cached per entry"
11722 },
11723 {"is_file", (PyCFunction)DirEntry_is_file, METH_VARARGS | METH_KEYWORDS,
11724 "return True if the entry is a file; cached per entry"
11725 },
11726 {"is_symlink", (PyCFunction)DirEntry_py_is_symlink, METH_NOARGS,
11727 "return True if the entry is a symbolic link; cached per entry"
11728 },
11729 {"stat", (PyCFunction)DirEntry_stat, METH_VARARGS | METH_KEYWORDS,
11730 "return stat_result object for the entry; cached per entry"
11731 },
11732 {"inode", (PyCFunction)DirEntry_inode, METH_NOARGS,
11733 "return inode of the entry; cached per entry",
11734 },
11735 {NULL}
11736};
11737
Benjamin Peterson5646de42015-04-12 17:56:34 -040011738static PyTypeObject DirEntryType = {
Victor Stinner6036e442015-03-08 01:58:04 +010011739 PyVarObject_HEAD_INIT(NULL, 0)
11740 MODNAME ".DirEntry", /* tp_name */
11741 sizeof(DirEntry), /* tp_basicsize */
11742 0, /* tp_itemsize */
11743 /* methods */
11744 (destructor)DirEntry_dealloc, /* tp_dealloc */
11745 0, /* tp_print */
11746 0, /* tp_getattr */
11747 0, /* tp_setattr */
11748 0, /* tp_compare */
11749 (reprfunc)DirEntry_repr, /* tp_repr */
11750 0, /* tp_as_number */
11751 0, /* tp_as_sequence */
11752 0, /* tp_as_mapping */
11753 0, /* tp_hash */
11754 0, /* tp_call */
11755 0, /* tp_str */
11756 0, /* tp_getattro */
11757 0, /* tp_setattro */
11758 0, /* tp_as_buffer */
11759 Py_TPFLAGS_DEFAULT, /* tp_flags */
11760 0, /* tp_doc */
11761 0, /* tp_traverse */
11762 0, /* tp_clear */
11763 0, /* tp_richcompare */
11764 0, /* tp_weaklistoffset */
11765 0, /* tp_iter */
11766 0, /* tp_iternext */
11767 DirEntry_methods, /* tp_methods */
11768 DirEntry_members, /* tp_members */
11769};
11770
11771#ifdef MS_WINDOWS
11772
11773static wchar_t *
11774join_path_filenameW(wchar_t *path_wide, wchar_t* filename)
11775{
11776 Py_ssize_t path_len;
11777 Py_ssize_t size;
11778 wchar_t *result;
11779 wchar_t ch;
11780
11781 if (!path_wide) { /* Default arg: "." */
11782 path_wide = L".";
11783 path_len = 1;
11784 }
11785 else {
11786 path_len = wcslen(path_wide);
11787 }
11788
11789 /* The +1's are for the path separator and the NUL */
11790 size = path_len + 1 + wcslen(filename) + 1;
11791 result = PyMem_New(wchar_t, size);
11792 if (!result) {
11793 PyErr_NoMemory();
11794 return NULL;
11795 }
11796 wcscpy(result, path_wide);
11797 if (path_len > 0) {
11798 ch = result[path_len - 1];
11799 if (ch != SEP && ch != ALTSEP && ch != L':')
11800 result[path_len++] = SEP;
11801 wcscpy(result + path_len, filename);
11802 }
11803 return result;
11804}
11805
11806static PyObject *
11807DirEntry_from_find_data(path_t *path, WIN32_FIND_DATAW *dataW)
11808{
11809 DirEntry *entry;
11810 BY_HANDLE_FILE_INFORMATION file_info;
11811 ULONG reparse_tag;
11812 wchar_t *joined_path;
11813
11814 entry = PyObject_New(DirEntry, &DirEntryType);
11815 if (!entry)
11816 return NULL;
11817 entry->name = NULL;
11818 entry->path = NULL;
11819 entry->stat = NULL;
11820 entry->lstat = NULL;
11821 entry->got_file_index = 0;
11822
11823 entry->name = PyUnicode_FromWideChar(dataW->cFileName, -1);
11824 if (!entry->name)
11825 goto error;
11826
11827 joined_path = join_path_filenameW(path->wide, dataW->cFileName);
11828 if (!joined_path)
11829 goto error;
11830
11831 entry->path = PyUnicode_FromWideChar(joined_path, -1);
11832 PyMem_Free(joined_path);
11833 if (!entry->path)
11834 goto error;
11835
11836 find_data_to_file_info_w(dataW, &file_info, &reparse_tag);
11837 _Py_attribute_data_to_stat(&file_info, reparse_tag, &entry->win32_lstat);
11838
11839 return (PyObject *)entry;
11840
11841error:
11842 Py_DECREF(entry);
11843 return NULL;
11844}
11845
11846#else /* POSIX */
11847
11848static char *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +020011849join_path_filename(const char *path_narrow, const char* filename, Py_ssize_t filename_len)
Victor Stinner6036e442015-03-08 01:58:04 +010011850{
11851 Py_ssize_t path_len;
11852 Py_ssize_t size;
11853 char *result;
11854
11855 if (!path_narrow) { /* Default arg: "." */
11856 path_narrow = ".";
11857 path_len = 1;
11858 }
11859 else {
11860 path_len = strlen(path_narrow);
11861 }
11862
11863 if (filename_len == -1)
11864 filename_len = strlen(filename);
11865
11866 /* The +1's are for the path separator and the NUL */
11867 size = path_len + 1 + filename_len + 1;
11868 result = PyMem_New(char, size);
11869 if (!result) {
11870 PyErr_NoMemory();
11871 return NULL;
11872 }
11873 strcpy(result, path_narrow);
11874 if (path_len > 0 && result[path_len - 1] != '/')
11875 result[path_len++] = '/';
11876 strcpy(result + path_len, filename);
11877 return result;
11878}
11879
11880static PyObject *
Serhiy Storchakaef1585e2015-12-25 20:01:53 +020011881DirEntry_from_posix_info(path_t *path, const char *name, Py_ssize_t name_len,
Victor Stinner35a97c02015-03-08 02:59:09 +010011882 ino_t d_ino
11883#ifdef HAVE_DIRENT_D_TYPE
11884 , unsigned char d_type
11885#endif
11886 )
Victor Stinner6036e442015-03-08 01:58:04 +010011887{
11888 DirEntry *entry;
11889 char *joined_path;
11890
11891 entry = PyObject_New(DirEntry, &DirEntryType);
11892 if (!entry)
11893 return NULL;
11894 entry->name = NULL;
11895 entry->path = NULL;
11896 entry->stat = NULL;
11897 entry->lstat = NULL;
11898
11899 joined_path = join_path_filename(path->narrow, name, name_len);
11900 if (!joined_path)
11901 goto error;
11902
11903 if (!path->narrow || !PyBytes_Check(path->object)) {
11904 entry->name = PyUnicode_DecodeFSDefaultAndSize(name, name_len);
11905 entry->path = PyUnicode_DecodeFSDefault(joined_path);
11906 }
11907 else {
11908 entry->name = PyBytes_FromStringAndSize(name, name_len);
11909 entry->path = PyBytes_FromString(joined_path);
11910 }
11911 PyMem_Free(joined_path);
11912 if (!entry->name || !entry->path)
11913 goto error;
11914
Victor Stinner35a97c02015-03-08 02:59:09 +010011915#ifdef HAVE_DIRENT_D_TYPE
Victor Stinner6036e442015-03-08 01:58:04 +010011916 entry->d_type = d_type;
Victor Stinner35a97c02015-03-08 02:59:09 +010011917#endif
Victor Stinner6036e442015-03-08 01:58:04 +010011918 entry->d_ino = d_ino;
11919
11920 return (PyObject *)entry;
11921
11922error:
11923 Py_XDECREF(entry);
11924 return NULL;
11925}
11926
11927#endif
11928
11929
11930typedef struct {
11931 PyObject_HEAD
11932 path_t path;
11933#ifdef MS_WINDOWS
11934 HANDLE handle;
11935 WIN32_FIND_DATAW file_data;
11936 int first_time;
11937#else /* POSIX */
11938 DIR *dirp;
11939#endif
11940} ScandirIterator;
11941
11942#ifdef MS_WINDOWS
11943
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020011944static int
11945ScandirIterator_is_closed(ScandirIterator *iterator)
11946{
11947 return iterator->handle == INVALID_HANDLE_VALUE;
11948}
11949
Victor Stinner6036e442015-03-08 01:58:04 +010011950static void
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020011951ScandirIterator_closedir(ScandirIterator *iterator)
Victor Stinner6036e442015-03-08 01:58:04 +010011952{
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +030011953 HANDLE handle = iterator->handle;
11954
11955 if (handle == INVALID_HANDLE_VALUE)
Victor Stinner6036e442015-03-08 01:58:04 +010011956 return;
11957
Victor Stinner6036e442015-03-08 01:58:04 +010011958 iterator->handle = INVALID_HANDLE_VALUE;
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +030011959 Py_BEGIN_ALLOW_THREADS
11960 FindClose(handle);
11961 Py_END_ALLOW_THREADS
Victor Stinner6036e442015-03-08 01:58:04 +010011962}
11963
11964static PyObject *
11965ScandirIterator_iternext(ScandirIterator *iterator)
11966{
11967 WIN32_FIND_DATAW *file_data = &iterator->file_data;
11968 BOOL success;
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020011969 PyObject *entry;
Victor Stinner6036e442015-03-08 01:58:04 +010011970
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020011971 /* Happens if the iterator is iterated twice, or closed explicitly */
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020011972 if (iterator->handle == INVALID_HANDLE_VALUE)
Victor Stinner6036e442015-03-08 01:58:04 +010011973 return NULL;
Victor Stinner6036e442015-03-08 01:58:04 +010011974
11975 while (1) {
11976 if (!iterator->first_time) {
11977 Py_BEGIN_ALLOW_THREADS
11978 success = FindNextFileW(iterator->handle, file_data);
11979 Py_END_ALLOW_THREADS
11980 if (!success) {
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020011981 /* Error or no more files */
Victor Stinner6036e442015-03-08 01:58:04 +010011982 if (GetLastError() != ERROR_NO_MORE_FILES)
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020011983 path_error(&iterator->path);
Victor Stinner6036e442015-03-08 01:58:04 +010011984 break;
11985 }
11986 }
11987 iterator->first_time = 0;
11988
11989 /* Skip over . and .. */
11990 if (wcscmp(file_data->cFileName, L".") != 0 &&
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020011991 wcscmp(file_data->cFileName, L"..") != 0) {
11992 entry = DirEntry_from_find_data(&iterator->path, file_data);
11993 if (!entry)
11994 break;
11995 return entry;
11996 }
Victor Stinner6036e442015-03-08 01:58:04 +010011997
11998 /* Loop till we get a non-dot directory or finish iterating */
11999 }
12000
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012001 /* Error or no more files */
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012002 ScandirIterator_closedir(iterator);
Victor Stinner6036e442015-03-08 01:58:04 +010012003 return NULL;
12004}
12005
12006#else /* POSIX */
12007
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012008static int
12009ScandirIterator_is_closed(ScandirIterator *iterator)
12010{
12011 return !iterator->dirp;
12012}
12013
Victor Stinner6036e442015-03-08 01:58:04 +010012014static void
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012015ScandirIterator_closedir(ScandirIterator *iterator)
Victor Stinner6036e442015-03-08 01:58:04 +010012016{
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +030012017 DIR *dirp = iterator->dirp;
12018
12019 if (!dirp)
Victor Stinner6036e442015-03-08 01:58:04 +010012020 return;
12021
Victor Stinner6036e442015-03-08 01:58:04 +010012022 iterator->dirp = NULL;
Serhiy Storchakafbb1c5e2016-03-30 20:40:02 +030012023 Py_BEGIN_ALLOW_THREADS
12024 closedir(dirp);
12025 Py_END_ALLOW_THREADS
Victor Stinner6036e442015-03-08 01:58:04 +010012026 return;
12027}
12028
12029static PyObject *
12030ScandirIterator_iternext(ScandirIterator *iterator)
12031{
12032 struct dirent *direntp;
12033 Py_ssize_t name_len;
12034 int is_dot;
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012035 PyObject *entry;
Victor Stinner6036e442015-03-08 01:58:04 +010012036
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012037 /* Happens if the iterator is iterated twice, or closed explicitly */
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012038 if (!iterator->dirp)
Victor Stinner6036e442015-03-08 01:58:04 +010012039 return NULL;
Victor Stinner6036e442015-03-08 01:58:04 +010012040
12041 while (1) {
12042 errno = 0;
12043 Py_BEGIN_ALLOW_THREADS
12044 direntp = readdir(iterator->dirp);
12045 Py_END_ALLOW_THREADS
12046
12047 if (!direntp) {
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012048 /* Error or no more files */
Victor Stinner6036e442015-03-08 01:58:04 +010012049 if (errno != 0)
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012050 path_error(&iterator->path);
Victor Stinner6036e442015-03-08 01:58:04 +010012051 break;
12052 }
12053
12054 /* Skip over . and .. */
12055 name_len = NAMLEN(direntp);
12056 is_dot = direntp->d_name[0] == '.' &&
12057 (name_len == 1 || (direntp->d_name[1] == '.' && name_len == 2));
12058 if (!is_dot) {
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012059 entry = DirEntry_from_posix_info(&iterator->path, direntp->d_name,
Victor Stinner35a97c02015-03-08 02:59:09 +010012060 name_len, direntp->d_ino
12061#ifdef HAVE_DIRENT_D_TYPE
12062 , direntp->d_type
12063#endif
12064 );
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012065 if (!entry)
12066 break;
12067 return entry;
Victor Stinner6036e442015-03-08 01:58:04 +010012068 }
12069
12070 /* Loop till we get a non-dot directory or finish iterating */
12071 }
12072
Serhiy Storchaka988b9bc2016-02-08 17:56:36 +020012073 /* Error or no more files */
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012074 ScandirIterator_closedir(iterator);
Victor Stinner6036e442015-03-08 01:58:04 +010012075 return NULL;
12076}
12077
12078#endif
12079
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012080static PyObject *
12081ScandirIterator_close(ScandirIterator *self, PyObject *args)
12082{
12083 ScandirIterator_closedir(self);
12084 Py_RETURN_NONE;
12085}
12086
12087static PyObject *
12088ScandirIterator_enter(PyObject *self, PyObject *args)
12089{
12090 Py_INCREF(self);
12091 return self;
12092}
12093
12094static PyObject *
12095ScandirIterator_exit(ScandirIterator *self, PyObject *args)
12096{
12097 ScandirIterator_closedir(self);
12098 Py_RETURN_NONE;
12099}
12100
Victor Stinner6036e442015-03-08 01:58:04 +010012101static void
Victor Stinner7bfa4092016-03-23 00:43:54 +010012102ScandirIterator_finalize(ScandirIterator *iterator)
12103{
12104 PyObject *error_type, *error_value, *error_traceback;
12105
12106 /* Save the current exception, if any. */
12107 PyErr_Fetch(&error_type, &error_value, &error_traceback);
12108
12109 if (!ScandirIterator_is_closed(iterator)) {
12110 ScandirIterator_closedir(iterator);
12111
12112 if (PyErr_ResourceWarning((PyObject *)iterator, 1,
12113 "unclosed scandir iterator %R", iterator)) {
12114 /* Spurious errors can appear at shutdown */
12115 if (PyErr_ExceptionMatches(PyExc_Warning)) {
12116 PyErr_WriteUnraisable((PyObject *) iterator);
12117 }
12118 }
12119 }
12120
12121 Py_CLEAR(iterator->path.object);
12122 path_cleanup(&iterator->path);
12123
12124 /* Restore the saved exception. */
12125 PyErr_Restore(error_type, error_value, error_traceback);
12126}
12127
12128static void
Victor Stinner6036e442015-03-08 01:58:04 +010012129ScandirIterator_dealloc(ScandirIterator *iterator)
12130{
Victor Stinner7bfa4092016-03-23 00:43:54 +010012131 if (PyObject_CallFinalizerFromDealloc((PyObject *)iterator) < 0)
12132 return;
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012133
Victor Stinner6036e442015-03-08 01:58:04 +010012134 Py_TYPE(iterator)->tp_free((PyObject *)iterator);
12135}
12136
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012137static PyMethodDef ScandirIterator_methods[] = {
12138 {"__enter__", (PyCFunction)ScandirIterator_enter, METH_NOARGS},
12139 {"__exit__", (PyCFunction)ScandirIterator_exit, METH_VARARGS},
12140 {"close", (PyCFunction)ScandirIterator_close, METH_NOARGS},
12141 {NULL}
12142};
12143
Benjamin Peterson5646de42015-04-12 17:56:34 -040012144static PyTypeObject ScandirIteratorType = {
Victor Stinner6036e442015-03-08 01:58:04 +010012145 PyVarObject_HEAD_INIT(NULL, 0)
12146 MODNAME ".ScandirIterator", /* tp_name */
12147 sizeof(ScandirIterator), /* tp_basicsize */
12148 0, /* tp_itemsize */
12149 /* methods */
12150 (destructor)ScandirIterator_dealloc, /* tp_dealloc */
12151 0, /* tp_print */
12152 0, /* tp_getattr */
12153 0, /* tp_setattr */
12154 0, /* tp_compare */
12155 0, /* tp_repr */
12156 0, /* tp_as_number */
12157 0, /* tp_as_sequence */
12158 0, /* tp_as_mapping */
12159 0, /* tp_hash */
12160 0, /* tp_call */
12161 0, /* tp_str */
12162 0, /* tp_getattro */
12163 0, /* tp_setattro */
12164 0, /* tp_as_buffer */
Victor Stinner7bfa4092016-03-23 00:43:54 +010012165 Py_TPFLAGS_DEFAULT
12166 | Py_TPFLAGS_HAVE_FINALIZE, /* tp_flags */
Victor Stinner6036e442015-03-08 01:58:04 +010012167 0, /* tp_doc */
12168 0, /* tp_traverse */
12169 0, /* tp_clear */
12170 0, /* tp_richcompare */
12171 0, /* tp_weaklistoffset */
12172 PyObject_SelfIter, /* tp_iter */
12173 (iternextfunc)ScandirIterator_iternext, /* tp_iternext */
Serhiy Storchakaffe96ae2016-02-11 13:21:30 +020012174 ScandirIterator_methods, /* tp_methods */
Victor Stinner7bfa4092016-03-23 00:43:54 +010012175 0, /* tp_members */
12176 0, /* tp_getset */
12177 0, /* tp_base */
12178 0, /* tp_dict */
12179 0, /* tp_descr_get */
12180 0, /* tp_descr_set */
12181 0, /* tp_dictoffset */
12182 0, /* tp_init */
12183 0, /* tp_alloc */
12184 0, /* tp_new */
12185 0, /* tp_free */
12186 0, /* tp_is_gc */
12187 0, /* tp_bases */
12188 0, /* tp_mro */
12189 0, /* tp_cache */
12190 0, /* tp_subclasses */
12191 0, /* tp_weaklist */
12192 0, /* tp_del */
12193 0, /* tp_version_tag */
12194 (destructor)ScandirIterator_finalize, /* tp_finalize */
Victor Stinner6036e442015-03-08 01:58:04 +010012195};
12196
12197static PyObject *
12198posix_scandir(PyObject *self, PyObject *args, PyObject *kwargs)
12199{
12200 ScandirIterator *iterator;
12201 static char *keywords[] = {"path", NULL};
12202#ifdef MS_WINDOWS
12203 wchar_t *path_strW;
12204#else
12205 char *path;
12206#endif
12207
12208 iterator = PyObject_New(ScandirIterator, &ScandirIteratorType);
12209 if (!iterator)
12210 return NULL;
12211 memset(&iterator->path, 0, sizeof(path_t));
12212 iterator->path.function_name = "scandir";
12213 iterator->path.nullable = 1;
12214
12215#ifdef MS_WINDOWS
12216 iterator->handle = INVALID_HANDLE_VALUE;
12217#else
12218 iterator->dirp = NULL;
12219#endif
12220
12221 if (!PyArg_ParseTupleAndKeywords(args, kwargs, "|O&:scandir", keywords,
12222 path_converter, &iterator->path))
12223 goto error;
12224
12225 /* path_converter doesn't keep path.object around, so do it
12226 manually for the lifetime of the iterator here (the refcount
12227 is decremented in ScandirIterator_dealloc)
12228 */
12229 Py_XINCREF(iterator->path.object);
12230
12231#ifdef MS_WINDOWS
12232 if (iterator->path.narrow) {
12233 PyErr_SetString(PyExc_TypeError,
12234 "os.scandir() doesn't support bytes path on Windows, use Unicode instead");
12235 goto error;
12236 }
12237 iterator->first_time = 1;
12238
12239 path_strW = join_path_filenameW(iterator->path.wide, L"*.*");
12240 if (!path_strW)
12241 goto error;
12242
12243 Py_BEGIN_ALLOW_THREADS
12244 iterator->handle = FindFirstFileW(path_strW, &iterator->file_data);
12245 Py_END_ALLOW_THREADS
12246
12247 PyMem_Free(path_strW);
12248
12249 if (iterator->handle == INVALID_HANDLE_VALUE) {
12250 path_error(&iterator->path);
12251 goto error;
12252 }
12253#else /* POSIX */
12254 if (iterator->path.narrow)
12255 path = iterator->path.narrow;
12256 else
12257 path = ".";
12258
12259 errno = 0;
12260 Py_BEGIN_ALLOW_THREADS
12261 iterator->dirp = opendir(path);
12262 Py_END_ALLOW_THREADS
12263
12264 if (!iterator->dirp) {
12265 path_error(&iterator->path);
12266 goto error;
12267 }
12268#endif
12269
12270 return (PyObject *)iterator;
12271
12272error:
12273 Py_DECREF(iterator);
12274 return NULL;
12275}
12276
12277
Serhiy Storchakaa4c6bad2015-04-04 23:35:52 +030012278#include "clinic/posixmodule.c.h"
12279
Larry Hastings7726ac92014-01-31 22:03:12 -080012280/*[clinic input]
12281dump buffer
12282[clinic start generated code]*/
Serhiy Storchaka1009bf12015-04-03 23:53:51 +030012283/*[clinic end generated code: output=da39a3ee5e6b4b0d input=524ce2e021e4eba6]*/
Larry Hastings7726ac92014-01-31 22:03:12 -080012284
Larry Hastings31826802013-10-19 00:09:25 -070012285
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012286static PyMethodDef posix_methods[] = {
Larry Hastings31826802013-10-19 00:09:25 -070012287
12288 OS_STAT_METHODDEF
12289 OS_ACCESS_METHODDEF
12290 OS_TTYNAME_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100012291 OS_CHDIR_METHODDEF
12292 OS_CHFLAGS_METHODDEF
12293 OS_CHMOD_METHODDEF
12294 OS_FCHMOD_METHODDEF
12295 OS_LCHMOD_METHODDEF
12296 OS_CHOWN_METHODDEF
12297 OS_FCHOWN_METHODDEF
12298 OS_LCHOWN_METHODDEF
12299 OS_LCHFLAGS_METHODDEF
12300 OS_CHROOT_METHODDEF
12301 OS_CTERMID_METHODDEF
12302 OS_GETCWD_METHODDEF
12303 OS_GETCWDB_METHODDEF
12304 OS_LINK_METHODDEF
12305 OS_LISTDIR_METHODDEF
12306 OS_LSTAT_METHODDEF
12307 OS_MKDIR_METHODDEF
12308 OS_NICE_METHODDEF
12309 OS_GETPRIORITY_METHODDEF
12310 OS_SETPRIORITY_METHODDEF
Guido van Rossumb6775db1994-08-01 11:34:53 +000012311#ifdef HAVE_READLINK
Larry Hastings9cf065c2012-06-22 16:30:09 -070012312 {"readlink", (PyCFunction)posix_readlink,
12313 METH_VARARGS | METH_KEYWORDS,
12314 readlink__doc__},
Guido van Rossum6a3eb5f1994-08-18 15:42:46 +000012315#endif /* HAVE_READLINK */
Brian Curtind40e6f72010-07-08 21:39:08 +000012316#if !defined(HAVE_READLINK) && defined(MS_WINDOWS)
Larry Hastings9cf065c2012-06-22 16:30:09 -070012317 {"readlink", (PyCFunction)win_readlink,
12318 METH_VARARGS | METH_KEYWORDS,
12319 readlink__doc__},
Brian Curtind40e6f72010-07-08 21:39:08 +000012320#endif /* !defined(HAVE_READLINK) && defined(MS_WINDOWS) */
Larry Hastings2f936352014-08-05 14:04:04 +100012321 OS_RENAME_METHODDEF
12322 OS_REPLACE_METHODDEF
12323 OS_RMDIR_METHODDEF
Victor Stinner8c62be82010-05-06 00:08:46 +000012324 {"stat_float_times", stat_float_times, METH_VARARGS, stat_float_times__doc__},
Larry Hastings2f936352014-08-05 14:04:04 +100012325 OS_SYMLINK_METHODDEF
12326 OS_SYSTEM_METHODDEF
12327 OS_UMASK_METHODDEF
12328 OS_UNAME_METHODDEF
12329 OS_UNLINK_METHODDEF
12330 OS_REMOVE_METHODDEF
12331 OS_UTIME_METHODDEF
12332 OS_TIMES_METHODDEF
12333 OS__EXIT_METHODDEF
12334 OS_EXECV_METHODDEF
12335 OS_EXECVE_METHODDEF
12336 OS_SPAWNV_METHODDEF
12337 OS_SPAWNVE_METHODDEF
12338 OS_FORK1_METHODDEF
12339 OS_FORK_METHODDEF
12340 OS_SCHED_GET_PRIORITY_MAX_METHODDEF
12341 OS_SCHED_GET_PRIORITY_MIN_METHODDEF
12342 OS_SCHED_GETPARAM_METHODDEF
12343 OS_SCHED_GETSCHEDULER_METHODDEF
12344 OS_SCHED_RR_GET_INTERVAL_METHODDEF
12345 OS_SCHED_SETPARAM_METHODDEF
12346 OS_SCHED_SETSCHEDULER_METHODDEF
12347 OS_SCHED_YIELD_METHODDEF
12348 OS_SCHED_SETAFFINITY_METHODDEF
12349 OS_SCHED_GETAFFINITY_METHODDEF
12350 OS_OPENPTY_METHODDEF
12351 OS_FORKPTY_METHODDEF
12352 OS_GETEGID_METHODDEF
12353 OS_GETEUID_METHODDEF
12354 OS_GETGID_METHODDEF
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +020012355#ifdef HAVE_GETGROUPLIST
12356 {"getgrouplist", posix_getgrouplist, METH_VARARGS, posix_getgrouplist__doc__},
12357#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012358 OS_GETGROUPS_METHODDEF
12359 OS_GETPID_METHODDEF
12360 OS_GETPGRP_METHODDEF
12361 OS_GETPPID_METHODDEF
12362 OS_GETUID_METHODDEF
12363 OS_GETLOGIN_METHODDEF
12364 OS_KILL_METHODDEF
12365 OS_KILLPG_METHODDEF
12366 OS_PLOCK_METHODDEF
Thomas Heller8b7a9572007-08-31 06:44:36 +000012367#ifdef MS_WINDOWS
Victor Stinner8c62be82010-05-06 00:08:46 +000012368 {"startfile", win32_startfile, METH_VARARGS, win32_startfile__doc__},
Thomas Heller8b7a9572007-08-31 06:44:36 +000012369#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012370 OS_SETUID_METHODDEF
12371 OS_SETEUID_METHODDEF
12372 OS_SETREUID_METHODDEF
12373 OS_SETGID_METHODDEF
12374 OS_SETEGID_METHODDEF
12375 OS_SETREGID_METHODDEF
12376 OS_SETGROUPS_METHODDEF
Antoine Pitroub7572f02009-12-02 20:46:48 +000012377#ifdef HAVE_INITGROUPS
Victor Stinner8c62be82010-05-06 00:08:46 +000012378 {"initgroups", posix_initgroups, METH_VARARGS, posix_initgroups__doc__},
Antoine Pitroub7572f02009-12-02 20:46:48 +000012379#endif /* HAVE_INITGROUPS */
Larry Hastings2f936352014-08-05 14:04:04 +100012380 OS_GETPGID_METHODDEF
12381 OS_SETPGRP_METHODDEF
12382 OS_WAIT_METHODDEF
12383 OS_WAIT3_METHODDEF
12384 OS_WAIT4_METHODDEF
12385 OS_WAITID_METHODDEF
12386 OS_WAITPID_METHODDEF
12387 OS_GETSID_METHODDEF
12388 OS_SETSID_METHODDEF
12389 OS_SETPGID_METHODDEF
12390 OS_TCGETPGRP_METHODDEF
12391 OS_TCSETPGRP_METHODDEF
12392 OS_OPEN_METHODDEF
12393 OS_CLOSE_METHODDEF
12394 OS_CLOSERANGE_METHODDEF
12395 OS_DEVICE_ENCODING_METHODDEF
12396 OS_DUP_METHODDEF
12397 OS_DUP2_METHODDEF
12398 OS_LOCKF_METHODDEF
12399 OS_LSEEK_METHODDEF
12400 OS_READ_METHODDEF
12401 OS_READV_METHODDEF
12402 OS_PREAD_METHODDEF
12403 OS_WRITE_METHODDEF
12404 OS_WRITEV_METHODDEF
12405 OS_PWRITE_METHODDEF
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012406#ifdef HAVE_SENDFILE
12407 {"sendfile", (PyCFunction)posix_sendfile, METH_VARARGS | METH_KEYWORDS,
12408 posix_sendfile__doc__},
12409#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012410 OS_FSTAT_METHODDEF
12411 OS_ISATTY_METHODDEF
12412 OS_PIPE_METHODDEF
12413 OS_PIPE2_METHODDEF
12414 OS_MKFIFO_METHODDEF
12415 OS_MKNOD_METHODDEF
12416 OS_MAJOR_METHODDEF
12417 OS_MINOR_METHODDEF
12418 OS_MAKEDEV_METHODDEF
12419 OS_FTRUNCATE_METHODDEF
12420 OS_TRUNCATE_METHODDEF
12421 OS_POSIX_FALLOCATE_METHODDEF
12422 OS_POSIX_FADVISE_METHODDEF
12423 OS_PUTENV_METHODDEF
12424 OS_UNSETENV_METHODDEF
12425 OS_STRERROR_METHODDEF
12426 OS_FCHDIR_METHODDEF
12427 OS_FSYNC_METHODDEF
12428 OS_SYNC_METHODDEF
12429 OS_FDATASYNC_METHODDEF
12430 OS_WCOREDUMP_METHODDEF
12431 OS_WIFCONTINUED_METHODDEF
12432 OS_WIFSTOPPED_METHODDEF
12433 OS_WIFSIGNALED_METHODDEF
12434 OS_WIFEXITED_METHODDEF
12435 OS_WEXITSTATUS_METHODDEF
12436 OS_WTERMSIG_METHODDEF
12437 OS_WSTOPSIG_METHODDEF
12438 OS_FSTATVFS_METHODDEF
12439 OS_STATVFS_METHODDEF
12440 OS_CONFSTR_METHODDEF
12441 OS_SYSCONF_METHODDEF
12442 OS_FPATHCONF_METHODDEF
12443 OS_PATHCONF_METHODDEF
12444 OS_ABORT_METHODDEF
Serhiy Storchakaf0b50152015-05-13 00:52:39 +030012445 OS__GETFULLPATHNAME_METHODDEF
12446 OS__ISDIR_METHODDEF
Larry Hastings2f936352014-08-05 14:04:04 +100012447 OS__GETDISKUSAGE_METHODDEF
12448 OS__GETFINALPATHNAME_METHODDEF
12449 OS__GETVOLUMEPATHNAME_METHODDEF
12450 OS_GETLOADAVG_METHODDEF
12451 OS_URANDOM_METHODDEF
12452 OS_SETRESUID_METHODDEF
12453 OS_SETRESGID_METHODDEF
12454 OS_GETRESUID_METHODDEF
12455 OS_GETRESGID_METHODDEF
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000012456
Larry Hastings2f936352014-08-05 14:04:04 +100012457 OS_GETXATTR_METHODDEF
12458 OS_SETXATTR_METHODDEF
12459 OS_REMOVEXATTR_METHODDEF
12460 OS_LISTXATTR_METHODDEF
12461
Antoine Pitroubcf2b592012-02-08 23:28:36 +010012462#if defined(TERMSIZE_USE_CONIO) || defined(TERMSIZE_USE_IOCTL)
12463 {"get_terminal_size", get_terminal_size, METH_VARARGS, termsize__doc__},
12464#endif
Larry Hastings2f936352014-08-05 14:04:04 +100012465 OS_CPU_COUNT_METHODDEF
12466 OS_GET_INHERITABLE_METHODDEF
12467 OS_SET_INHERITABLE_METHODDEF
12468 OS_GET_HANDLE_INHERITABLE_METHODDEF
12469 OS_SET_HANDLE_INHERITABLE_METHODDEF
Victor Stinner1db9e7b2014-07-29 22:32:47 +020012470#ifndef MS_WINDOWS
12471 {"get_blocking", posix_get_blocking, METH_VARARGS, get_blocking__doc__},
12472 {"set_blocking", posix_set_blocking, METH_VARARGS, set_blocking__doc__},
12473#endif
Victor Stinner6036e442015-03-08 01:58:04 +010012474 {"scandir", (PyCFunction)posix_scandir,
12475 METH_VARARGS | METH_KEYWORDS,
12476 posix_scandir__doc__},
Victor Stinner8c62be82010-05-06 00:08:46 +000012477 {NULL, NULL} /* Sentinel */
Guido van Rossum85a5fbb1990-10-14 12:07:46 +000012478};
12479
12480
Brian Curtin52173d42010-12-02 18:29:18 +000012481#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000012482static int
Brian Curtin52173d42010-12-02 18:29:18 +000012483enable_symlink()
12484{
12485 HANDLE tok;
12486 TOKEN_PRIVILEGES tok_priv;
12487 LUID luid;
Brian Curtin52173d42010-12-02 18:29:18 +000012488
12489 if (!OpenProcessToken(GetCurrentProcess(), TOKEN_ALL_ACCESS, &tok))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012490 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012491
12492 if (!LookupPrivilegeValue(NULL, SE_CREATE_SYMBOLIC_LINK_NAME, &luid))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012493 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012494
12495 tok_priv.PrivilegeCount = 1;
12496 tok_priv.Privileges[0].Luid = luid;
12497 tok_priv.Privileges[0].Attributes = SE_PRIVILEGE_ENABLED;
12498
12499 if (!AdjustTokenPrivileges(tok, FALSE, &tok_priv,
12500 sizeof(TOKEN_PRIVILEGES),
12501 (PTOKEN_PRIVILEGES) NULL, (PDWORD) NULL))
Brian Curtin3b4499c2010-12-28 14:31:47 +000012502 return 0;
Brian Curtin52173d42010-12-02 18:29:18 +000012503
Brian Curtin3b4499c2010-12-28 14:31:47 +000012504 /* ERROR_NOT_ALL_ASSIGNED returned when the privilege can't be assigned. */
12505 return GetLastError() == ERROR_NOT_ALL_ASSIGNED ? 0 : 1;
Brian Curtin52173d42010-12-02 18:29:18 +000012506}
12507#endif /* defined(HAVE_SYMLINK) && defined(MS_WINDOWS) */
12508
Barry Warsaw4a342091996-12-19 23:50:02 +000012509static int
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012510all_ins(PyObject *m)
Barry Warsaw4a342091996-12-19 23:50:02 +000012511{
Guido van Rossum94f6f721999-01-06 18:42:14 +000012512#ifdef F_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012513 if (PyModule_AddIntMacro(m, F_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012514#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012515#ifdef R_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012516 if (PyModule_AddIntMacro(m, R_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012517#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012518#ifdef W_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012519 if (PyModule_AddIntMacro(m, W_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012520#endif
Guido van Rossum94f6f721999-01-06 18:42:14 +000012521#ifdef X_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012522 if (PyModule_AddIntMacro(m, X_OK)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012523#endif
Fred Drakec9680921999-12-13 16:37:25 +000012524#ifdef NGROUPS_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012525 if (PyModule_AddIntMacro(m, NGROUPS_MAX)) return -1;
Fred Drakec9680921999-12-13 16:37:25 +000012526#endif
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012527#ifdef TMP_MAX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012528 if (PyModule_AddIntMacro(m, TMP_MAX)) return -1;
Fred Drake5ab8eaf1999-12-09 21:13:07 +000012529#endif
Fred Drake106c1a02002-04-23 15:58:02 +000012530#ifdef WCONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012531 if (PyModule_AddIntMacro(m, WCONTINUED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000012532#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000012533#ifdef WNOHANG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012534 if (PyModule_AddIntMacro(m, WNOHANG)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012535#endif
Fred Drake106c1a02002-04-23 15:58:02 +000012536#ifdef WUNTRACED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012537 if (PyModule_AddIntMacro(m, WUNTRACED)) return -1;
Fred Drake106c1a02002-04-23 15:58:02 +000012538#endif
Barry Warsaw4a342091996-12-19 23:50:02 +000012539#ifdef O_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012540 if (PyModule_AddIntMacro(m, O_RDONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012541#endif
12542#ifdef O_WRONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012543 if (PyModule_AddIntMacro(m, O_WRONLY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012544#endif
12545#ifdef O_RDWR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012546 if (PyModule_AddIntMacro(m, O_RDWR)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012547#endif
12548#ifdef O_NDELAY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012549 if (PyModule_AddIntMacro(m, O_NDELAY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012550#endif
12551#ifdef O_NONBLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012552 if (PyModule_AddIntMacro(m, O_NONBLOCK)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012553#endif
12554#ifdef O_APPEND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012555 if (PyModule_AddIntMacro(m, O_APPEND)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012556#endif
12557#ifdef O_DSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012558 if (PyModule_AddIntMacro(m, O_DSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012559#endif
12560#ifdef O_RSYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012561 if (PyModule_AddIntMacro(m, O_RSYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012562#endif
12563#ifdef O_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012564 if (PyModule_AddIntMacro(m, O_SYNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012565#endif
12566#ifdef O_NOCTTY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012567 if (PyModule_AddIntMacro(m, O_NOCTTY)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012568#endif
12569#ifdef O_CREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012570 if (PyModule_AddIntMacro(m, O_CREAT)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012571#endif
12572#ifdef O_EXCL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012573 if (PyModule_AddIntMacro(m, O_EXCL)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012574#endif
12575#ifdef O_TRUNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012576 if (PyModule_AddIntMacro(m, O_TRUNC)) return -1;
Barry Warsaw4a342091996-12-19 23:50:02 +000012577#endif
Guido van Rossum98d9d091997-08-08 21:48:51 +000012578#ifdef O_BINARY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012579 if (PyModule_AddIntMacro(m, O_BINARY)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000012580#endif
12581#ifdef O_TEXT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012582 if (PyModule_AddIntMacro(m, O_TEXT)) return -1;
Guido van Rossum98d9d091997-08-08 21:48:51 +000012583#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012584#ifdef O_XATTR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012585 if (PyModule_AddIntMacro(m, O_XATTR)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012586#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012587#ifdef O_LARGEFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012588 if (PyModule_AddIntMacro(m, O_LARGEFILE)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012589#endif
Skip Montanaro5ff14922005-05-16 02:42:22 +000012590#ifdef O_SHLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012591 if (PyModule_AddIntMacro(m, O_SHLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000012592#endif
12593#ifdef O_EXLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012594 if (PyModule_AddIntMacro(m, O_EXLOCK)) return -1;
Skip Montanaro5ff14922005-05-16 02:42:22 +000012595#endif
Jesus Ceacf381202012-04-24 20:44:40 +020012596#ifdef O_EXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012597 if (PyModule_AddIntMacro(m, O_EXEC)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012598#endif
12599#ifdef O_SEARCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012600 if (PyModule_AddIntMacro(m, O_SEARCH)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012601#endif
Benjamin Peterson3b965a22013-03-13 10:27:41 -050012602#ifdef O_PATH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012603 if (PyModule_AddIntMacro(m, O_PATH)) return -1;
Benjamin Peterson3b965a22013-03-13 10:27:41 -050012604#endif
Jesus Ceacf381202012-04-24 20:44:40 +020012605#ifdef O_TTY_INIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012606 if (PyModule_AddIntMacro(m, O_TTY_INIT)) return -1;
Jesus Ceacf381202012-04-24 20:44:40 +020012607#endif
Christian Heimes177b3f92013-08-16 14:35:09 +020012608#ifdef O_TMPFILE
12609 if (PyModule_AddIntMacro(m, O_TMPFILE)) return -1;
12610#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012611#ifdef PRIO_PROCESS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012612 if (PyModule_AddIntMacro(m, PRIO_PROCESS)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012613#endif
12614#ifdef PRIO_PGRP
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012615 if (PyModule_AddIntMacro(m, PRIO_PGRP)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012616#endif
12617#ifdef PRIO_USER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012618 if (PyModule_AddIntMacro(m, PRIO_USER)) return -1;
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012619#endif
Charles-François Natali1e045b12011-05-22 20:42:32 +020012620#ifdef O_CLOEXEC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012621 if (PyModule_AddIntMacro(m, O_CLOEXEC)) return -1;
Charles-François Natali1e045b12011-05-22 20:42:32 +020012622#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012623#ifdef O_ACCMODE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012624 if (PyModule_AddIntMacro(m, O_ACCMODE)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012625#endif
Giampaolo Rodolà18e8bcb2011-02-25 20:57:54 +000012626
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012627
Jesus Cea94363612012-06-22 18:32:07 +020012628#ifdef SEEK_HOLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012629 if (PyModule_AddIntMacro(m, SEEK_HOLE)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020012630#endif
12631#ifdef SEEK_DATA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012632 if (PyModule_AddIntMacro(m, SEEK_DATA)) return -1;
Jesus Cea94363612012-06-22 18:32:07 +020012633#endif
12634
Tim Peters5aa91602002-01-30 05:46:57 +000012635/* MS Windows */
12636#ifdef O_NOINHERIT
Victor Stinner8c62be82010-05-06 00:08:46 +000012637 /* Don't inherit in child processes. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012638 if (PyModule_AddIntMacro(m, O_NOINHERIT)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012639#endif
12640#ifdef _O_SHORT_LIVED
Victor Stinner8c62be82010-05-06 00:08:46 +000012641 /* Optimize for short life (keep in memory). */
12642 /* MS forgot to define this one with a non-underscore form too. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012643 if (PyModule_AddIntConstant(m, "O_SHORT_LIVED", _O_SHORT_LIVED)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012644#endif
12645#ifdef O_TEMPORARY
Victor Stinner8c62be82010-05-06 00:08:46 +000012646 /* Automatically delete when last handle is closed. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012647 if (PyModule_AddIntMacro(m, O_TEMPORARY)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012648#endif
12649#ifdef O_RANDOM
Victor Stinner8c62be82010-05-06 00:08:46 +000012650 /* Optimize for random access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012651 if (PyModule_AddIntMacro(m, O_RANDOM)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012652#endif
12653#ifdef O_SEQUENTIAL
Victor Stinner8c62be82010-05-06 00:08:46 +000012654 /* Optimize for sequential access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012655 if (PyModule_AddIntMacro(m, O_SEQUENTIAL)) return -1;
Tim Peters5aa91602002-01-30 05:46:57 +000012656#endif
12657
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012658/* GNU extensions. */
Alexandre Vassalottibee32532008-05-16 18:15:12 +000012659#ifdef O_ASYNC
Victor Stinner8c62be82010-05-06 00:08:46 +000012660 /* Send a SIGIO signal whenever input or output
12661 becomes available on file descriptor */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012662 if (PyModule_AddIntMacro(m, O_ASYNC)) return -1;
Alexandre Vassalottibee32532008-05-16 18:15:12 +000012663#endif
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012664#ifdef O_DIRECT
Victor Stinner8c62be82010-05-06 00:08:46 +000012665 /* Direct disk access. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012666 if (PyModule_AddIntMacro(m, O_DIRECT)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012667#endif
12668#ifdef O_DIRECTORY
Victor Stinner8c62be82010-05-06 00:08:46 +000012669 /* Must be a directory. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012670 if (PyModule_AddIntMacro(m, O_DIRECTORY)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012671#endif
12672#ifdef O_NOFOLLOW
Victor Stinner8c62be82010-05-06 00:08:46 +000012673 /* Do not follow links. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012674 if (PyModule_AddIntMacro(m, O_NOFOLLOW)) return -1;
Martin v. Löwis4fe3c272001-10-18 22:05:36 +000012675#endif
Jesus Cea1d642d22012-04-24 20:59:17 +020012676#ifdef O_NOLINKS
12677 /* Fails if link count of the named file is greater than 1 */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012678 if (PyModule_AddIntMacro(m, O_NOLINKS)) return -1;
Jesus Cea1d642d22012-04-24 20:59:17 +020012679#endif
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000012680#ifdef O_NOATIME
Victor Stinner8c62be82010-05-06 00:08:46 +000012681 /* Do not update the access time. */
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012682 if (PyModule_AddIntMacro(m, O_NOATIME)) return -1;
Guido van Rossum0d3fb8a2007-11-26 23:23:18 +000012683#endif
Guido van Rossumd48f2521997-12-05 22:19:34 +000012684
Victor Stinner8c62be82010-05-06 00:08:46 +000012685 /* These come from sysexits.h */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012686#ifdef EX_OK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012687 if (PyModule_AddIntMacro(m, EX_OK)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012688#endif /* EX_OK */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012689#ifdef EX_USAGE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012690 if (PyModule_AddIntMacro(m, EX_USAGE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012691#endif /* EX_USAGE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012692#ifdef EX_DATAERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012693 if (PyModule_AddIntMacro(m, EX_DATAERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012694#endif /* EX_DATAERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012695#ifdef EX_NOINPUT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012696 if (PyModule_AddIntMacro(m, EX_NOINPUT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012697#endif /* EX_NOINPUT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012698#ifdef EX_NOUSER
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012699 if (PyModule_AddIntMacro(m, EX_NOUSER)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012700#endif /* EX_NOUSER */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012701#ifdef EX_NOHOST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012702 if (PyModule_AddIntMacro(m, EX_NOHOST)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012703#endif /* EX_NOHOST */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012704#ifdef EX_UNAVAILABLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012705 if (PyModule_AddIntMacro(m, EX_UNAVAILABLE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012706#endif /* EX_UNAVAILABLE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012707#ifdef EX_SOFTWARE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012708 if (PyModule_AddIntMacro(m, EX_SOFTWARE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012709#endif /* EX_SOFTWARE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012710#ifdef EX_OSERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012711 if (PyModule_AddIntMacro(m, EX_OSERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012712#endif /* EX_OSERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012713#ifdef EX_OSFILE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012714 if (PyModule_AddIntMacro(m, EX_OSFILE)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012715#endif /* EX_OSFILE */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012716#ifdef EX_CANTCREAT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012717 if (PyModule_AddIntMacro(m, EX_CANTCREAT)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012718#endif /* EX_CANTCREAT */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012719#ifdef EX_IOERR
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012720 if (PyModule_AddIntMacro(m, EX_IOERR)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012721#endif /* EX_IOERR */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012722#ifdef EX_TEMPFAIL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012723 if (PyModule_AddIntMacro(m, EX_TEMPFAIL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012724#endif /* EX_TEMPFAIL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012725#ifdef EX_PROTOCOL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012726 if (PyModule_AddIntMacro(m, EX_PROTOCOL)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012727#endif /* EX_PROTOCOL */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012728#ifdef EX_NOPERM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012729 if (PyModule_AddIntMacro(m, EX_NOPERM)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012730#endif /* EX_NOPERM */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012731#ifdef EX_CONFIG
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012732 if (PyModule_AddIntMacro(m, EX_CONFIG)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012733#endif /* EX_CONFIG */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012734#ifdef EX_NOTFOUND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012735 if (PyModule_AddIntMacro(m, EX_NOTFOUND)) return -1;
Neal Norwitz8e914d92003-01-10 15:29:16 +000012736#endif /* EX_NOTFOUND */
Barry Warsaw5676bd12003-01-07 20:57:09 +000012737
Amaury Forgeot d'Arc66d00ad2010-09-10 18:11:45 +000012738 /* statvfs */
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012739#ifdef ST_RDONLY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012740 if (PyModule_AddIntMacro(m, ST_RDONLY)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012741#endif /* ST_RDONLY */
12742#ifdef ST_NOSUID
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012743 if (PyModule_AddIntMacro(m, ST_NOSUID)) return -1;
Andrew M. Kuchling4ea04a32010-08-18 22:30:34 +000012744#endif /* ST_NOSUID */
12745
doko@ubuntu.comca616a22013-12-08 15:23:07 +010012746 /* GNU extensions */
12747#ifdef ST_NODEV
12748 if (PyModule_AddIntMacro(m, ST_NODEV)) return -1;
12749#endif /* ST_NODEV */
12750#ifdef ST_NOEXEC
12751 if (PyModule_AddIntMacro(m, ST_NOEXEC)) return -1;
12752#endif /* ST_NOEXEC */
12753#ifdef ST_SYNCHRONOUS
12754 if (PyModule_AddIntMacro(m, ST_SYNCHRONOUS)) return -1;
12755#endif /* ST_SYNCHRONOUS */
12756#ifdef ST_MANDLOCK
12757 if (PyModule_AddIntMacro(m, ST_MANDLOCK)) return -1;
12758#endif /* ST_MANDLOCK */
12759#ifdef ST_WRITE
12760 if (PyModule_AddIntMacro(m, ST_WRITE)) return -1;
12761#endif /* ST_WRITE */
12762#ifdef ST_APPEND
12763 if (PyModule_AddIntMacro(m, ST_APPEND)) return -1;
12764#endif /* ST_APPEND */
12765#ifdef ST_NOATIME
12766 if (PyModule_AddIntMacro(m, ST_NOATIME)) return -1;
12767#endif /* ST_NOATIME */
12768#ifdef ST_NODIRATIME
12769 if (PyModule_AddIntMacro(m, ST_NODIRATIME)) return -1;
12770#endif /* ST_NODIRATIME */
12771#ifdef ST_RELATIME
12772 if (PyModule_AddIntMacro(m, ST_RELATIME)) return -1;
12773#endif /* ST_RELATIME */
12774
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012775 /* FreeBSD sendfile() constants */
12776#ifdef SF_NODISKIO
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012777 if (PyModule_AddIntMacro(m, SF_NODISKIO)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012778#endif
12779#ifdef SF_MNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012780 if (PyModule_AddIntMacro(m, SF_MNOWAIT)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012781#endif
12782#ifdef SF_SYNC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012783 if (PyModule_AddIntMacro(m, SF_SYNC)) return -1;
Giampaolo Rodolàc9c2c8b2011-02-25 14:39:16 +000012784#endif
12785
Ross Lagerwall7807c352011-03-17 20:20:30 +020012786 /* constants for posix_fadvise */
12787#ifdef POSIX_FADV_NORMAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012788 if (PyModule_AddIntMacro(m, POSIX_FADV_NORMAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012789#endif
12790#ifdef POSIX_FADV_SEQUENTIAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012791 if (PyModule_AddIntMacro(m, POSIX_FADV_SEQUENTIAL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012792#endif
12793#ifdef POSIX_FADV_RANDOM
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012794 if (PyModule_AddIntMacro(m, POSIX_FADV_RANDOM)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012795#endif
12796#ifdef POSIX_FADV_NOREUSE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012797 if (PyModule_AddIntMacro(m, POSIX_FADV_NOREUSE)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012798#endif
12799#ifdef POSIX_FADV_WILLNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012800 if (PyModule_AddIntMacro(m, POSIX_FADV_WILLNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012801#endif
12802#ifdef POSIX_FADV_DONTNEED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012803 if (PyModule_AddIntMacro(m, POSIX_FADV_DONTNEED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012804#endif
12805
12806 /* constants for waitid */
12807#if defined(HAVE_SYS_WAIT_H) && defined(HAVE_WAITID)
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012808 if (PyModule_AddIntMacro(m, P_PID)) return -1;
12809 if (PyModule_AddIntMacro(m, P_PGID)) return -1;
12810 if (PyModule_AddIntMacro(m, P_ALL)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012811#endif
12812#ifdef WEXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012813 if (PyModule_AddIntMacro(m, WEXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012814#endif
12815#ifdef WNOWAIT
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012816 if (PyModule_AddIntMacro(m, WNOWAIT)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012817#endif
12818#ifdef WSTOPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012819 if (PyModule_AddIntMacro(m, WSTOPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012820#endif
12821#ifdef CLD_EXITED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012822 if (PyModule_AddIntMacro(m, CLD_EXITED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012823#endif
12824#ifdef CLD_DUMPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012825 if (PyModule_AddIntMacro(m, CLD_DUMPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012826#endif
12827#ifdef CLD_TRAPPED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012828 if (PyModule_AddIntMacro(m, CLD_TRAPPED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012829#endif
12830#ifdef CLD_CONTINUED
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012831 if (PyModule_AddIntMacro(m, CLD_CONTINUED)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012832#endif
12833
12834 /* constants for lockf */
12835#ifdef F_LOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012836 if (PyModule_AddIntMacro(m, F_LOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012837#endif
12838#ifdef F_TLOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012839 if (PyModule_AddIntMacro(m, F_TLOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012840#endif
12841#ifdef F_ULOCK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012842 if (PyModule_AddIntMacro(m, F_ULOCK)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012843#endif
12844#ifdef F_TEST
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012845 if (PyModule_AddIntMacro(m, F_TEST)) return -1;
Ross Lagerwall7807c352011-03-17 20:20:30 +020012846#endif
12847
Guido van Rossum246bc171999-02-01 23:54:31 +000012848#ifdef HAVE_SPAWNV
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012849 if (PyModule_AddIntConstant(m, "P_WAIT", _P_WAIT)) return -1;
12850 if (PyModule_AddIntConstant(m, "P_NOWAIT", _P_NOWAIT)) return -1;
12851 if (PyModule_AddIntConstant(m, "P_OVERLAY", _OLD_P_OVERLAY)) return -1;
12852 if (PyModule_AddIntConstant(m, "P_NOWAITO", _P_NOWAITO)) return -1;
12853 if (PyModule_AddIntConstant(m, "P_DETACH", _P_DETACH)) return -1;
Guido van Rossum246bc171999-02-01 23:54:31 +000012854#endif
12855
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012856#ifdef HAVE_SCHED_H
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012857 if (PyModule_AddIntMacro(m, SCHED_OTHER)) return -1;
12858 if (PyModule_AddIntMacro(m, SCHED_FIFO)) return -1;
12859 if (PyModule_AddIntMacro(m, SCHED_RR)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012860#ifdef SCHED_SPORADIC
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012861 if (PyModule_AddIntMacro(m, SCHED_SPORADIC) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012862#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012863#ifdef SCHED_BATCH
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012864 if (PyModule_AddIntMacro(m, SCHED_BATCH)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012865#endif
12866#ifdef SCHED_IDLE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012867 if (PyModule_AddIntMacro(m, SCHED_IDLE)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012868#endif
12869#ifdef SCHED_RESET_ON_FORK
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012870 if (PyModule_AddIntMacro(m, SCHED_RESET_ON_FORK)) return -1;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012871#endif
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012872#ifdef SCHED_SYS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012873 if (PyModule_AddIntMacro(m, SCHED_SYS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012874#endif
12875#ifdef SCHED_IA
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012876 if (PyModule_AddIntMacro(m, SCHED_IA)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012877#endif
12878#ifdef SCHED_FSS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012879 if (PyModule_AddIntMacro(m, SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012880#endif
12881#ifdef SCHED_FX
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012882 if (PyModule_AddIntConstant(m, "SCHED_FX", SCHED_FSS)) return -1;
Jesus Ceaf2cb4e82011-09-09 23:55:42 +020012883#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050012884#endif
12885
Benjamin Peterson9428d532011-09-14 11:45:52 -040012886#ifdef USE_XATTRS
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012887 if (PyModule_AddIntMacro(m, XATTR_CREATE)) return -1;
12888 if (PyModule_AddIntMacro(m, XATTR_REPLACE)) return -1;
12889 if (PyModule_AddIntMacro(m, XATTR_SIZE_MAX)) return -1;
Benjamin Peterson799bd802011-08-31 22:15:17 -040012890#endif
12891
Victor Stinner8b905bd2011-10-25 13:34:04 +020012892#ifdef RTLD_LAZY
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012893 if (PyModule_AddIntMacro(m, RTLD_LAZY)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012894#endif
12895#ifdef RTLD_NOW
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012896 if (PyModule_AddIntMacro(m, RTLD_NOW)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012897#endif
12898#ifdef RTLD_GLOBAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012899 if (PyModule_AddIntMacro(m, RTLD_GLOBAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012900#endif
12901#ifdef RTLD_LOCAL
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012902 if (PyModule_AddIntMacro(m, RTLD_LOCAL)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012903#endif
12904#ifdef RTLD_NODELETE
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012905 if (PyModule_AddIntMacro(m, RTLD_NODELETE)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012906#endif
12907#ifdef RTLD_NOLOAD
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012908 if (PyModule_AddIntMacro(m, RTLD_NOLOAD)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012909#endif
12910#ifdef RTLD_DEEPBIND
Charles-Francois Natali74ca8862013-05-20 19:13:19 +020012911 if (PyModule_AddIntMacro(m, RTLD_DEEPBIND)) return -1;
Victor Stinner8b905bd2011-10-25 13:34:04 +020012912#endif
12913
Victor Stinner8c62be82010-05-06 00:08:46 +000012914 return 0;
Barry Warsaw4a342091996-12-19 23:50:02 +000012915}
12916
12917
Martin v. Löwis1a214512008-06-11 05:26:20 +000012918static struct PyModuleDef posixmodule = {
Victor Stinner8c62be82010-05-06 00:08:46 +000012919 PyModuleDef_HEAD_INIT,
12920 MODNAME,
12921 posix__doc__,
12922 -1,
12923 posix_methods,
12924 NULL,
12925 NULL,
12926 NULL,
12927 NULL
Martin v. Löwis1a214512008-06-11 05:26:20 +000012928};
12929
12930
Serhiy Storchaka2d06e842015-12-25 19:53:18 +020012931static const char * const have_functions[] = {
Larry Hastings9cf065c2012-06-22 16:30:09 -070012932
12933#ifdef HAVE_FACCESSAT
12934 "HAVE_FACCESSAT",
12935#endif
12936
12937#ifdef HAVE_FCHDIR
12938 "HAVE_FCHDIR",
12939#endif
12940
12941#ifdef HAVE_FCHMOD
12942 "HAVE_FCHMOD",
12943#endif
12944
12945#ifdef HAVE_FCHMODAT
12946 "HAVE_FCHMODAT",
12947#endif
12948
12949#ifdef HAVE_FCHOWN
12950 "HAVE_FCHOWN",
12951#endif
12952
Larry Hastings00964ed2013-08-12 13:49:30 -040012953#ifdef HAVE_FCHOWNAT
12954 "HAVE_FCHOWNAT",
12955#endif
12956
Larry Hastings9cf065c2012-06-22 16:30:09 -070012957#ifdef HAVE_FEXECVE
12958 "HAVE_FEXECVE",
12959#endif
12960
12961#ifdef HAVE_FDOPENDIR
12962 "HAVE_FDOPENDIR",
12963#endif
12964
Georg Brandl306336b2012-06-24 12:55:33 +020012965#ifdef HAVE_FPATHCONF
12966 "HAVE_FPATHCONF",
12967#endif
12968
Larry Hastings9cf065c2012-06-22 16:30:09 -070012969#ifdef HAVE_FSTATAT
12970 "HAVE_FSTATAT",
12971#endif
12972
12973#ifdef HAVE_FSTATVFS
12974 "HAVE_FSTATVFS",
12975#endif
12976
Steve Dowerfe0a41a2015-03-20 19:50:46 -070012977#if defined HAVE_FTRUNCATE || defined MS_WINDOWS
Georg Brandl306336b2012-06-24 12:55:33 +020012978 "HAVE_FTRUNCATE",
12979#endif
12980
Larry Hastings9cf065c2012-06-22 16:30:09 -070012981#ifdef HAVE_FUTIMENS
12982 "HAVE_FUTIMENS",
12983#endif
12984
12985#ifdef HAVE_FUTIMES
12986 "HAVE_FUTIMES",
12987#endif
12988
12989#ifdef HAVE_FUTIMESAT
12990 "HAVE_FUTIMESAT",
12991#endif
12992
12993#ifdef HAVE_LINKAT
12994 "HAVE_LINKAT",
12995#endif
12996
12997#ifdef HAVE_LCHFLAGS
12998 "HAVE_LCHFLAGS",
12999#endif
13000
13001#ifdef HAVE_LCHMOD
13002 "HAVE_LCHMOD",
13003#endif
13004
13005#ifdef HAVE_LCHOWN
13006 "HAVE_LCHOWN",
13007#endif
13008
13009#ifdef HAVE_LSTAT
13010 "HAVE_LSTAT",
13011#endif
13012
13013#ifdef HAVE_LUTIMES
13014 "HAVE_LUTIMES",
13015#endif
13016
13017#ifdef HAVE_MKDIRAT
13018 "HAVE_MKDIRAT",
13019#endif
13020
13021#ifdef HAVE_MKFIFOAT
13022 "HAVE_MKFIFOAT",
13023#endif
13024
13025#ifdef HAVE_MKNODAT
13026 "HAVE_MKNODAT",
13027#endif
13028
13029#ifdef HAVE_OPENAT
13030 "HAVE_OPENAT",
13031#endif
13032
13033#ifdef HAVE_READLINKAT
13034 "HAVE_READLINKAT",
13035#endif
13036
13037#ifdef HAVE_RENAMEAT
13038 "HAVE_RENAMEAT",
13039#endif
13040
13041#ifdef HAVE_SYMLINKAT
13042 "HAVE_SYMLINKAT",
13043#endif
13044
13045#ifdef HAVE_UNLINKAT
13046 "HAVE_UNLINKAT",
13047#endif
13048
13049#ifdef HAVE_UTIMENSAT
13050 "HAVE_UTIMENSAT",
13051#endif
13052
13053#ifdef MS_WINDOWS
13054 "MS_WINDOWS",
13055#endif
13056
13057 NULL
13058};
13059
13060
Mark Hammondfe51c6d2002-08-02 02:27:13 +000013061PyMODINIT_FUNC
Thomas Woutersf3f33dc2000-07-21 06:00:07 +000013062INITFUNC(void)
Guido van Rossumb6775db1994-08-01 11:34:53 +000013063{
Victor Stinner8c62be82010-05-06 00:08:46 +000013064 PyObject *m, *v;
Larry Hastings9cf065c2012-06-22 16:30:09 -070013065 PyObject *list;
Serhiy Storchaka2d06e842015-12-25 19:53:18 +020013066 const char * const *trace;
Tim Peters5aa91602002-01-30 05:46:57 +000013067
Brian Curtin52173d42010-12-02 18:29:18 +000013068#if defined(HAVE_SYMLINK) && defined(MS_WINDOWS)
Brian Curtin3b4499c2010-12-28 14:31:47 +000013069 win32_can_symlink = enable_symlink();
Brian Curtin52173d42010-12-02 18:29:18 +000013070#endif
13071
Victor Stinner8c62be82010-05-06 00:08:46 +000013072 m = PyModule_Create(&posixmodule);
13073 if (m == NULL)
13074 return NULL;
Tim Peters5aa91602002-01-30 05:46:57 +000013075
Victor Stinner8c62be82010-05-06 00:08:46 +000013076 /* Initialize environ dictionary */
13077 v = convertenviron();
13078 Py_XINCREF(v);
13079 if (v == NULL || PyModule_AddObject(m, "environ", v) != 0)
13080 return NULL;
13081 Py_DECREF(v);
Fred Drakec9680921999-12-13 16:37:25 +000013082
Victor Stinner8c62be82010-05-06 00:08:46 +000013083 if (all_ins(m))
13084 return NULL;
Barry Warsaw4a342091996-12-19 23:50:02 +000013085
Victor Stinner8c62be82010-05-06 00:08:46 +000013086 if (setup_confname_tables(m))
13087 return NULL;
Fred Drakebec628d1999-12-15 18:31:10 +000013088
Victor Stinner8c62be82010-05-06 00:08:46 +000013089 Py_INCREF(PyExc_OSError);
13090 PyModule_AddObject(m, "error", PyExc_OSError);
Fred Drake762e2061999-08-26 17:23:54 +000013091
Guido van Rossumb3d39562000-01-31 18:41:26 +000013092#ifdef HAVE_PUTENV
Victor Stinner8c62be82010-05-06 00:08:46 +000013093 if (posix_putenv_garbage == NULL)
13094 posix_putenv_garbage = PyDict_New();
Guido van Rossumb3d39562000-01-31 18:41:26 +000013095#endif
Guido van Rossum98bf58f2001-10-18 20:34:25 +000013096
Victor Stinner8c62be82010-05-06 00:08:46 +000013097 if (!initialized) {
Ross Lagerwall7807c352011-03-17 20:20:30 +020013098#if defined(HAVE_WAITID) && !defined(__APPLE__)
13099 waitid_result_desc.name = MODNAME ".waitid_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013100 if (PyStructSequence_InitType2(&WaitidResultType, &waitid_result_desc) < 0)
13101 return NULL;
Ross Lagerwall7807c352011-03-17 20:20:30 +020013102#endif
13103
Christian Heimes25827622013-10-12 01:27:08 +020013104 stat_result_desc.name = "os.stat_result"; /* see issue #19209 */
Victor Stinner8c62be82010-05-06 00:08:46 +000013105 stat_result_desc.fields[7].name = PyStructSequence_UnnamedField;
13106 stat_result_desc.fields[8].name = PyStructSequence_UnnamedField;
13107 stat_result_desc.fields[9].name = PyStructSequence_UnnamedField;
Victor Stinner1c8f0592013-07-22 22:24:54 +020013108 if (PyStructSequence_InitType2(&StatResultType, &stat_result_desc) < 0)
13109 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013110 structseq_new = StatResultType.tp_new;
13111 StatResultType.tp_new = statresult_new;
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000013112
Christian Heimes25827622013-10-12 01:27:08 +020013113 statvfs_result_desc.name = "os.statvfs_result"; /* see issue #19209 */
Victor Stinner1c8f0592013-07-22 22:24:54 +020013114 if (PyStructSequence_InitType2(&StatVFSResultType,
13115 &statvfs_result_desc) < 0)
13116 return NULL;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013117#ifdef NEED_TICKS_PER_SECOND
13118# if defined(HAVE_SYSCONF) && defined(_SC_CLK_TCK)
Victor Stinner8c62be82010-05-06 00:08:46 +000013119 ticks_per_second = sysconf(_SC_CLK_TCK);
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013120# elif defined(HZ)
Victor Stinner8c62be82010-05-06 00:08:46 +000013121 ticks_per_second = HZ;
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013122# else
Victor Stinner8c62be82010-05-06 00:08:46 +000013123 ticks_per_second = 60; /* magic fallback value; may be bogus */
Martin v. Löwis05bfe1f2008-12-29 18:21:47 +000013124# endif
13125#endif
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013126
Benjamin Peterson0163c9a2011-08-02 18:11:38 -050013127#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013128 sched_param_desc.name = MODNAME ".sched_param";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013129 if (PyStructSequence_InitType2(&SchedParamType, &sched_param_desc) < 0)
13130 return NULL;
Larry Hastings2f936352014-08-05 14:04:04 +100013131 SchedParamType.tp_new = os_sched_param;
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013132#endif
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013133
13134 /* initialize TerminalSize_info */
Victor Stinner1c8f0592013-07-22 22:24:54 +020013135 if (PyStructSequence_InitType2(&TerminalSizeType,
13136 &TerminalSize_desc) < 0)
13137 return NULL;
Victor Stinner6036e442015-03-08 01:58:04 +010013138
13139 /* initialize scandir types */
13140 if (PyType_Ready(&ScandirIteratorType) < 0)
13141 return NULL;
13142 if (PyType_Ready(&DirEntryType) < 0)
13143 return NULL;
Victor Stinner8c62be82010-05-06 00:08:46 +000013144 }
Ross Lagerwall7807c352011-03-17 20:20:30 +020013145#if defined(HAVE_WAITID) && !defined(__APPLE__)
13146 Py_INCREF((PyObject*) &WaitidResultType);
13147 PyModule_AddObject(m, "waitid_result", (PyObject*) &WaitidResultType);
13148#endif
Victor Stinner8c62be82010-05-06 00:08:46 +000013149 Py_INCREF((PyObject*) &StatResultType);
13150 PyModule_AddObject(m, "stat_result", (PyObject*) &StatResultType);
13151 Py_INCREF((PyObject*) &StatVFSResultType);
13152 PyModule_AddObject(m, "statvfs_result",
13153 (PyObject*) &StatVFSResultType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050013154
13155#if defined(HAVE_SCHED_SETPARAM) || defined(HAVE_SCHED_SETSCHEDULER)
Benjamin Peterson94b580d2011-08-02 17:30:04 -050013156 Py_INCREF(&SchedParamType);
13157 PyModule_AddObject(m, "sched_param", (PyObject *)&SchedParamType);
Benjamin Petersone3298dd2011-08-02 18:40:46 -050013158#endif
Thomas Wouters477c8d52006-05-27 19:21:47 +000013159
Larry Hastings605a62d2012-06-24 04:33:36 -070013160 times_result_desc.name = MODNAME ".times_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013161 if (PyStructSequence_InitType2(&TimesResultType, &times_result_desc) < 0)
13162 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070013163 PyModule_AddObject(m, "times_result", (PyObject *)&TimesResultType);
13164
13165 uname_result_desc.name = MODNAME ".uname_result";
Victor Stinner1c8f0592013-07-22 22:24:54 +020013166 if (PyStructSequence_InitType2(&UnameResultType, &uname_result_desc) < 0)
13167 return NULL;
Larry Hastings605a62d2012-06-24 04:33:36 -070013168 PyModule_AddObject(m, "uname_result", (PyObject *)&UnameResultType);
13169
Thomas Wouters477c8d52006-05-27 19:21:47 +000013170#ifdef __APPLE__
Victor Stinner8c62be82010-05-06 00:08:46 +000013171 /*
13172 * Step 2 of weak-linking support on Mac OS X.
13173 *
13174 * The code below removes functions that are not available on the
13175 * currently active platform.
13176 *
13177 * This block allow one to use a python binary that was build on
Larry Hastings9cf065c2012-06-22 16:30:09 -070013178 * OSX 10.4 on OSX 10.3, without losing access to new APIs on
Victor Stinner8c62be82010-05-06 00:08:46 +000013179 * OSX 10.4.
13180 */
Thomas Wouters477c8d52006-05-27 19:21:47 +000013181#ifdef HAVE_FSTATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000013182 if (fstatvfs == NULL) {
13183 if (PyObject_DelAttrString(m, "fstatvfs") == -1) {
13184 return NULL;
13185 }
13186 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013187#endif /* HAVE_FSTATVFS */
13188
13189#ifdef HAVE_STATVFS
Victor Stinner8c62be82010-05-06 00:08:46 +000013190 if (statvfs == NULL) {
13191 if (PyObject_DelAttrString(m, "statvfs") == -1) {
13192 return NULL;
13193 }
13194 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013195#endif /* HAVE_STATVFS */
13196
13197# ifdef HAVE_LCHOWN
Victor Stinner8c62be82010-05-06 00:08:46 +000013198 if (lchown == NULL) {
13199 if (PyObject_DelAttrString(m, "lchown") == -1) {
13200 return NULL;
13201 }
13202 }
Thomas Wouters477c8d52006-05-27 19:21:47 +000013203#endif /* HAVE_LCHOWN */
13204
13205
13206#endif /* __APPLE__ */
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013207
Antoine Pitrou9d20e0e2012-09-12 18:01:36 +020013208 Py_INCREF(&TerminalSizeType);
Antoine Pitroubcf2b592012-02-08 23:28:36 +010013209 PyModule_AddObject(m, "terminal_size", (PyObject*) &TerminalSizeType);
13210
Larry Hastings6fe20b32012-04-19 15:07:49 -070013211 billion = PyLong_FromLong(1000000000);
13212 if (!billion)
13213 return NULL;
13214
Larry Hastings9cf065c2012-06-22 16:30:09 -070013215 /* suppress "function not used" warnings */
13216 {
13217 int ignored;
13218 fd_specified("", -1);
13219 follow_symlinks_specified("", 1);
13220 dir_fd_and_follow_symlinks_invalid("chmod", DEFAULT_DIR_FD, 1);
13221 dir_fd_converter(Py_None, &ignored);
13222 dir_fd_unavailable(Py_None, &ignored);
13223 }
13224
13225 /*
13226 * provide list of locally available functions
13227 * so os.py can populate support_* lists
13228 */
13229 list = PyList_New(0);
13230 if (!list)
13231 return NULL;
13232 for (trace = have_functions; *trace; trace++) {
13233 PyObject *unicode = PyUnicode_DecodeASCII(*trace, strlen(*trace), NULL);
13234 if (!unicode)
13235 return NULL;
13236 if (PyList_Append(list, unicode))
13237 return NULL;
13238 Py_DECREF(unicode);
13239 }
13240 PyModule_AddObject(m, "_have_functions", list);
13241
13242 initialized = 1;
13243
Victor Stinner8c62be82010-05-06 00:08:46 +000013244 return m;
Guido van Rossumb6775db1994-08-01 11:34:53 +000013245}
Thomas Wouters49fd7fa2006-04-21 10:40:58 +000013246
13247#ifdef __cplusplus
13248}
13249#endif