blob: a72f83c8dcfe9b2c39da86897dbd204d04b44146 [file] [log] [blame]
Neal Norwitze241ce82003-02-17 18:17:05 +00001"Test posix functions"
2
Benjamin Petersonee8712c2008-05-20 21:35:26 +00003from test import support
Antoine Pitrou346cbd32017-05-27 17:50:54 +02004from test.support.script_helper import assert_python_ok
Xavier de Gaye3a4e9892016-12-13 10:00:01 +01005android_not_root = support.android_not_root
R. David Murrayeb3615d2009-04-22 02:24:39 +00006
7# Skip these tests if there is no posix module.
8posix = support.import_module('posix')
Neal Norwitze241ce82003-02-17 18:17:05 +00009
Antoine Pitroub7572f02009-12-02 20:46:48 +000010import errno
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +000011import sys
Neal Norwitze241ce82003-02-17 18:17:05 +000012import time
13import os
Charles-François Nataliab2d58e2012-04-17 19:48:35 +020014import platform
Christian Heimesd5e2b6f2008-03-19 21:50:51 +000015import pwd
Benjamin Peterson052a02b2010-08-17 01:27:09 +000016import stat
Ned Deilyba2eab22011-07-26 13:53:55 -070017import tempfile
Neal Norwitze241ce82003-02-17 18:17:05 +000018import unittest
19import warnings
R. David Murraya21e4ca2009-03-31 23:16:50 +000020
Ned Deilyba2eab22011-07-26 13:53:55 -070021_DUMMY_SYMLINK = os.path.join(tempfile.gettempdir(),
22 support.TESTFN + '-dummy-symlink')
Neal Norwitze241ce82003-02-17 18:17:05 +000023
24class PosixTester(unittest.TestCase):
25
26 def setUp(self):
27 # create empty file
Benjamin Petersonee8712c2008-05-20 21:35:26 +000028 fp = open(support.TESTFN, 'w+')
Neal Norwitze241ce82003-02-17 18:17:05 +000029 fp.close()
Ned Deily3eb67d52011-06-28 00:00:28 -070030 self.teardown_files = [ support.TESTFN ]
Brett Cannonc8d502e2010-03-20 21:53:28 +000031 self._warnings_manager = support.check_warnings()
32 self._warnings_manager.__enter__()
33 warnings.filterwarnings('ignore', '.* potential security risk .*',
34 RuntimeWarning)
Neal Norwitze241ce82003-02-17 18:17:05 +000035
36 def tearDown(self):
Ned Deily3eb67d52011-06-28 00:00:28 -070037 for teardown_file in self.teardown_files:
38 support.unlink(teardown_file)
Brett Cannonc8d502e2010-03-20 21:53:28 +000039 self._warnings_manager.__exit__(None, None, None)
Neal Norwitze241ce82003-02-17 18:17:05 +000040
41 def testNoArgFunctions(self):
42 # test posix functions which take no arguments and have
43 # no side-effects which we need to cleanup (e.g., fork, wait, abort)
Guido van Rossumf0af3e32008-10-02 18:55:37 +000044 NO_ARG_FUNCTIONS = [ "ctermid", "getcwd", "getcwdb", "uname",
Guido van Rossum687b9c02007-10-25 23:18:51 +000045 "times", "getloadavg",
Neal Norwitze241ce82003-02-17 18:17:05 +000046 "getegid", "geteuid", "getgid", "getgroups",
Ross Lagerwall7807c352011-03-17 20:20:30 +020047 "getpid", "getpgrp", "getppid", "getuid", "sync",
Neal Norwitze241ce82003-02-17 18:17:05 +000048 ]
Neal Norwitz71b13e82003-02-23 22:12:24 +000049
Neal Norwitze241ce82003-02-17 18:17:05 +000050 for name in NO_ARG_FUNCTIONS:
51 posix_func = getattr(posix, name, None)
52 if posix_func is not None:
53 posix_func()
Neal Norwitz2ff51a82003-02-17 22:40:31 +000054 self.assertRaises(TypeError, posix_func, 1)
Neal Norwitze241ce82003-02-17 18:17:05 +000055
Serhiy Storchaka43767632013-11-03 21:31:38 +020056 @unittest.skipUnless(hasattr(posix, 'getresuid'),
57 'test needs posix.getresuid()')
58 def test_getresuid(self):
59 user_ids = posix.getresuid()
60 self.assertEqual(len(user_ids), 3)
61 for val in user_ids:
62 self.assertGreaterEqual(val, 0)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000063
Serhiy Storchaka43767632013-11-03 21:31:38 +020064 @unittest.skipUnless(hasattr(posix, 'getresgid'),
65 'test needs posix.getresgid()')
66 def test_getresgid(self):
67 group_ids = posix.getresgid()
68 self.assertEqual(len(group_ids), 3)
69 for val in group_ids:
70 self.assertGreaterEqual(val, 0)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000071
Serhiy Storchaka43767632013-11-03 21:31:38 +020072 @unittest.skipUnless(hasattr(posix, 'setresuid'),
73 'test needs posix.setresuid()')
74 def test_setresuid(self):
75 current_user_ids = posix.getresuid()
76 self.assertIsNone(posix.setresuid(*current_user_ids))
77 # -1 means don't change that value.
78 self.assertIsNone(posix.setresuid(-1, -1, -1))
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000079
Serhiy Storchaka43767632013-11-03 21:31:38 +020080 @unittest.skipUnless(hasattr(posix, 'setresuid'),
81 'test needs posix.setresuid()')
82 def test_setresuid_exception(self):
83 # Don't do this test if someone is silly enough to run us as root.
84 current_user_ids = posix.getresuid()
85 if 0 not in current_user_ids:
86 new_user_ids = (current_user_ids[0]+1, -1, -1)
87 self.assertRaises(OSError, posix.setresuid, *new_user_ids)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000088
Serhiy Storchaka43767632013-11-03 21:31:38 +020089 @unittest.skipUnless(hasattr(posix, 'setresgid'),
90 'test needs posix.setresgid()')
91 def test_setresgid(self):
92 current_group_ids = posix.getresgid()
93 self.assertIsNone(posix.setresgid(*current_group_ids))
94 # -1 means don't change that value.
95 self.assertIsNone(posix.setresgid(-1, -1, -1))
Martin v. Löwis7aed61a2009-11-27 14:09:49 +000096
Serhiy Storchaka43767632013-11-03 21:31:38 +020097 @unittest.skipUnless(hasattr(posix, 'setresgid'),
98 'test needs posix.setresgid()')
99 def test_setresgid_exception(self):
100 # Don't do this test if someone is silly enough to run us as root.
101 current_group_ids = posix.getresgid()
102 if 0 not in current_group_ids:
103 new_group_ids = (current_group_ids[0]+1, -1, -1)
104 self.assertRaises(OSError, posix.setresgid, *new_group_ids)
Martin v. Löwis7aed61a2009-11-27 14:09:49 +0000105
Antoine Pitroub7572f02009-12-02 20:46:48 +0000106 @unittest.skipUnless(hasattr(posix, 'initgroups'),
107 "test needs os.initgroups()")
108 def test_initgroups(self):
109 # It takes a string and an integer; check that it raises a TypeError
110 # for other argument lists.
111 self.assertRaises(TypeError, posix.initgroups)
112 self.assertRaises(TypeError, posix.initgroups, None)
113 self.assertRaises(TypeError, posix.initgroups, 3, "foo")
114 self.assertRaises(TypeError, posix.initgroups, "foo", 3, object())
115
116 # If a non-privileged user invokes it, it should fail with OSError
117 # EPERM.
118 if os.getuid() != 0:
Charles-François Natalie8a255a2012-05-02 20:01:38 +0200119 try:
120 name = pwd.getpwuid(posix.getuid()).pw_name
121 except KeyError:
122 # the current UID may not have a pwd entry
123 raise unittest.SkipTest("need a pwd entry")
Antoine Pitroub7572f02009-12-02 20:46:48 +0000124 try:
125 posix.initgroups(name, 13)
126 except OSError as e:
Ezio Melottib3aedd42010-11-20 19:04:17 +0000127 self.assertEqual(e.errno, errno.EPERM)
Antoine Pitroub7572f02009-12-02 20:46:48 +0000128 else:
129 self.fail("Expected OSError to be raised by initgroups")
130
Serhiy Storchaka43767632013-11-03 21:31:38 +0200131 @unittest.skipUnless(hasattr(posix, 'statvfs'),
132 'test needs posix.statvfs()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000133 def test_statvfs(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200134 self.assertTrue(posix.statvfs(os.curdir))
Neal Norwitze241ce82003-02-17 18:17:05 +0000135
Serhiy Storchaka43767632013-11-03 21:31:38 +0200136 @unittest.skipUnless(hasattr(posix, 'fstatvfs'),
137 'test needs posix.fstatvfs()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000138 def test_fstatvfs(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200139 fp = open(support.TESTFN)
140 try:
141 self.assertTrue(posix.fstatvfs(fp.fileno()))
142 self.assertTrue(posix.statvfs(fp.fileno()))
143 finally:
144 fp.close()
Neal Norwitze241ce82003-02-17 18:17:05 +0000145
Serhiy Storchaka43767632013-11-03 21:31:38 +0200146 @unittest.skipUnless(hasattr(posix, 'ftruncate'),
147 'test needs posix.ftruncate()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000148 def test_ftruncate(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200149 fp = open(support.TESTFN, 'w+')
150 try:
151 # we need to have some data to truncate
152 fp.write('test')
153 fp.flush()
154 posix.ftruncate(fp.fileno(), 0)
155 finally:
156 fp.close()
Neal Norwitze241ce82003-02-17 18:17:05 +0000157
Ross Lagerwall7807c352011-03-17 20:20:30 +0200158 @unittest.skipUnless(hasattr(posix, 'truncate'), "test needs posix.truncate()")
159 def test_truncate(self):
160 with open(support.TESTFN, 'w') as fp:
161 fp.write('test')
162 fp.flush()
163 posix.truncate(support.TESTFN, 0)
164
Larry Hastings9cf065c2012-06-22 16:30:09 -0700165 @unittest.skipUnless(getattr(os, 'execve', None) in os.supports_fd, "test needs execve() to support the fd parameter")
Ross Lagerwall7807c352011-03-17 20:20:30 +0200166 @unittest.skipUnless(hasattr(os, 'fork'), "test needs os.fork()")
Ross Lagerwalldedf6cf2011-03-20 18:27:05 +0200167 @unittest.skipUnless(hasattr(os, 'waitpid'), "test needs os.waitpid()")
Ross Lagerwall7807c352011-03-17 20:20:30 +0200168 def test_fexecve(self):
169 fp = os.open(sys.executable, os.O_RDONLY)
170 try:
171 pid = os.fork()
172 if pid == 0:
173 os.chdir(os.path.split(sys.executable)[0])
Larry Hastings9cf065c2012-06-22 16:30:09 -0700174 posix.execve(fp, [sys.executable, '-c', 'pass'], os.environ)
Ross Lagerwall7807c352011-03-17 20:20:30 +0200175 else:
Ross Lagerwalldedf6cf2011-03-20 18:27:05 +0200176 self.assertEqual(os.waitpid(pid, 0), (pid, 0))
Ross Lagerwall7807c352011-03-17 20:20:30 +0200177 finally:
178 os.close(fp)
179
180 @unittest.skipUnless(hasattr(posix, 'waitid'), "test needs posix.waitid()")
181 @unittest.skipUnless(hasattr(os, 'fork'), "test needs os.fork()")
182 def test_waitid(self):
183 pid = os.fork()
184 if pid == 0:
185 os.chdir(os.path.split(sys.executable)[0])
186 posix.execve(sys.executable, [sys.executable, '-c', 'pass'], os.environ)
187 else:
188 res = posix.waitid(posix.P_PID, pid, posix.WEXITED)
189 self.assertEqual(pid, res.si_pid)
190
Antoine Pitrou346cbd32017-05-27 17:50:54 +0200191 @unittest.skipUnless(hasattr(os, 'fork'), "test needs os.fork()")
192 def test_register_after_fork(self):
193 code = """if 1:
194 import os
195
196 r, w = os.pipe()
197 fin_r, fin_w = os.pipe()
198
199 os.register_at_fork(lambda: os.write(w, b'A'), when='before')
200 os.register_at_fork(lambda: os.write(w, b'B'), when='before')
201 os.register_at_fork(lambda: os.write(w, b'C'), when='parent')
202 os.register_at_fork(lambda: os.write(w, b'D'), when='parent')
203 os.register_at_fork(lambda: os.write(w, b'E'), when='child')
204 os.register_at_fork(lambda: os.write(w, b'F'), when='child')
205
206 pid = os.fork()
207 if pid == 0:
208 # At this point, after-forkers have already been executed
209 os.close(w)
210 # Wait for parent to tell us to exit
211 os.read(fin_r, 1)
212 os._exit(0)
213 else:
214 try:
215 os.close(w)
216 with open(r, "rb") as f:
217 data = f.read()
218 assert len(data) == 6, data
219 # Check before-fork callbacks
220 assert data[:2] == b'BA', data
221 # Check after-fork callbacks
222 assert sorted(data[2:]) == list(b'CDEF'), data
223 assert data.index(b'C') < data.index(b'D'), data
224 assert data.index(b'E') < data.index(b'F'), data
225 finally:
226 os.write(fin_w, b'!')
227 """
228 assert_python_ok('-c', code)
229
Ross Lagerwall7807c352011-03-17 20:20:30 +0200230 @unittest.skipUnless(hasattr(posix, 'lockf'), "test needs posix.lockf()")
231 def test_lockf(self):
232 fd = os.open(support.TESTFN, os.O_WRONLY | os.O_CREAT)
233 try:
234 os.write(fd, b'test')
235 os.lseek(fd, 0, os.SEEK_SET)
236 posix.lockf(fd, posix.F_LOCK, 4)
237 # section is locked
238 posix.lockf(fd, posix.F_ULOCK, 4)
239 finally:
240 os.close(fd)
241
242 @unittest.skipUnless(hasattr(posix, 'pread'), "test needs posix.pread()")
243 def test_pread(self):
244 fd = os.open(support.TESTFN, os.O_RDWR | os.O_CREAT)
245 try:
246 os.write(fd, b'test')
247 os.lseek(fd, 0, os.SEEK_SET)
248 self.assertEqual(b'es', posix.pread(fd, 2, 1))
Florent Xiclunae41f0de2011-11-11 19:39:25 +0100249 # the first pread() shouldn't disturb the file offset
Ross Lagerwall7807c352011-03-17 20:20:30 +0200250 self.assertEqual(b'te', posix.read(fd, 2))
251 finally:
252 os.close(fd)
253
254 @unittest.skipUnless(hasattr(posix, 'pwrite'), "test needs posix.pwrite()")
255 def test_pwrite(self):
256 fd = os.open(support.TESTFN, os.O_RDWR | os.O_CREAT)
257 try:
258 os.write(fd, b'test')
259 os.lseek(fd, 0, os.SEEK_SET)
260 posix.pwrite(fd, b'xx', 1)
261 self.assertEqual(b'txxt', posix.read(fd, 4))
262 finally:
263 os.close(fd)
264
265 @unittest.skipUnless(hasattr(posix, 'posix_fallocate'),
266 "test needs posix.posix_fallocate()")
267 def test_posix_fallocate(self):
268 fd = os.open(support.TESTFN, os.O_WRONLY | os.O_CREAT)
269 try:
270 posix.posix_fallocate(fd, 0, 10)
271 except OSError as inst:
272 # issue10812, ZFS doesn't appear to support posix_fallocate,
273 # so skip Solaris-based since they are likely to have ZFS.
274 if inst.errno != errno.EINVAL or not sys.platform.startswith("sunos"):
275 raise
276 finally:
277 os.close(fd)
278
279 @unittest.skipUnless(hasattr(posix, 'posix_fadvise'),
280 "test needs posix.posix_fadvise()")
281 def test_posix_fadvise(self):
282 fd = os.open(support.TESTFN, os.O_RDONLY)
283 try:
284 posix.posix_fadvise(fd, 0, 0, posix.POSIX_FADV_WILLNEED)
285 finally:
286 os.close(fd)
287
Larry Hastings9cf065c2012-06-22 16:30:09 -0700288 @unittest.skipUnless(os.utime in os.supports_fd, "test needs fd support in os.utime")
289 def test_utime_with_fd(self):
Ross Lagerwall7807c352011-03-17 20:20:30 +0200290 now = time.time()
291 fd = os.open(support.TESTFN, os.O_RDONLY)
292 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700293 posix.utime(fd)
294 posix.utime(fd, None)
295 self.assertRaises(TypeError, posix.utime, fd, (None, None))
296 self.assertRaises(TypeError, posix.utime, fd, (now, None))
297 self.assertRaises(TypeError, posix.utime, fd, (None, now))
298 posix.utime(fd, (int(now), int(now)))
299 posix.utime(fd, (now, now))
300 self.assertRaises(ValueError, posix.utime, fd, (now, now), ns=(now, now))
301 self.assertRaises(ValueError, posix.utime, fd, (now, 0), ns=(None, None))
302 self.assertRaises(ValueError, posix.utime, fd, (None, None), ns=(now, 0))
303 posix.utime(fd, (int(now), int((now - int(now)) * 1e9)))
304 posix.utime(fd, ns=(int(now), int((now - int(now)) * 1e9)))
305
Ross Lagerwall7807c352011-03-17 20:20:30 +0200306 finally:
307 os.close(fd)
308
Larry Hastings9cf065c2012-06-22 16:30:09 -0700309 @unittest.skipUnless(os.utime in os.supports_follow_symlinks, "test needs follow_symlinks support in os.utime")
310 def test_utime_nofollow_symlinks(self):
Ross Lagerwall7807c352011-03-17 20:20:30 +0200311 now = time.time()
Larry Hastings9cf065c2012-06-22 16:30:09 -0700312 posix.utime(support.TESTFN, None, follow_symlinks=False)
313 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, None), follow_symlinks=False)
314 self.assertRaises(TypeError, posix.utime, support.TESTFN, (now, None), follow_symlinks=False)
315 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, now), follow_symlinks=False)
316 posix.utime(support.TESTFN, (int(now), int(now)), follow_symlinks=False)
317 posix.utime(support.TESTFN, (now, now), follow_symlinks=False)
318 posix.utime(support.TESTFN, follow_symlinks=False)
Ross Lagerwall7807c352011-03-17 20:20:30 +0200319
320 @unittest.skipUnless(hasattr(posix, 'writev'), "test needs posix.writev()")
321 def test_writev(self):
322 fd = os.open(support.TESTFN, os.O_RDWR | os.O_CREAT)
323 try:
Victor Stinner57ddf782014-01-08 15:21:28 +0100324 n = os.writev(fd, (b'test1', b'tt2', b't3'))
325 self.assertEqual(n, 10)
326
Ross Lagerwall7807c352011-03-17 20:20:30 +0200327 os.lseek(fd, 0, os.SEEK_SET)
328 self.assertEqual(b'test1tt2t3', posix.read(fd, 10))
Victor Stinner57ddf782014-01-08 15:21:28 +0100329
330 # Issue #20113: empty list of buffers should not crash
Victor Stinnercd5ca6a2014-01-08 16:01:31 +0100331 try:
332 size = posix.writev(fd, [])
333 except OSError:
334 # writev(fd, []) raises OSError(22, "Invalid argument")
335 # on OpenIndiana
336 pass
337 else:
338 self.assertEqual(size, 0)
Ross Lagerwall7807c352011-03-17 20:20:30 +0200339 finally:
340 os.close(fd)
341
342 @unittest.skipUnless(hasattr(posix, 'readv'), "test needs posix.readv()")
343 def test_readv(self):
344 fd = os.open(support.TESTFN, os.O_RDWR | os.O_CREAT)
345 try:
346 os.write(fd, b'test1tt2t3')
347 os.lseek(fd, 0, os.SEEK_SET)
348 buf = [bytearray(i) for i in [5, 3, 2]]
349 self.assertEqual(posix.readv(fd, buf), 10)
350 self.assertEqual([b'test1', b'tt2', b't3'], [bytes(i) for i in buf])
Victor Stinner57ddf782014-01-08 15:21:28 +0100351
352 # Issue #20113: empty list of buffers should not crash
Victor Stinnercd5ca6a2014-01-08 16:01:31 +0100353 try:
354 size = posix.readv(fd, [])
355 except OSError:
356 # readv(fd, []) raises OSError(22, "Invalid argument")
357 # on OpenIndiana
358 pass
359 else:
360 self.assertEqual(size, 0)
Ross Lagerwall7807c352011-03-17 20:20:30 +0200361 finally:
362 os.close(fd)
363
Serhiy Storchaka43767632013-11-03 21:31:38 +0200364 @unittest.skipUnless(hasattr(posix, 'dup'),
365 'test needs posix.dup()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000366 def test_dup(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200367 fp = open(support.TESTFN)
368 try:
369 fd = posix.dup(fp.fileno())
370 self.assertIsInstance(fd, int)
371 os.close(fd)
372 finally:
373 fp.close()
Neal Norwitze241ce82003-02-17 18:17:05 +0000374
Serhiy Storchaka43767632013-11-03 21:31:38 +0200375 @unittest.skipUnless(hasattr(posix, 'confstr'),
376 'test needs posix.confstr()')
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000377 def test_confstr(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200378 self.assertRaises(ValueError, posix.confstr, "CS_garbage")
379 self.assertEqual(len(posix.confstr("CS_PATH")) > 0, True)
Thomas Wouters49fd7fa2006-04-21 10:40:58 +0000380
Serhiy Storchaka43767632013-11-03 21:31:38 +0200381 @unittest.skipUnless(hasattr(posix, 'dup2'),
382 'test needs posix.dup2()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000383 def test_dup2(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200384 fp1 = open(support.TESTFN)
385 fp2 = open(support.TESTFN)
386 try:
387 posix.dup2(fp1.fileno(), fp2.fileno())
388 finally:
389 fp1.close()
390 fp2.close()
Neal Norwitze241ce82003-02-17 18:17:05 +0000391
Charles-François Natali1e045b12011-05-22 20:42:32 +0200392 @unittest.skipUnless(hasattr(os, 'O_CLOEXEC'), "needs os.O_CLOEXEC")
Charles-François Natali239bb962011-06-03 12:55:15 +0200393 @support.requires_linux_version(2, 6, 23)
Charles-François Natali1e045b12011-05-22 20:42:32 +0200394 def test_oscloexec(self):
395 fd = os.open(support.TESTFN, os.O_RDONLY|os.O_CLOEXEC)
396 self.addCleanup(os.close, fd)
Victor Stinner1db9e7b2014-07-29 22:32:47 +0200397 self.assertFalse(os.get_inheritable(fd))
Charles-François Natali1e045b12011-05-22 20:42:32 +0200398
Serhiy Storchaka43767632013-11-03 21:31:38 +0200399 @unittest.skipUnless(hasattr(posix, 'O_EXLOCK'),
400 'test needs posix.O_EXLOCK')
Skip Montanaro98470002005-06-17 01:14:49 +0000401 def test_osexlock(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200402 fd = os.open(support.TESTFN,
403 os.O_WRONLY|os.O_EXLOCK|os.O_CREAT)
404 self.assertRaises(OSError, os.open, support.TESTFN,
405 os.O_WRONLY|os.O_EXLOCK|os.O_NONBLOCK)
406 os.close(fd)
407
408 if hasattr(posix, "O_SHLOCK"):
Benjamin Petersonee8712c2008-05-20 21:35:26 +0000409 fd = os.open(support.TESTFN,
Serhiy Storchaka43767632013-11-03 21:31:38 +0200410 os.O_WRONLY|os.O_SHLOCK|os.O_CREAT)
Benjamin Petersonee8712c2008-05-20 21:35:26 +0000411 self.assertRaises(OSError, os.open, support.TESTFN,
Skip Montanaro98470002005-06-17 01:14:49 +0000412 os.O_WRONLY|os.O_EXLOCK|os.O_NONBLOCK)
413 os.close(fd)
414
Serhiy Storchaka43767632013-11-03 21:31:38 +0200415 @unittest.skipUnless(hasattr(posix, 'O_SHLOCK'),
416 'test needs posix.O_SHLOCK')
Skip Montanaro98470002005-06-17 01:14:49 +0000417 def test_osshlock(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200418 fd1 = os.open(support.TESTFN,
419 os.O_WRONLY|os.O_SHLOCK|os.O_CREAT)
420 fd2 = os.open(support.TESTFN,
421 os.O_WRONLY|os.O_SHLOCK|os.O_CREAT)
422 os.close(fd2)
423 os.close(fd1)
424
425 if hasattr(posix, "O_EXLOCK"):
426 fd = os.open(support.TESTFN,
Skip Montanaro98470002005-06-17 01:14:49 +0000427 os.O_WRONLY|os.O_SHLOCK|os.O_CREAT)
Serhiy Storchaka43767632013-11-03 21:31:38 +0200428 self.assertRaises(OSError, os.open, support.TESTFN,
429 os.O_RDONLY|os.O_EXLOCK|os.O_NONBLOCK)
430 os.close(fd)
Skip Montanaro98470002005-06-17 01:14:49 +0000431
Serhiy Storchaka43767632013-11-03 21:31:38 +0200432 @unittest.skipUnless(hasattr(posix, 'fstat'),
433 'test needs posix.fstat()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000434 def test_fstat(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200435 fp = open(support.TESTFN)
436 try:
437 self.assertTrue(posix.fstat(fp.fileno()))
438 self.assertTrue(posix.stat(fp.fileno()))
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200439
Serhiy Storchaka43767632013-11-03 21:31:38 +0200440 self.assertRaisesRegex(TypeError,
Brett Cannon3f9183b2016-08-26 14:44:48 -0700441 'should be string, bytes, os.PathLike or integer, not',
Serhiy Storchaka43767632013-11-03 21:31:38 +0200442 posix.stat, float(fp.fileno()))
443 finally:
444 fp.close()
Neal Norwitze241ce82003-02-17 18:17:05 +0000445
Serhiy Storchaka43767632013-11-03 21:31:38 +0200446 @unittest.skipUnless(hasattr(posix, 'stat'),
447 'test needs posix.stat()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000448 def test_stat(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200449 self.assertTrue(posix.stat(support.TESTFN))
450 self.assertTrue(posix.stat(os.fsencode(support.TESTFN)))
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200451
Serhiy Storchakad73c3182016-08-06 23:22:08 +0300452 self.assertWarnsRegex(DeprecationWarning,
Brett Cannon3f9183b2016-08-26 14:44:48 -0700453 'should be string, bytes, os.PathLike or integer, not',
Serhiy Storchakad73c3182016-08-06 23:22:08 +0300454 posix.stat, bytearray(os.fsencode(support.TESTFN)))
Serhiy Storchaka43767632013-11-03 21:31:38 +0200455 self.assertRaisesRegex(TypeError,
Brett Cannon3f9183b2016-08-26 14:44:48 -0700456 'should be string, bytes, os.PathLike or integer, not',
Serhiy Storchaka43767632013-11-03 21:31:38 +0200457 posix.stat, None)
458 self.assertRaisesRegex(TypeError,
Brett Cannon3f9183b2016-08-26 14:44:48 -0700459 'should be string, bytes, os.PathLike or integer, not',
Serhiy Storchaka43767632013-11-03 21:31:38 +0200460 posix.stat, list(support.TESTFN))
461 self.assertRaisesRegex(TypeError,
Brett Cannon3f9183b2016-08-26 14:44:48 -0700462 'should be string, bytes, os.PathLike or integer, not',
Serhiy Storchaka43767632013-11-03 21:31:38 +0200463 posix.stat, list(os.fsencode(support.TESTFN)))
Neal Norwitze241ce82003-02-17 18:17:05 +0000464
Benjamin Peterson052a02b2010-08-17 01:27:09 +0000465 @unittest.skipUnless(hasattr(posix, 'mkfifo'), "don't have mkfifo()")
Xavier de Gaye3a4e9892016-12-13 10:00:01 +0100466 @unittest.skipIf(android_not_root, "mkfifo not allowed, non root user")
Benjamin Peterson052a02b2010-08-17 01:27:09 +0000467 def test_mkfifo(self):
468 support.unlink(support.TESTFN)
469 posix.mkfifo(support.TESTFN, stat.S_IRUSR | stat.S_IWUSR)
470 self.assertTrue(stat.S_ISFIFO(posix.stat(support.TESTFN).st_mode))
471
472 @unittest.skipUnless(hasattr(posix, 'mknod') and hasattr(stat, 'S_IFIFO'),
473 "don't have mknod()/S_IFIFO")
Xavier de Gaye3a4e9892016-12-13 10:00:01 +0100474 @unittest.skipIf(android_not_root, "mknod not allowed, non root user")
Benjamin Peterson052a02b2010-08-17 01:27:09 +0000475 def test_mknod(self):
476 # Test using mknod() to create a FIFO (the only use specified
477 # by POSIX).
478 support.unlink(support.TESTFN)
479 mode = stat.S_IFIFO | stat.S_IRUSR | stat.S_IWUSR
480 try:
481 posix.mknod(support.TESTFN, mode, 0)
482 except OSError as e:
483 # Some old systems don't allow unprivileged users to use
484 # mknod(), or only support creating device nodes.
485 self.assertIn(e.errno, (errno.EPERM, errno.EINVAL))
486 else:
487 self.assertTrue(stat.S_ISFIFO(posix.stat(support.TESTFN).st_mode))
488
Martin Panterbf19d162015-09-09 01:01:13 +0000489 # Keyword arguments are also supported
490 support.unlink(support.TESTFN)
491 try:
492 posix.mknod(path=support.TESTFN, mode=mode, device=0,
493 dir_fd=None)
494 except OSError as e:
495 self.assertIn(e.errno, (errno.EPERM, errno.EINVAL))
496
Serhiy Storchaka16b2e4f2015-04-20 09:22:13 +0300497 @unittest.skipUnless(hasattr(posix, 'stat'), 'test needs posix.stat()')
498 @unittest.skipUnless(hasattr(posix, 'makedev'), 'test needs posix.makedev()')
499 def test_makedev(self):
500 st = posix.stat(support.TESTFN)
501 dev = st.st_dev
502 self.assertIsInstance(dev, int)
503 self.assertGreaterEqual(dev, 0)
504
505 major = posix.major(dev)
506 self.assertIsInstance(major, int)
507 self.assertGreaterEqual(major, 0)
508 self.assertEqual(posix.major(dev), major)
509 self.assertRaises(TypeError, posix.major, float(dev))
510 self.assertRaises(TypeError, posix.major)
511 self.assertRaises((ValueError, OverflowError), posix.major, -1)
512
513 minor = posix.minor(dev)
514 self.assertIsInstance(minor, int)
515 self.assertGreaterEqual(minor, 0)
516 self.assertEqual(posix.minor(dev), minor)
517 self.assertRaises(TypeError, posix.minor, float(dev))
518 self.assertRaises(TypeError, posix.minor)
519 self.assertRaises((ValueError, OverflowError), posix.minor, -1)
520
521 self.assertEqual(posix.makedev(major, minor), dev)
522 self.assertRaises(TypeError, posix.makedev, float(major), minor)
523 self.assertRaises(TypeError, posix.makedev, major, float(minor))
524 self.assertRaises(TypeError, posix.makedev, major)
525 self.assertRaises(TypeError, posix.makedev)
526
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200527 def _test_all_chown_common(self, chown_func, first_param, stat_func):
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000528 """Common code for chown, fchown and lchown tests."""
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200529 def check_stat(uid, gid):
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200530 if stat_func is not None:
531 stat = stat_func(first_param)
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200532 self.assertEqual(stat.st_uid, uid)
533 self.assertEqual(stat.st_gid, gid)
534 uid = os.getuid()
535 gid = os.getgid()
Charles-François Nataliab2d58e2012-04-17 19:48:35 +0200536 # test a successful chown call
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200537 chown_func(first_param, uid, gid)
538 check_stat(uid, gid)
539 chown_func(first_param, -1, gid)
540 check_stat(uid, gid)
541 chown_func(first_param, uid, -1)
542 check_stat(uid, gid)
Charles-François Nataliab2d58e2012-04-17 19:48:35 +0200543
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200544 if uid == 0:
545 # Try an amusingly large uid/gid to make sure we handle
546 # large unsigned values. (chown lets you use any
547 # uid/gid you like, even if they aren't defined.)
548 #
549 # This problem keeps coming up:
550 # http://bugs.python.org/issue1747858
551 # http://bugs.python.org/issue4591
552 # http://bugs.python.org/issue15301
553 # Hopefully the fix in 4591 fixes it for good!
554 #
555 # This part of the test only runs when run as root.
556 # Only scary people run their tests as root.
557
558 big_value = 2**31
559 chown_func(first_param, big_value, big_value)
560 check_stat(big_value, big_value)
561 chown_func(first_param, -1, -1)
562 check_stat(big_value, big_value)
563 chown_func(first_param, uid, gid)
564 check_stat(uid, gid)
Charles-François Nataliab2d58e2012-04-17 19:48:35 +0200565 elif platform.system() in ('HP-UX', 'SunOS'):
566 # HP-UX and Solaris can allow a non-root user to chown() to root
567 # (issue #5113)
568 raise unittest.SkipTest("Skipping because of non-standard chown() "
569 "behavior")
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000570 else:
571 # non-root cannot chown to root, raises OSError
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200572 self.assertRaises(OSError, chown_func, first_param, 0, 0)
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200573 check_stat(uid, gid)
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200574 self.assertRaises(OSError, chown_func, first_param, 0, -1)
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200575 check_stat(uid, gid)
Serhiy Storchakaa2964b32013-02-21 14:34:36 +0200576 if 0 not in os.getgroups():
Serhiy Storchakab3d62ce2013-02-20 19:48:22 +0200577 self.assertRaises(OSError, chown_func, first_param, -1, 0)
578 check_stat(uid, gid)
Serhiy Storchaka54db2fd2013-02-20 19:40:25 +0200579 # test illegal types
580 for t in str, float:
581 self.assertRaises(TypeError, chown_func, first_param, t(uid), gid)
582 check_stat(uid, gid)
583 self.assertRaises(TypeError, chown_func, first_param, uid, t(gid))
584 check_stat(uid, gid)
Christian Heimesd5e2b6f2008-03-19 21:50:51 +0000585
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000586 @unittest.skipUnless(hasattr(posix, 'chown'), "test needs os.chown()")
587 def test_chown(self):
588 # raise an OSError if the file does not exist
589 os.unlink(support.TESTFN)
590 self.assertRaises(OSError, posix.chown, support.TESTFN, -1, -1)
Christian Heimesd5e2b6f2008-03-19 21:50:51 +0000591
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000592 # re-create the file
Victor Stinnerbf816222011-06-30 23:25:47 +0200593 support.create_empty_file(support.TESTFN)
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200594 self._test_all_chown_common(posix.chown, support.TESTFN,
595 getattr(posix, 'stat', None))
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000596
597 @unittest.skipUnless(hasattr(posix, 'fchown'), "test needs os.fchown()")
598 def test_fchown(self):
599 os.unlink(support.TESTFN)
600
601 # re-create the file
602 test_file = open(support.TESTFN, 'w')
603 try:
604 fd = test_file.fileno()
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200605 self._test_all_chown_common(posix.fchown, fd,
606 getattr(posix, 'fstat', None))
Benjamin Peterson1baf4652009-12-31 03:11:23 +0000607 finally:
608 test_file.close()
609
610 @unittest.skipUnless(hasattr(posix, 'lchown'), "test needs os.lchown()")
611 def test_lchown(self):
612 os.unlink(support.TESTFN)
613 # create a symlink
Ned Deily3eb67d52011-06-28 00:00:28 -0700614 os.symlink(_DUMMY_SYMLINK, support.TESTFN)
Serhiy Storchaka7cf55992013-02-10 21:56:49 +0200615 self._test_all_chown_common(posix.lchown, support.TESTFN,
616 getattr(posix, 'lstat', None))
Christian Heimesd5e2b6f2008-03-19 21:50:51 +0000617
Serhiy Storchaka43767632013-11-03 21:31:38 +0200618 @unittest.skipUnless(hasattr(posix, 'chdir'), 'test needs posix.chdir()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000619 def test_chdir(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200620 posix.chdir(os.curdir)
621 self.assertRaises(OSError, posix.chdir, support.TESTFN)
Neal Norwitze241ce82003-02-17 18:17:05 +0000622
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +0000623 def test_listdir(self):
Larry Hastingsfdaea062012-06-25 04:42:23 -0700624 self.assertTrue(support.TESTFN in posix.listdir(os.curdir))
Martin v. Löwisc9e1c7d2010-07-23 12:16:41 +0000625
626 def test_listdir_default(self):
Larry Hastingsfdaea062012-06-25 04:42:23 -0700627 # When listdir is called without argument,
628 # it's the same as listdir(os.curdir).
629 self.assertTrue(support.TESTFN in posix.listdir())
Neal Norwitze241ce82003-02-17 18:17:05 +0000630
Larry Hastingsfdaea062012-06-25 04:42:23 -0700631 def test_listdir_bytes(self):
632 # When listdir is called with a bytes object,
633 # the returned strings are of type bytes.
634 self.assertTrue(os.fsencode(support.TESTFN) in posix.listdir(b'.'))
635
636 @unittest.skipUnless(posix.listdir in os.supports_fd,
637 "test needs fd support for posix.listdir()")
638 def test_listdir_fd(self):
Antoine Pitrou8250e232011-02-25 23:41:16 +0000639 f = posix.open(posix.getcwd(), posix.O_RDONLY)
Charles-François Natali7546ad32012-01-08 18:34:06 +0100640 self.addCleanup(posix.close, f)
Antoine Pitrou8250e232011-02-25 23:41:16 +0000641 self.assertEqual(
642 sorted(posix.listdir('.')),
Larry Hastings9cf065c2012-06-22 16:30:09 -0700643 sorted(posix.listdir(f))
Antoine Pitrou8250e232011-02-25 23:41:16 +0000644 )
Charles-François Natali7546ad32012-01-08 18:34:06 +0100645 # Check that the fd offset was reset (issue #13739)
Charles-François Natali7546ad32012-01-08 18:34:06 +0100646 self.assertEqual(
647 sorted(posix.listdir('.')),
Larry Hastings9cf065c2012-06-22 16:30:09 -0700648 sorted(posix.listdir(f))
Charles-François Natali7546ad32012-01-08 18:34:06 +0100649 )
Antoine Pitrou8250e232011-02-25 23:41:16 +0000650
Serhiy Storchaka43767632013-11-03 21:31:38 +0200651 @unittest.skipUnless(hasattr(posix, 'access'), 'test needs posix.access()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000652 def test_access(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200653 self.assertTrue(posix.access(support.TESTFN, os.R_OK))
Neal Norwitze241ce82003-02-17 18:17:05 +0000654
Serhiy Storchaka43767632013-11-03 21:31:38 +0200655 @unittest.skipUnless(hasattr(posix, 'umask'), 'test needs posix.umask()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000656 def test_umask(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200657 old_mask = posix.umask(0)
658 self.assertIsInstance(old_mask, int)
659 posix.umask(old_mask)
Neal Norwitze241ce82003-02-17 18:17:05 +0000660
Serhiy Storchaka43767632013-11-03 21:31:38 +0200661 @unittest.skipUnless(hasattr(posix, 'strerror'),
662 'test needs posix.strerror()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000663 def test_strerror(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200664 self.assertTrue(posix.strerror(0))
Neal Norwitze241ce82003-02-17 18:17:05 +0000665
Serhiy Storchaka43767632013-11-03 21:31:38 +0200666 @unittest.skipUnless(hasattr(posix, 'pipe'), 'test needs posix.pipe()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000667 def test_pipe(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200668 reader, writer = posix.pipe()
669 os.close(reader)
670 os.close(writer)
Neal Norwitze241ce82003-02-17 18:17:05 +0000671
Charles-François Natalidaafdd52011-05-29 20:07:40 +0200672 @unittest.skipUnless(hasattr(os, 'pipe2'), "test needs os.pipe2()")
Charles-François Natali239bb962011-06-03 12:55:15 +0200673 @support.requires_linux_version(2, 6, 27)
Charles-François Natalidaafdd52011-05-29 20:07:40 +0200674 def test_pipe2(self):
675 self.assertRaises(TypeError, os.pipe2, 'DEADBEEF')
676 self.assertRaises(TypeError, os.pipe2, 0, 0)
677
Charles-François Natali368f34b2011-06-06 19:49:47 +0200678 # try calling with flags = 0, like os.pipe()
679 r, w = os.pipe2(0)
Charles-François Natalidaafdd52011-05-29 20:07:40 +0200680 os.close(r)
681 os.close(w)
682
683 # test flags
684 r, w = os.pipe2(os.O_CLOEXEC|os.O_NONBLOCK)
685 self.addCleanup(os.close, r)
686 self.addCleanup(os.close, w)
Victor Stinnerbff989e2013-08-28 12:25:40 +0200687 self.assertFalse(os.get_inheritable(r))
688 self.assertFalse(os.get_inheritable(w))
Victor Stinner1db9e7b2014-07-29 22:32:47 +0200689 self.assertFalse(os.get_blocking(r))
690 self.assertFalse(os.get_blocking(w))
Charles-François Natalidaafdd52011-05-29 20:07:40 +0200691 # try reading from an empty pipe: this should fail, not block
692 self.assertRaises(OSError, os.read, r, 1)
693 # try a write big enough to fill-up the pipe: this should either
694 # fail or perform a partial write, not block
695 try:
696 os.write(w, b'x' * support.PIPE_MAX_SIZE)
697 except OSError:
698 pass
699
Serhiy Storchaka5cfc79d2014-02-07 10:06:39 +0200700 @support.cpython_only
701 @unittest.skipUnless(hasattr(os, 'pipe2'), "test needs os.pipe2()")
702 @support.requires_linux_version(2, 6, 27)
703 def test_pipe2_c_limits(self):
Serhiy Storchaka78980432013-01-15 01:12:17 +0200704 # Issue 15989
Serhiy Storchaka5cfc79d2014-02-07 10:06:39 +0200705 import _testcapi
Serhiy Storchaka78980432013-01-15 01:12:17 +0200706 self.assertRaises(OverflowError, os.pipe2, _testcapi.INT_MAX + 1)
707 self.assertRaises(OverflowError, os.pipe2, _testcapi.UINT_MAX + 1)
708
Serhiy Storchaka43767632013-11-03 21:31:38 +0200709 @unittest.skipUnless(hasattr(posix, 'utime'), 'test needs posix.utime()')
Neal Norwitze241ce82003-02-17 18:17:05 +0000710 def test_utime(self):
Serhiy Storchaka43767632013-11-03 21:31:38 +0200711 now = time.time()
712 posix.utime(support.TESTFN, None)
713 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, None))
714 self.assertRaises(TypeError, posix.utime, support.TESTFN, (now, None))
715 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, now))
716 posix.utime(support.TESTFN, (int(now), int(now)))
717 posix.utime(support.TESTFN, (now, now))
Neal Norwitze241ce82003-02-17 18:17:05 +0000718
Larry Hastings9cf065c2012-06-22 16:30:09 -0700719 def _test_chflags_regular_file(self, chflags_func, target_file, **kwargs):
Ned Deily3eb67d52011-06-28 00:00:28 -0700720 st = os.stat(target_file)
721 self.assertTrue(hasattr(st, 'st_flags'))
Trent Nelson75959cf2012-08-21 23:59:31 +0000722
723 # ZFS returns EOPNOTSUPP when attempting to set flag UF_IMMUTABLE.
724 flags = st.st_flags | stat.UF_IMMUTABLE
725 try:
726 chflags_func(target_file, flags, **kwargs)
727 except OSError as err:
728 if err.errno != errno.EOPNOTSUPP:
729 raise
730 msg = 'chflag UF_IMMUTABLE not supported by underlying fs'
731 self.skipTest(msg)
732
Ned Deily3eb67d52011-06-28 00:00:28 -0700733 try:
734 new_st = os.stat(target_file)
735 self.assertEqual(st.st_flags | stat.UF_IMMUTABLE, new_st.st_flags)
736 try:
737 fd = open(target_file, 'w+')
Andrew Svetlovf7a17b42012-12-25 16:47:37 +0200738 except OSError as e:
Ned Deily3eb67d52011-06-28 00:00:28 -0700739 self.assertEqual(e.errno, errno.EPERM)
740 finally:
741 posix.chflags(target_file, st.st_flags)
Thomas Wouterscf297e42007-02-23 15:07:44 +0000742
Ned Deily3eb67d52011-06-28 00:00:28 -0700743 @unittest.skipUnless(hasattr(posix, 'chflags'), 'test needs os.chflags()')
744 def test_chflags(self):
745 self._test_chflags_regular_file(posix.chflags, support.TESTFN)
746
747 @unittest.skipUnless(hasattr(posix, 'lchflags'), 'test needs os.lchflags()')
748 def test_lchflags_regular_file(self):
749 self._test_chflags_regular_file(posix.lchflags, support.TESTFN)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700750 self._test_chflags_regular_file(posix.chflags, support.TESTFN, follow_symlinks=False)
Ned Deily3eb67d52011-06-28 00:00:28 -0700751
752 @unittest.skipUnless(hasattr(posix, 'lchflags'), 'test needs os.lchflags()')
753 def test_lchflags_symlink(self):
754 testfn_st = os.stat(support.TESTFN)
755
756 self.assertTrue(hasattr(testfn_st, 'st_flags'))
757
758 os.symlink(support.TESTFN, _DUMMY_SYMLINK)
759 self.teardown_files.append(_DUMMY_SYMLINK)
760 dummy_symlink_st = os.lstat(_DUMMY_SYMLINK)
761
Larry Hastings9cf065c2012-06-22 16:30:09 -0700762 def chflags_nofollow(path, flags):
763 return posix.chflags(path, flags, follow_symlinks=False)
Ned Deily3eb67d52011-06-28 00:00:28 -0700764
Larry Hastings9cf065c2012-06-22 16:30:09 -0700765 for fn in (posix.lchflags, chflags_nofollow):
Trent Nelson75959cf2012-08-21 23:59:31 +0000766 # ZFS returns EOPNOTSUPP when attempting to set flag UF_IMMUTABLE.
767 flags = dummy_symlink_st.st_flags | stat.UF_IMMUTABLE
768 try:
769 fn(_DUMMY_SYMLINK, flags)
770 except OSError as err:
771 if err.errno != errno.EOPNOTSUPP:
772 raise
773 msg = 'chflag UF_IMMUTABLE not supported by underlying fs'
774 self.skipTest(msg)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700775 try:
776 new_testfn_st = os.stat(support.TESTFN)
777 new_dummy_symlink_st = os.lstat(_DUMMY_SYMLINK)
778
779 self.assertEqual(testfn_st.st_flags, new_testfn_st.st_flags)
780 self.assertEqual(dummy_symlink_st.st_flags | stat.UF_IMMUTABLE,
781 new_dummy_symlink_st.st_flags)
782 finally:
783 fn(_DUMMY_SYMLINK, dummy_symlink_st.st_flags)
Thomas Wouterscf297e42007-02-23 15:07:44 +0000784
Guido van Rossum98297ee2007-11-06 21:34:58 +0000785 def test_environ(self):
Victor Stinner17b490d2010-05-06 22:19:30 +0000786 if os.name == "nt":
787 item_type = str
788 else:
789 item_type = bytes
Guido van Rossum98297ee2007-11-06 21:34:58 +0000790 for k, v in posix.environ.items():
Victor Stinner17b490d2010-05-06 22:19:30 +0000791 self.assertEqual(type(k), item_type)
792 self.assertEqual(type(v), item_type)
Guido van Rossum98297ee2007-11-06 21:34:58 +0000793
Serhiy Storchaka43767632013-11-03 21:31:38 +0200794 @unittest.skipUnless(hasattr(posix, 'getcwd'), 'test needs posix.getcwd()')
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000795 def test_getcwd_long_pathnames(self):
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500796 dirname = 'getcwd-test-directory-0123456789abcdef-01234567890abcdef'
797 curdir = os.getcwd()
798 base_path = os.path.abspath(support.TESTFN) + '.getcwd'
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000799
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500800 try:
801 os.mkdir(base_path)
802 os.chdir(base_path)
803 except:
804 # Just returning nothing instead of the SkipTest exception, because
805 # the test results in Error in that case. Is that ok?
806 # raise unittest.SkipTest("cannot create directory for testing")
807 return
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000808
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500809 def _create_and_do_getcwd(dirname, current_path_length = 0):
810 try:
811 os.mkdir(dirname)
812 except:
813 raise unittest.SkipTest("mkdir cannot create directory sufficiently deep for getcwd test")
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000814
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500815 os.chdir(dirname)
816 try:
817 os.getcwd()
818 if current_path_length < 1027:
819 _create_and_do_getcwd(dirname, current_path_length + len(dirname) + 1)
820 finally:
821 os.chdir('..')
822 os.rmdir(dirname)
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000823
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500824 _create_and_do_getcwd(dirname)
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000825
Benjamin Peterson3a7dffa2013-08-23 21:01:48 -0500826 finally:
827 os.chdir(curdir)
828 support.rmtree(base_path)
Benjamin Petersondcf97b92008-07-02 17:30:14 +0000829
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +0200830 @unittest.skipUnless(hasattr(posix, 'getgrouplist'), "test needs posix.getgrouplist()")
831 @unittest.skipUnless(hasattr(pwd, 'getpwuid'), "test needs pwd.getpwuid()")
832 @unittest.skipUnless(hasattr(os, 'getuid'), "test needs os.getuid()")
833 def test_getgrouplist(self):
Ross Lagerwalla0b315f2012-12-13 15:20:26 +0000834 user = pwd.getpwuid(os.getuid())[0]
835 group = pwd.getpwuid(os.getuid())[3]
836 self.assertIn(group, posix.getgrouplist(user, group))
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +0200837
Ross Lagerwallb0ae53d2011-06-10 07:30:30 +0200838
Antoine Pitrou318b8f32011-01-12 18:45:27 +0000839 @unittest.skipUnless(hasattr(os, 'getegid'), "test needs os.getegid()")
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +0000840 def test_getgroups(self):
Jesus Cea61f32cb2014-06-28 18:39:35 +0200841 with os.popen('id -G 2>/dev/null') as idg:
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +0000842 groups = idg.read().strip()
Charles-François Natalie8a255a2012-05-02 20:01:38 +0200843 ret = idg.close()
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +0000844
Xavier de Gaye24c3b492016-10-19 11:00:26 +0200845 try:
846 idg_groups = set(int(g) for g in groups.split())
847 except ValueError:
848 idg_groups = set()
849 if ret is not None or not idg_groups:
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +0000850 raise unittest.SkipTest("need working 'id -G'")
851
Ned Deily028915e2013-02-02 15:08:52 -0800852 # Issues 16698: OS X ABIs prior to 10.6 have limits on getgroups()
853 if sys.platform == 'darwin':
854 import sysconfig
855 dt = sysconfig.get_config_var('MACOSX_DEPLOYMENT_TARGET') or '10.0'
Ned Deily04cdfa12014-06-25 13:36:14 -0700856 if tuple(int(n) for n in dt.split('.')[0:2]) < (10, 6):
Ned Deily028915e2013-02-02 15:08:52 -0800857 raise unittest.SkipTest("getgroups(2) is broken prior to 10.6")
858
Ronald Oussoren7fb6f512010-08-01 19:18:13 +0000859 # 'id -G' and 'os.getgroups()' should return the same
Xavier de Gaye24c3b492016-10-19 11:00:26 +0200860 # groups, ignoring order, duplicates, and the effective gid.
861 # #10822/#26944 - It is implementation defined whether
862 # posix.getgroups() includes the effective gid.
863 symdiff = idg_groups.symmetric_difference(posix.getgroups())
864 self.assertTrue(not symdiff or symdiff == {posix.getegid()})
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +0000865
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000866 # tests for the posix *at functions follow
867
Larry Hastings9cf065c2012-06-22 16:30:09 -0700868 @unittest.skipUnless(os.access in os.supports_dir_fd, "test needs dir_fd support for os.access()")
869 def test_access_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000870 f = posix.open(posix.getcwd(), posix.O_RDONLY)
871 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700872 self.assertTrue(posix.access(support.TESTFN, os.R_OK, dir_fd=f))
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000873 finally:
874 posix.close(f)
875
Larry Hastings9cf065c2012-06-22 16:30:09 -0700876 @unittest.skipUnless(os.chmod in os.supports_dir_fd, "test needs dir_fd support in os.chmod()")
877 def test_chmod_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000878 os.chmod(support.TESTFN, stat.S_IRUSR)
879
880 f = posix.open(posix.getcwd(), posix.O_RDONLY)
881 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700882 posix.chmod(support.TESTFN, stat.S_IRUSR | stat.S_IWUSR, dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000883
884 s = posix.stat(support.TESTFN)
885 self.assertEqual(s[0] & stat.S_IRWXU, stat.S_IRUSR | stat.S_IWUSR)
886 finally:
887 posix.close(f)
888
Larry Hastings9cf065c2012-06-22 16:30:09 -0700889 @unittest.skipUnless(os.chown in os.supports_dir_fd, "test needs dir_fd support in os.chown()")
890 def test_chown_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000891 support.unlink(support.TESTFN)
Victor Stinnerbf816222011-06-30 23:25:47 +0200892 support.create_empty_file(support.TESTFN)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000893
894 f = posix.open(posix.getcwd(), posix.O_RDONLY)
895 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700896 posix.chown(support.TESTFN, os.getuid(), os.getgid(), dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000897 finally:
898 posix.close(f)
899
Larry Hastings9cf065c2012-06-22 16:30:09 -0700900 @unittest.skipUnless(os.stat in os.supports_dir_fd, "test needs dir_fd support in os.stat()")
901 def test_stat_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000902 support.unlink(support.TESTFN)
903 with open(support.TESTFN, 'w') as outfile:
904 outfile.write("testline\n")
905
906 f = posix.open(posix.getcwd(), posix.O_RDONLY)
907 try:
908 s1 = posix.stat(support.TESTFN)
Larry Hastings9cf065c2012-06-22 16:30:09 -0700909 s2 = posix.stat(support.TESTFN, dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000910 self.assertEqual(s1, s2)
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200911 s2 = posix.stat(support.TESTFN, dir_fd=None)
912 self.assertEqual(s1, s2)
Serhiy Storchaka7155b882016-04-08 08:48:20 +0300913 self.assertRaisesRegex(TypeError, 'should be integer or None, not',
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200914 posix.stat, support.TESTFN, dir_fd=posix.getcwd())
Serhiy Storchaka7155b882016-04-08 08:48:20 +0300915 self.assertRaisesRegex(TypeError, 'should be integer or None, not',
Serhiy Storchakaa2ad5c32013-01-07 23:13:46 +0200916 posix.stat, support.TESTFN, dir_fd=float(f))
917 self.assertRaises(OverflowError,
918 posix.stat, support.TESTFN, dir_fd=10**20)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000919 finally:
920 posix.close(f)
921
Larry Hastings9cf065c2012-06-22 16:30:09 -0700922 @unittest.skipUnless(os.utime in os.supports_dir_fd, "test needs dir_fd support in os.utime()")
923 def test_utime_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000924 f = posix.open(posix.getcwd(), posix.O_RDONLY)
925 try:
926 now = time.time()
Larry Hastings9cf065c2012-06-22 16:30:09 -0700927 posix.utime(support.TESTFN, None, dir_fd=f)
928 posix.utime(support.TESTFN, dir_fd=f)
929 self.assertRaises(TypeError, posix.utime, support.TESTFN, now, dir_fd=f)
930 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, None), dir_fd=f)
931 self.assertRaises(TypeError, posix.utime, support.TESTFN, (now, None), dir_fd=f)
932 self.assertRaises(TypeError, posix.utime, support.TESTFN, (None, now), dir_fd=f)
933 self.assertRaises(TypeError, posix.utime, support.TESTFN, (now, "x"), dir_fd=f)
934 posix.utime(support.TESTFN, (int(now), int(now)), dir_fd=f)
935 posix.utime(support.TESTFN, (now, now), dir_fd=f)
936 posix.utime(support.TESTFN,
937 (int(now), int((now - int(now)) * 1e9)), dir_fd=f)
938 posix.utime(support.TESTFN, dir_fd=f,
939 times=(int(now), int((now - int(now)) * 1e9)))
940
Larry Hastings90867a52012-06-22 17:01:41 -0700941 # try dir_fd and follow_symlinks together
Larry Hastings9cf065c2012-06-22 16:30:09 -0700942 if os.utime in os.supports_follow_symlinks:
Larry Hastings90867a52012-06-22 17:01:41 -0700943 try:
944 posix.utime(support.TESTFN, follow_symlinks=False, dir_fd=f)
Georg Brandl969288e2012-06-26 09:25:44 +0200945 except ValueError:
Larry Hastings90867a52012-06-22 17:01:41 -0700946 # whoops! using both together not supported on this platform.
947 pass
Larry Hastings9cf065c2012-06-22 16:30:09 -0700948
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000949 finally:
950 posix.close(f)
951
Larry Hastings9cf065c2012-06-22 16:30:09 -0700952 @unittest.skipUnless(os.link in os.supports_dir_fd, "test needs dir_fd support in os.link()")
Xavier de Gaye3a4e9892016-12-13 10:00:01 +0100953 @unittest.skipIf(android_not_root, "hard link not allowed, non root user")
Larry Hastings9cf065c2012-06-22 16:30:09 -0700954 def test_link_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000955 f = posix.open(posix.getcwd(), posix.O_RDONLY)
956 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700957 posix.link(support.TESTFN, support.TESTFN + 'link', src_dir_fd=f, dst_dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000958 # should have same inodes
959 self.assertEqual(posix.stat(support.TESTFN)[1],
960 posix.stat(support.TESTFN + 'link')[1])
961 finally:
962 posix.close(f)
963 support.unlink(support.TESTFN + 'link')
964
Larry Hastings9cf065c2012-06-22 16:30:09 -0700965 @unittest.skipUnless(os.mkdir in os.supports_dir_fd, "test needs dir_fd support in os.mkdir()")
966 def test_mkdir_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000967 f = posix.open(posix.getcwd(), posix.O_RDONLY)
968 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700969 posix.mkdir(support.TESTFN + 'dir', dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000970 posix.stat(support.TESTFN + 'dir') # should not raise exception
971 finally:
972 posix.close(f)
973 support.rmtree(support.TESTFN + 'dir')
974
Larry Hastings9cf065c2012-06-22 16:30:09 -0700975 @unittest.skipUnless((os.mknod in os.supports_dir_fd) and hasattr(stat, 'S_IFIFO'),
976 "test requires both stat.S_IFIFO and dir_fd support for os.mknod()")
Xavier de Gaye3a4e9892016-12-13 10:00:01 +0100977 @unittest.skipIf(android_not_root, "mknod not allowed, non root user")
Larry Hastings9cf065c2012-06-22 16:30:09 -0700978 def test_mknod_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000979 # Test using mknodat() to create a FIFO (the only use specified
980 # by POSIX).
981 support.unlink(support.TESTFN)
982 mode = stat.S_IFIFO | stat.S_IRUSR | stat.S_IWUSR
983 f = posix.open(posix.getcwd(), posix.O_RDONLY)
984 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -0700985 posix.mknod(support.TESTFN, mode, 0, dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000986 except OSError as e:
987 # Some old systems don't allow unprivileged users to use
988 # mknod(), or only support creating device nodes.
989 self.assertIn(e.errno, (errno.EPERM, errno.EINVAL))
990 else:
991 self.assertTrue(stat.S_ISFIFO(posix.stat(support.TESTFN).st_mode))
992 finally:
993 posix.close(f)
994
Larry Hastings9cf065c2012-06-22 16:30:09 -0700995 @unittest.skipUnless(os.open in os.supports_dir_fd, "test needs dir_fd support in os.open()")
996 def test_open_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +0000997 support.unlink(support.TESTFN)
998 with open(support.TESTFN, 'w') as outfile:
999 outfile.write("testline\n")
1000 a = posix.open(posix.getcwd(), posix.O_RDONLY)
Larry Hastings9cf065c2012-06-22 16:30:09 -07001001 b = posix.open(support.TESTFN, posix.O_RDONLY, dir_fd=a)
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001002 try:
1003 res = posix.read(b, 9).decode(encoding="utf-8")
1004 self.assertEqual("testline\n", res)
1005 finally:
1006 posix.close(a)
1007 posix.close(b)
1008
Larry Hastings9cf065c2012-06-22 16:30:09 -07001009 @unittest.skipUnless(os.readlink in os.supports_dir_fd, "test needs dir_fd support in os.readlink()")
1010 def test_readlink_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001011 os.symlink(support.TESTFN, support.TESTFN + 'link')
1012 f = posix.open(posix.getcwd(), posix.O_RDONLY)
1013 try:
1014 self.assertEqual(posix.readlink(support.TESTFN + 'link'),
Larry Hastings9cf065c2012-06-22 16:30:09 -07001015 posix.readlink(support.TESTFN + 'link', dir_fd=f))
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001016 finally:
1017 support.unlink(support.TESTFN + 'link')
1018 posix.close(f)
1019
Larry Hastings9cf065c2012-06-22 16:30:09 -07001020 @unittest.skipUnless(os.rename in os.supports_dir_fd, "test needs dir_fd support in os.rename()")
1021 def test_rename_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001022 support.unlink(support.TESTFN)
Victor Stinnerbf816222011-06-30 23:25:47 +02001023 support.create_empty_file(support.TESTFN + 'ren')
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001024 f = posix.open(posix.getcwd(), posix.O_RDONLY)
1025 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -07001026 posix.rename(support.TESTFN + 'ren', support.TESTFN, src_dir_fd=f, dst_dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001027 except:
1028 posix.rename(support.TESTFN + 'ren', support.TESTFN)
1029 raise
1030 else:
Andrew Svetlov5b898402012-12-18 21:26:36 +02001031 posix.stat(support.TESTFN) # should not raise exception
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001032 finally:
1033 posix.close(f)
1034
Larry Hastings9cf065c2012-06-22 16:30:09 -07001035 @unittest.skipUnless(os.symlink in os.supports_dir_fd, "test needs dir_fd support in os.symlink()")
1036 def test_symlink_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001037 f = posix.open(posix.getcwd(), posix.O_RDONLY)
1038 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -07001039 posix.symlink(support.TESTFN, support.TESTFN + 'link', dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001040 self.assertEqual(posix.readlink(support.TESTFN + 'link'), support.TESTFN)
1041 finally:
1042 posix.close(f)
1043 support.unlink(support.TESTFN + 'link')
1044
Larry Hastings9cf065c2012-06-22 16:30:09 -07001045 @unittest.skipUnless(os.unlink in os.supports_dir_fd, "test needs dir_fd support in os.unlink()")
1046 def test_unlink_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001047 f = posix.open(posix.getcwd(), posix.O_RDONLY)
Victor Stinnerbf816222011-06-30 23:25:47 +02001048 support.create_empty_file(support.TESTFN + 'del')
Andrew Svetlov5b898402012-12-18 21:26:36 +02001049 posix.stat(support.TESTFN + 'del') # should not raise exception
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001050 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -07001051 posix.unlink(support.TESTFN + 'del', dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001052 except:
1053 support.unlink(support.TESTFN + 'del')
1054 raise
1055 else:
1056 self.assertRaises(OSError, posix.stat, support.TESTFN + 'link')
1057 finally:
1058 posix.close(f)
1059
Larry Hastings9cf065c2012-06-22 16:30:09 -07001060 @unittest.skipUnless(os.mkfifo in os.supports_dir_fd, "test needs dir_fd support in os.mkfifo()")
Xavier de Gaye3a4e9892016-12-13 10:00:01 +01001061 @unittest.skipIf(android_not_root, "mkfifo not allowed, non root user")
Larry Hastings9cf065c2012-06-22 16:30:09 -07001062 def test_mkfifo_dir_fd(self):
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001063 support.unlink(support.TESTFN)
1064 f = posix.open(posix.getcwd(), posix.O_RDONLY)
1065 try:
Larry Hastings9cf065c2012-06-22 16:30:09 -07001066 posix.mkfifo(support.TESTFN, stat.S_IRUSR | stat.S_IWUSR, dir_fd=f)
Antoine Pitrouf65132d2011-02-25 23:25:17 +00001067 self.assertTrue(stat.S_ISFIFO(posix.stat(support.TESTFN).st_mode))
1068 finally:
1069 posix.close(f)
1070
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001071 requires_sched_h = unittest.skipUnless(hasattr(posix, 'sched_yield'),
1072 "don't have scheduling support")
Antoine Pitrou84869872012-08-04 16:16:35 +02001073 requires_sched_affinity = unittest.skipUnless(hasattr(posix, 'sched_setaffinity'),
Benjamin Peterson50ba2712011-08-02 22:15:40 -05001074 "don't have sched affinity support")
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001075
1076 @requires_sched_h
1077 def test_sched_yield(self):
1078 # This has no error conditions (at least on Linux).
1079 posix.sched_yield()
1080
1081 @requires_sched_h
Charles-François Nataliea0d5fc2011-09-06 19:03:35 +02001082 @unittest.skipUnless(hasattr(posix, 'sched_get_priority_max'),
1083 "requires sched_get_priority_max()")
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001084 def test_sched_priority(self):
1085 # Round-robin usually has interesting priorities.
1086 pol = posix.SCHED_RR
1087 lo = posix.sched_get_priority_min(pol)
1088 hi = posix.sched_get_priority_max(pol)
1089 self.assertIsInstance(lo, int)
1090 self.assertIsInstance(hi, int)
1091 self.assertGreaterEqual(hi, lo)
Benjamin Peterson539b6c42011-08-02 22:09:37 -05001092 # OSX evidently just returns 15 without checking the argument.
1093 if sys.platform != "darwin":
Benjamin Petersonc1581582011-08-02 22:10:55 -05001094 self.assertRaises(OSError, posix.sched_get_priority_min, -23)
1095 self.assertRaises(OSError, posix.sched_get_priority_max, -23)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001096
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05001097 @unittest.skipUnless(hasattr(posix, 'sched_setscheduler'), "can't change scheduler")
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001098 def test_get_and_set_scheduler_and_param(self):
1099 possible_schedulers = [sched for name, sched in posix.__dict__.items()
1100 if name.startswith("SCHED_")]
1101 mine = posix.sched_getscheduler(0)
1102 self.assertIn(mine, possible_schedulers)
1103 try:
Jesus Ceaceb5d162011-09-10 01:16:55 +02001104 parent = posix.sched_getscheduler(os.getppid())
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001105 except OSError as e:
Jesus Ceaceb5d162011-09-10 01:16:55 +02001106 if e.errno != errno.EPERM:
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001107 raise
1108 else:
Jesus Ceaceb5d162011-09-10 01:16:55 +02001109 self.assertIn(parent, possible_schedulers)
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001110 self.assertRaises(OSError, posix.sched_getscheduler, -1)
1111 self.assertRaises(OSError, posix.sched_getparam, -1)
1112 param = posix.sched_getparam(0)
1113 self.assertIsInstance(param.sched_priority, int)
Charles-François Natali7b911cb2011-08-21 12:41:43 +02001114
Charles-François Natalib402a5c2013-01-13 14:13:25 +01001115 # POSIX states that calling sched_setparam() or sched_setscheduler() on
1116 # a process with a scheduling policy other than SCHED_FIFO or SCHED_RR
1117 # is implementation-defined: NetBSD and FreeBSD can return EINVAL.
1118 if not sys.platform.startswith(('freebsd', 'netbsd')):
1119 try:
1120 posix.sched_setscheduler(0, mine, param)
1121 posix.sched_setparam(0, param)
1122 except OSError as e:
1123 if e.errno != errno.EPERM:
1124 raise
Charles-François Natali7b911cb2011-08-21 12:41:43 +02001125 self.assertRaises(OSError, posix.sched_setparam, -1, param)
1126
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001127 self.assertRaises(OSError, posix.sched_setscheduler, -1, mine, param)
1128 self.assertRaises(TypeError, posix.sched_setscheduler, 0, mine, None)
1129 self.assertRaises(TypeError, posix.sched_setparam, 0, 43)
1130 param = posix.sched_param(None)
1131 self.assertRaises(TypeError, posix.sched_setparam, 0, param)
1132 large = 214748364700
1133 param = posix.sched_param(large)
1134 self.assertRaises(OverflowError, posix.sched_setparam, 0, param)
1135 param = posix.sched_param(sched_priority=-large)
1136 self.assertRaises(OverflowError, posix.sched_setparam, 0, param)
1137
Benjamin Petersonc5fce4d2011-08-02 18:07:32 -05001138 @unittest.skipUnless(hasattr(posix, "sched_rr_get_interval"), "no function")
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001139 def test_sched_rr_get_interval(self):
Benjamin Peterson43234ab2011-08-02 22:19:14 -05001140 try:
1141 interval = posix.sched_rr_get_interval(0)
1142 except OSError as e:
1143 # This likely means that sched_rr_get_interval is only valid for
1144 # processes with the SCHED_RR scheduler in effect.
1145 if e.errno != errno.EINVAL:
1146 raise
1147 self.skipTest("only works on SCHED_RR processes")
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001148 self.assertIsInstance(interval, float)
1149 # Reasonable constraints, I think.
1150 self.assertGreaterEqual(interval, 0.)
1151 self.assertLess(interval, 1.)
1152
Benjamin Peterson2740af82011-08-02 17:41:34 -05001153 @requires_sched_affinity
Antoine Pitrou84869872012-08-04 16:16:35 +02001154 def test_sched_getaffinity(self):
1155 mask = posix.sched_getaffinity(0)
1156 self.assertIsInstance(mask, set)
1157 self.assertGreaterEqual(len(mask), 1)
1158 self.assertRaises(OSError, posix.sched_getaffinity, -1)
1159 for cpu in mask:
1160 self.assertIsInstance(cpu, int)
1161 self.assertGreaterEqual(cpu, 0)
1162 self.assertLess(cpu, 1 << 32)
1163
1164 @requires_sched_affinity
1165 def test_sched_setaffinity(self):
1166 mask = posix.sched_getaffinity(0)
1167 if len(mask) > 1:
1168 # Empty masks are forbidden
1169 mask.pop()
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001170 posix.sched_setaffinity(0, mask)
Antoine Pitrou84869872012-08-04 16:16:35 +02001171 self.assertEqual(posix.sched_getaffinity(0), mask)
1172 self.assertRaises(OSError, posix.sched_setaffinity, 0, [])
1173 self.assertRaises(ValueError, posix.sched_setaffinity, 0, [-10])
1174 self.assertRaises(OverflowError, posix.sched_setaffinity, 0, [1<<128])
Benjamin Peterson94b580d2011-08-02 17:30:04 -05001175 self.assertRaises(OSError, posix.sched_setaffinity, -1, mask)
1176
Victor Stinner8b905bd2011-10-25 13:34:04 +02001177 def test_rtld_constants(self):
1178 # check presence of major RTLD_* constants
1179 posix.RTLD_LAZY
1180 posix.RTLD_NOW
1181 posix.RTLD_GLOBAL
1182 posix.RTLD_LOCAL
1183
Jesus Cea60c13dd2012-06-23 02:58:14 +02001184 @unittest.skipUnless(hasattr(os, 'SEEK_HOLE'),
1185 "test needs an OS that reports file holes")
Hynek Schlawackf841e422012-06-24 09:51:46 +02001186 def test_fs_holes(self):
Jesus Cea94363612012-06-22 18:32:07 +02001187 # Even if the filesystem doesn't report holes,
1188 # if the OS supports it the SEEK_* constants
1189 # will be defined and will have a consistent
1190 # behaviour:
1191 # os.SEEK_DATA = current position
1192 # os.SEEK_HOLE = end of file position
Hynek Schlawackf841e422012-06-24 09:51:46 +02001193 with open(support.TESTFN, 'r+b') as fp:
Jesus Cea94363612012-06-22 18:32:07 +02001194 fp.write(b"hello")
1195 fp.flush()
1196 size = fp.tell()
1197 fno = fp.fileno()
Jesus Cead46f7d22012-07-07 14:56:04 +02001198 try :
1199 for i in range(size):
1200 self.assertEqual(i, os.lseek(fno, i, os.SEEK_DATA))
1201 self.assertLessEqual(size, os.lseek(fno, i, os.SEEK_HOLE))
1202 self.assertRaises(OSError, os.lseek, fno, size, os.SEEK_DATA)
1203 self.assertRaises(OSError, os.lseek, fno, size, os.SEEK_HOLE)
1204 except OSError :
1205 # Some OSs claim to support SEEK_HOLE/SEEK_DATA
1206 # but it is not true.
1207 # For instance:
1208 # http://lists.freebsd.org/pipermail/freebsd-amd64/2012-January/014332.html
1209 raise unittest.SkipTest("OSError raised!")
Jesus Cea94363612012-06-22 18:32:07 +02001210
Larry Hastingsb0827312014-02-09 22:05:19 -08001211 def test_path_error2(self):
1212 """
1213 Test functions that call path_error2(), providing two filenames in their exceptions.
1214 """
Victor Stinner047b7ae2014-10-05 17:37:41 +02001215 for name in ("rename", "replace", "link"):
Larry Hastingsb0827312014-02-09 22:05:19 -08001216 function = getattr(os, name, None)
Victor Stinnerbed04a72014-10-05 17:37:59 +02001217 if function is None:
1218 continue
Larry Hastingsb0827312014-02-09 22:05:19 -08001219
Victor Stinnerbed04a72014-10-05 17:37:59 +02001220 for dst in ("noodly2", support.TESTFN):
1221 try:
1222 function('doesnotexistfilename', dst)
1223 except OSError as e:
1224 self.assertIn("'doesnotexistfilename' -> '{}'".format(dst), str(e))
1225 break
1226 else:
1227 self.fail("No valid path_error2() test for os." + name)
Larry Hastingsb0827312014-02-09 22:05:19 -08001228
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +03001229 def test_path_with_null_character(self):
1230 fn = support.TESTFN
1231 fn_with_NUL = fn + '\0'
1232 self.addCleanup(support.unlink, fn)
1233 support.unlink(fn)
1234 fd = None
1235 try:
Serhiy Storchaka7e9d1d12015-04-20 10:12:28 +03001236 with self.assertRaises(ValueError):
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +03001237 fd = os.open(fn_with_NUL, os.O_WRONLY | os.O_CREAT) # raises
1238 finally:
1239 if fd is not None:
1240 os.close(fd)
1241 self.assertFalse(os.path.exists(fn))
Serhiy Storchaka7e9d1d12015-04-20 10:12:28 +03001242 self.assertRaises(ValueError, os.mkdir, fn_with_NUL)
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +03001243 self.assertFalse(os.path.exists(fn))
1244 open(fn, 'wb').close()
Serhiy Storchaka7e9d1d12015-04-20 10:12:28 +03001245 self.assertRaises(ValueError, os.stat, fn_with_NUL)
Serhiy Storchaka2b0d2002015-04-20 09:53:58 +03001246
1247 def test_path_with_null_byte(self):
1248 fn = os.fsencode(support.TESTFN)
1249 fn_with_NUL = fn + b'\0'
1250 self.addCleanup(support.unlink, fn)
1251 support.unlink(fn)
1252 fd = None
1253 try:
1254 with self.assertRaises(ValueError):
1255 fd = os.open(fn_with_NUL, os.O_WRONLY | os.O_CREAT) # raises
1256 finally:
1257 if fd is not None:
1258 os.close(fd)
1259 self.assertFalse(os.path.exists(fn))
1260 self.assertRaises(ValueError, os.mkdir, fn_with_NUL)
1261 self.assertFalse(os.path.exists(fn))
1262 open(fn, 'wb').close()
1263 self.assertRaises(ValueError, os.stat, fn_with_NUL)
1264
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00001265class PosixGroupsTester(unittest.TestCase):
1266
1267 def setUp(self):
1268 if posix.getuid() != 0:
1269 raise unittest.SkipTest("not enough privileges")
1270 if not hasattr(posix, 'getgroups'):
1271 raise unittest.SkipTest("need posix.getgroups")
1272 if sys.platform == 'darwin':
1273 raise unittest.SkipTest("getgroups(2) is broken on OSX")
1274 self.saved_groups = posix.getgroups()
1275
1276 def tearDown(self):
1277 if hasattr(posix, 'setgroups'):
1278 posix.setgroups(self.saved_groups)
1279 elif hasattr(posix, 'initgroups'):
1280 name = pwd.getpwuid(posix.getuid()).pw_name
1281 posix.initgroups(name, self.saved_groups[0])
1282
1283 @unittest.skipUnless(hasattr(posix, 'initgroups'),
1284 "test needs posix.initgroups()")
1285 def test_initgroups(self):
1286 # find missing group
1287
Benjamin Peterson659a6f52014-03-01 19:14:12 -05001288 g = max(self.saved_groups or [0]) + 1
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00001289 name = pwd.getpwuid(posix.getuid()).pw_name
1290 posix.initgroups(name, g)
1291 self.assertIn(g, posix.getgroups())
1292
1293 @unittest.skipUnless(hasattr(posix, 'setgroups'),
1294 "test needs posix.setgroups()")
1295 def test_setgroups(self):
Antoine Pitroue5a91012010-09-04 17:32:06 +00001296 for groups in [[0], list(range(16))]:
Ronald Oussorenb6ee4f52010-07-23 13:53:51 +00001297 posix.setgroups(groups)
1298 self.assertListEqual(groups, posix.getgroups())
1299
Neal Norwitze241ce82003-02-17 18:17:05 +00001300def test_main():
Antoine Pitrou68c95922011-03-20 17:33:57 +01001301 try:
1302 support.run_unittest(PosixTester, PosixGroupsTester)
1303 finally:
1304 support.reap_children()
Neal Norwitze241ce82003-02-17 18:17:05 +00001305
1306if __name__ == '__main__':
1307 test_main()