blob: a8a08ed43aa69ac17531512bd5fb982b586e3eef [file] [log] [blame]
Guido van Rossumdd8cb441993-12-29 15:33:08 +00001# os.py -- either mac, dos or posix depending on what system we're on.
Guido van Rossum31104f41992-01-14 18:28:36 +00002
3# This exports:
4# - all functions from either posix or mac, e.g., os.unlink, os.stat, etc.
Guido van Rossum1a76ef21992-03-31 18:57:28 +00005# - os.path is either module posixpath or macpath
Guido van Rossum31104f41992-01-14 18:28:36 +00006# - os.name is either 'posix' or 'mac'
7# - os.curdir is a string representing the current directory ('.' or ':')
Guido van Rossum1a76ef21992-03-31 18:57:28 +00008# - os.pardir is a string representing the parent directory ('..' or '::')
Guido van Rossuma28dab51997-08-29 22:36:47 +00009# - os.sep is the (or a most common) pathname separator ('/' or ':' or '\\')
10# - os.altsep is the alternatte pathname separator (None or '/')
Guido van Rossum2979b011994-08-01 11:18:30 +000011# - os.pathsep is the component separator used in $PATH etc
12# - os.defpath is the default search path for executables
Guido van Rossum31104f41992-01-14 18:28:36 +000013
14# Programs that import and use 'os' stand a better chance of being
15# portable between different platforms. Of course, they must then
16# only use functions that are defined by all platforms (e.g., unlink
17# and opendir), and leave all pathname manipulation to os.path
18# (e.g., split and join).
19
Guido van Rossum2979b011994-08-01 11:18:30 +000020import sys
Guido van Rossuma28dab51997-08-29 22:36:47 +000021
22_names = sys.builtin_module_names
23
24altsep = None
25
26if 'posix' in _names:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000027 name = 'posix'
Guido van Rossume9387ea1998-05-22 15:26:04 +000028 linesep = '\n'
Guido van Rossum61de0ac1997-12-05 21:24:30 +000029 curdir = '.'; pardir = '..'; sep = '/'; pathsep = ':'
30 defpath = ':/bin:/usr/bin'
31 from posix import *
32 try:
33 from posix import _exit
34 except ImportError:
35 pass
36 import posixpath
37 path = posixpath
38 del posixpath
Guido van Rossuma28dab51997-08-29 22:36:47 +000039elif 'nt' in _names:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000040 name = 'nt'
Guido van Rossume9387ea1998-05-22 15:26:04 +000041 linesep = '\r\n'
Guido van Rossum61de0ac1997-12-05 21:24:30 +000042 curdir = '.'; pardir = '..'; sep = '\\'; pathsep = ';'
43 defpath = '.;C:\\bin'
44 from nt import *
Guido van Rossum67c65b21999-02-01 23:52:29 +000045 for i in ['_exit',
46 '_P_WAIT', '_P_NOWAIT', '_P_OVERLAY',
47 '_P_NOWAITO', '_P_DETACH']:
48 try:
49 exec "from nt import " + i
50 except ImportError:
51 pass
Guido van Rossum61de0ac1997-12-05 21:24:30 +000052 import ntpath
53 path = ntpath
54 del ntpath
Guido van Rossuma28dab51997-08-29 22:36:47 +000055elif 'dos' in _names:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000056 name = 'dos'
Guido van Rossume9387ea1998-05-22 15:26:04 +000057 linesep = '\r\n'
Guido van Rossum61de0ac1997-12-05 21:24:30 +000058 curdir = '.'; pardir = '..'; sep = '\\'; pathsep = ';'
59 defpath = '.;C:\\bin'
60 from dos import *
61 try:
62 from dos import _exit
63 except ImportError:
64 pass
65 import dospath
66 path = dospath
67 del dospath
Guido van Rossum8e9ebfd1997-11-22 21:53:48 +000068elif 'os2' in _names:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000069 name = 'os2'
Guido van Rossume9387ea1998-05-22 15:26:04 +000070 linesep = '\r\n'
Guido van Rossum61de0ac1997-12-05 21:24:30 +000071 curdir = '.'; pardir = '..'; sep = '\\'; pathsep = ';'
72 defpath = '.;C:\\bin'
73 from os2 import *
74 try:
75 from os2 import _exit
76 except ImportError:
77 pass
78 import ntpath
79 path = ntpath
80 del ntpath
Guido van Rossuma28dab51997-08-29 22:36:47 +000081elif 'mac' in _names:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000082 name = 'mac'
Guido van Rossume9387ea1998-05-22 15:26:04 +000083 linesep = '\r'
Guido van Rossum61de0ac1997-12-05 21:24:30 +000084 curdir = ':'; pardir = '::'; sep = ':'; pathsep = '\n'
85 defpath = ':'
86 from mac import *
87 try:
88 from mac import _exit
89 except ImportError:
90 pass
91 import macpath
92 path = macpath
93 del macpath
Guido van Rossum2979b011994-08-01 11:18:30 +000094else:
Guido van Rossum61de0ac1997-12-05 21:24:30 +000095 raise ImportError, 'no os specific module found'
Guido van Rossume65cce51993-11-08 15:05:21 +000096
Guido van Rossuma28dab51997-08-29 22:36:47 +000097del _names
98
Fred Drake02379091999-01-19 16:05:13 +000099sys.modules['os.path'] = path
100
Guido van Rossum4def7de1998-07-24 20:48:03 +0000101# Super directory utilities.
102# (Inspired by Eric Raymond; the doc strings are mostly his)
103
104def makedirs(name, mode=0777):
105 """makedirs(path [, mode=0777]) -> None
106
107 Super-mkdir; create a leaf directory and all intermediate ones.
108 Works like mkdir, except that any intermediate path segment (not
109 just the rightmost) will be created if it does not exist. This is
110 recursive.
111
112 """
113 head, tail = path.split(name)
114 if head and tail and not path.exists(head):
115 makedirs(head, mode)
116 mkdir(name, mode)
117
118def removedirs(name):
119 """removedirs(path) -> None
120
121 Super-rmdir; remove a leaf directory and empty all intermediate
122 ones. Works like rmdir except that, if the leaf directory is
123 successfully removed, directories corresponding to rightmost path
124 segments will be pruned way until either the whole path is
125 consumed or an error occurs. Errors during this latter phase are
126 ignored -- they generally mean that a directory was not empty.
127
128 """
129 rmdir(name)
130 head, tail = path.split(name)
131 while head and tail:
132 try:
133 rmdir(head)
134 except error:
135 break
136 head, tail = path.split(head)
137
138def renames(old, new):
139 """renames(old, new) -> None
140
141 Super-rename; create directories as necessary and delete any left
142 empty. Works like rename, except creation of any intermediate
143 directories needed to make the new pathname good is attempted
144 first. After the rename, directories corresponding to rightmost
145 path segments of the old name will be pruned way until either the
146 whole path is consumed or a nonempty directory is found.
147
148 Note: this function can fail with the new directory structure made
149 if you lack permissions needed to unlink the leaf directory or
150 file.
151
152 """
153 head, tail = path.split(new)
154 if head and tail and not path.exists(head):
155 makedirs(head)
156 rename(old, new)
157 head, tail = path.split(old)
158 if head and tail:
159 try:
160 removedirs(head)
161 except error:
162 pass
163
Guido van Rossuma28dab51997-08-29 22:36:47 +0000164# Make sure os.environ exists, at least
165try:
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000166 environ
Guido van Rossuma28dab51997-08-29 22:36:47 +0000167except NameError:
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000168 environ = {}
Guido van Rossuma28dab51997-08-29 22:36:47 +0000169
Guido van Rossume65cce51993-11-08 15:05:21 +0000170def execl(file, *args):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000171 execv(file, args)
Guido van Rossume65cce51993-11-08 15:05:21 +0000172
173def execle(file, *args):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000174 env = args[-1]
175 execve(file, args[:-1], env)
Guido van Rossume65cce51993-11-08 15:05:21 +0000176
177def execlp(file, *args):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000178 execvp(file, args)
Guido van Rossume65cce51993-11-08 15:05:21 +0000179
Guido van Rossum030afb11995-03-14 17:27:18 +0000180def execlpe(file, *args):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000181 env = args[-1]
182 execvpe(file, args[:-1], env)
Guido van Rossum030afb11995-03-14 17:27:18 +0000183
Guido van Rossume65cce51993-11-08 15:05:21 +0000184def execvp(file, args):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000185 _execvpe(file, args)
Guido van Rossum030afb11995-03-14 17:27:18 +0000186
187def execvpe(file, args, env):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000188 _execvpe(file, args, env)
Guido van Rossum030afb11995-03-14 17:27:18 +0000189
190_notfound = None
191def _execvpe(file, args, env = None):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000192 if env:
193 func = execve
194 argrest = (args, env)
195 else:
196 func = execv
197 argrest = (args,)
198 env = environ
199 global _notfound
200 head, tail = path.split(file)
201 if head:
202 apply(func, (file,) + argrest)
203 return
204 if env.has_key('PATH'):
205 envpath = env['PATH']
206 else:
207 envpath = defpath
208 import string
209 PATH = string.splitfields(envpath, pathsep)
210 if not _notfound:
211 import tempfile
212 # Exec a file that is guaranteed not to exist
213 try: execv(tempfile.mktemp(), ())
214 except error, _notfound: pass
215 exc, arg = error, _notfound
216 for dir in PATH:
217 fullname = path.join(dir, file)
218 try:
219 apply(func, (fullname,) + argrest)
220 except error, (errno, msg):
221 if errno != arg[0]:
222 exc, arg = error, (errno, msg)
223 raise exc, arg
Guido van Rossum2979b011994-08-01 11:18:30 +0000224
Guido van Rossum3b8e20d1996-07-24 00:55:17 +0000225# Change environ to automatically call putenv() if it exists
226try:
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000227 # This will fail if there's no putenv
228 putenv
Guido van Rossum3b8e20d1996-07-24 00:55:17 +0000229except NameError:
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000230 pass
Guido van Rossuma28dab51997-08-29 22:36:47 +0000231else:
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000232 import UserDict
Guido van Rossum3b8e20d1996-07-24 00:55:17 +0000233
Guido van Rossumda4d6da1998-08-04 16:01:23 +0000234 if name in ('os2', 'nt', 'dos'): # Where Env Var Names Must Be UPPERCASE
235 # But we store them as upper case
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000236 import string
237 class _Environ(UserDict.UserDict):
238 def __init__(self, environ):
239 UserDict.UserDict.__init__(self)
Guido van Rossumda4d6da1998-08-04 16:01:23 +0000240 data = self.data
241 upper = string.upper
242 for k, v in environ.items():
243 data[upper(k)] = v
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000244 def __setitem__(self, key, item):
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000245 putenv(key, item)
Guido van Rossumda4d6da1998-08-04 16:01:23 +0000246 key = string.upper(key)
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000247 self.data[key] = item
248 def __getitem__(self, key):
249 return self.data[string.upper(key)]
Guido van Rossum3b8e20d1996-07-24 00:55:17 +0000250
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000251 else: # Where Env Var Names Can Be Mixed Case
252 class _Environ(UserDict.UserDict):
253 def __init__(self, environ):
254 UserDict.UserDict.__init__(self)
255 self.data = environ
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000256 def __setitem__(self, key, item):
257 putenv(key, item)
258 self.data[key] = item
Guido van Rossum61de0ac1997-12-05 21:24:30 +0000259
260 environ = _Environ(environ)