Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit e40b3aa

Browse files
author
Victor Stinner
committed
Issue #12469: Run "wakeup" signal tests in subprocess to run the test in a
fresh process with only one thread and to not change signal handling of the parent process.
1 parent cd1aa0d commit e40b3aa

2 files changed

Lines changed: 72 additions & 37 deletions

File tree

Lib/test/test_signal.py

Lines changed: 68 additions & 37 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
import unittest
1212
from test import support
1313
from contextlib import closing
14-
from test.script_helper import spawn_python
14+
from test.script_helper import assert_python_ok, spawn_python
1515

1616
if sys.platform in ('os2', 'riscos'):
1717
raise unittest.SkipTest("Can't test signal on %s" % sys.platform)
@@ -233,49 +233,80 @@ def test_issue9324(self):
233233

234234
@unittest.skipIf(sys.platform == "win32", "Not valid on Windows")
235235
class WakeupSignalTests(unittest.TestCase):
236-
TIMEOUT_FULL = 10
237-
TIMEOUT_HALF = 5
236+
def check_wakeup(self, test_body):
237+
# use a subprocess to have only one thread and to not change signal
238+
# handling of the parent process
239+
code = """if 1:
240+
import fcntl
241+
import os
242+
import signal
243+
244+
def handler(signum, frame):
245+
pass
246+
247+
{}
248+
249+
signal.signal(signal.SIGALRM, handler)
250+
read, write = os.pipe()
251+
flags = fcntl.fcntl(write, fcntl.F_GETFL, 0)
252+
flags = flags | os.O_NONBLOCK
253+
fcntl.fcntl(write, fcntl.F_SETFL, flags)
254+
signal.set_wakeup_fd(write)
255+
256+
test()
257+
258+
os.close(read)
259+
os.close(write)
260+
""".format(test_body)
261+
262+
assert_python_ok('-c', code)
238263

239264
def test_wakeup_fd_early(self):
240-
import select
241-
242-
signal.alarm(1)
243-
before_time = time.time()
244-
# We attempt to get a signal during the sleep,
245-
# before select is called
246-
time.sleep(self.TIMEOUT_FULL)
247-
mid_time = time.time()
248-
self.assertTrue(mid_time - before_time < self.TIMEOUT_HALF)
249-
select.select([self.read], [], [], self.TIMEOUT_FULL)
250-
after_time = time.time()
251-
self.assertTrue(after_time - mid_time < self.TIMEOUT_HALF)
265+
self.check_wakeup("""def test():
266+
import select
267+
import time
252268
253-
def test_wakeup_fd_during(self):
254-
import select
269+
TIMEOUT_FULL = 10
270+
TIMEOUT_HALF = 5
255271
256-
signal.alarm(1)
257-
before_time = time.time()
258-
# We attempt to get a signal during the select call
259-
self.assertRaises(select.error, select.select,
260-
[self.read], [], [], self.TIMEOUT_FULL)
261-
after_time = time.time()
262-
self.assertTrue(after_time - before_time < self.TIMEOUT_HALF)
272+
signal.alarm(1)
273+
before_time = time.time()
274+
# We attempt to get a signal during the sleep,
275+
# before select is called
276+
time.sleep(TIMEOUT_FULL)
277+
mid_time = time.time()
278+
dt = mid_time - before_time
279+
if dt >= TIMEOUT_HALF:
280+
raise Exception("%s >= %s" % (dt, TIMEOUT_HALF))
281+
select.select([read], [], [], TIMEOUT_FULL)
282+
after_time = time.time()
283+
dt = after_time - mid_time
284+
if dt >= TIMEOUT_HALF:
285+
raise Exception("%s >= %s" % (dt, TIMEOUT_HALF))
286+
""")
263287

264-
def setUp(self):
265-
import fcntl
288+
def test_wakeup_fd_during(self):
289+
self.check_wakeup("""def test():
290+
import select
291+
import time
266292
267-
self.alrm = signal.signal(signal.SIGALRM, lambda x,y:None)
268-
self.read, self.write = os.pipe()
269-
flags = fcntl.fcntl(self.write, fcntl.F_GETFL, 0)
270-
flags = flags | os.O_NONBLOCK
271-
fcntl.fcntl(self.write, fcntl.F_SETFL, flags)
272-
self.old_wakeup = signal.set_wakeup_fd(self.write)
293+
TIMEOUT_FULL = 10
294+
TIMEOUT_HALF = 5
273295
274-
def tearDown(self):
275-
signal.set_wakeup_fd(self.old_wakeup)
276-
os.close(self.read)
277-
os.close(self.write)
278-
signal.signal(signal.SIGALRM, self.alrm)
296+
signal.alarm(1)
297+
before_time = time.time()
298+
# We attempt to get a signal during the select call
299+
try:
300+
select.select([read], [], [], TIMEOUT_FULL)
301+
except select.error:
302+
pass
303+
else:
304+
raise Exception("select.error not raised")
305+
after_time = time.time()
306+
dt = after_time - before_time
307+
if dt >= TIMEOUT_HALF:
308+
raise Exception("%s >= %s" % (dt, TIMEOUT_HALF))
309+
""")
279310

280311
@unittest.skipIf(sys.platform == "win32", "Not valid on Windows")
281312
class SiginterruptTest(unittest.TestCase):

Misc/NEWS

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,10 @@ C-API
3838
Tests
3939
-----
4040

41+
- Issue #12469: Run "wakeup" signal tests in subprocess to run the test in a
42+
fresh process with only one thread and to not change signal handling of the
43+
parent process.
44+
4145
- Issue #8716: Avoid crashes caused by Aqua Tk on OSX when attempting to run
4246
test_tk or test_ttk_guionly under a username that is not currently logged
4347
in to the console windowserver (as may be the case under buildbot or ssh).

0 commit comments

Comments
 (0)