diff options
author | Matthew Pickering <matthewtpickering@gmail.com> | 2021-05-11 17:39:38 +0100 |
---|---|---|
committer | Matthew Pickering <matthewtpickering@gmail.com> | 2021-05-12 08:25:50 +0100 |
commit | df8ef1a4865ed9d1ec0ac6f1f34465c118060933 (patch) | |
tree | 00e135f76db96c9e14a2997f0e0d9fa9cd42ecfd | |
parent | ad659f711a8e01c6035b9fc3a4074b031211d515 (diff) | |
download | haskell-wip/hpt-oneshot.tar.gz |
testsuite: Teminate processes when the testsuite is interruptedwip/hpt-oneshot
-rw-r--r-- | testsuite/driver/runtests.py | 5 | ||||
-rw-r--r-- | testsuite/driver/testlib.py | 20 | ||||
-rw-r--r-- | testsuite/timeout/timeout.py | 53 |
3 files changed, 53 insertions, 25 deletions
diff --git a/testsuite/driver/runtests.py b/testsuite/driver/runtests.py index 39256aee5f..6335939245 100644 --- a/testsuite/driver/runtests.py +++ b/testsuite/driver/runtests.py @@ -465,6 +465,11 @@ else: break oneTest(watcher) except KeyboardInterrupt: + # Signal we are stopping + stopNow() + # Acquire all slots in the semaphore + acquire_all() + # Exit pass # flush everything before we continue diff --git a/testsuite/driver/testlib.py b/testsuite/driver/testlib.py index db40d6f82f..50f5133386 100644 --- a/testsuite/driver/testlib.py +++ b/testsuite/driver/testlib.py @@ -37,6 +37,11 @@ if config.use_threads: import threading pool_sema = threading.BoundedSemaphore(value=config.threads) +def acquire_all() -> None: + global pool_sema + for i in range(config.threads): + pool_sema.acquire() + global wantToStop wantToStop = False @@ -2340,6 +2345,19 @@ def dump_file(f: Path): except Exception: print('') +# Wait for a process but kill it if a global trigger is sent +def process_loop(r): + finished = False + while not (stopping() or finished): + try: + r.wait(timeout=1) + finished = True + except subprocess.TimeoutExpired: + pass + if not finished: + r.terminate() + return r.communicate() + def runCmd(cmd: str, stdin: Union[None, Path]=None, stdout: Union[None, Path]=None, @@ -2372,8 +2390,8 @@ def runCmd(cmd: str, stdout=subprocess.PIPE, stderr=hStdErr, env=ghc_env) + stdout_buffer, stderr_buffer = process_loop(r) - stdout_buffer, stderr_buffer = r.communicate() finally: if stdin_file: stdin_file.close() diff --git a/testsuite/timeout/timeout.py b/testsuite/timeout/timeout.py index f3468ad9fb..d6bc0cf326 100644 --- a/testsuite/timeout/timeout.py +++ b/testsuite/timeout/timeout.py @@ -1,33 +1,33 @@ #!/usr/bin/env python -try: +import errno +import os +import signal +import sys +import time - import errno - import os - import signal - import sys - import time +secs = int(sys.argv[1]) +cmd = sys.argv[2] - secs = int(sys.argv[1]) - cmd = sys.argv[2] +def killProcess(pid): + os.killpg(pid, signal.SIGKILL) + for x in range(10): + try: + time.sleep(0.3) + r = os.waitpid(pid, os.WNOHANG) + if r == (0, 0): + os.killpg(pid, signal.SIGKILL) + else: + return + except OSError as e: + if e.errno == errno.ECHILD: + return + else: + raise e - def killProcess(pid): - os.killpg(pid, signal.SIGKILL) - for x in range(10): - try: - time.sleep(0.3) - r = os.waitpid(pid, os.WNOHANG) - if r == (0, 0): - os.killpg(pid, signal.SIGKILL) - else: - return - except OSError as e: - if e.errno == errno.ECHILD: - return - else: - raise e +pid = os.fork() - pid = os.fork() +try: if pid == 0: # child os.setpgrp() @@ -50,7 +50,12 @@ try: sys.exit(99) # unexpected except KeyboardInterrupt: + killProcess(pid) sys.exit(98) +except SystemExit: + raise except: + print("Unexpected error:", sys.exc_info()[0]) + killProcess(pid) raise |