summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAngelos Evripiotis <jevripiotis@bloomberg.net>2017-12-22 13:54:58 +0000
committerTristan Van Berkom <tristan.vanberkom@codethink.co.uk>2017-12-22 14:45:51 -0500
commit78fc8440fdf9f007d893031275b5842fa4de7631 (patch)
tree59aa02aaa84eb8fde67cf9b829a74c1fcb94d998
parentac2bcb2cd5c6d5bb11201919658de4aa2b26788d (diff)
downloadbuildstream-78fc8440fdf9f007d893031275b5842fa4de7631.tar.gz
_signals.terminator_handler: wrap handlers in trys
It's possible for the custom termination handlers to raise exceptions. Indeed this was actually the case for utils._call(). They're especially difficult to reach with tests, so make extra effort to insulate them. Print any exceptions encountered as a regular traceback before exiting.
-rw-r--r--buildstream/_signals.py15
1 files changed, 14 insertions, 1 deletions
diff --git a/buildstream/_signals.py b/buildstream/_signals.py
index 65841df89..ee27190ac 100644
--- a/buildstream/_signals.py
+++ b/buildstream/_signals.py
@@ -19,6 +19,8 @@
# Tristan Van Berkom <tristan.vanberkom@codethink.co.uk>
import os
import signal
+import sys
+import traceback
from contextlib import contextmanager, ExitStack
from collections import deque
@@ -34,7 +36,18 @@ suspendable_stack = deque()
def terminator_handler(signal, frame):
while terminator_stack:
terminator = terminator_stack.pop()
- terminator()
+ try:
+ terminator()
+ except:
+ # Ensure we print something if there's an exception raised when
+ # processing the handlers. Note that the default exception
+ # handler won't be called because we os._exit next, so we must
+ # catch all possible exceptions with the unqualified 'except'
+ # clause.
+ traceback.print_exc(file=sys.stderr)
+ print('Error encountered in BuildStream while processing custom SIGTERM handler:',
+ terminator,
+ file=sys.stderr)
# Use special exit here, terminate immediately, recommended
# for precisely this situation where child forks are teminated.