Skip to content

Instantly share code, notes, and snippets.

@hoelzro
Created October 19, 2017 17:39
Show Gist options
  • Select an option

  • Save hoelzro/f0cef6d31367cd22ece498a0e83be6f7 to your computer and use it in GitHub Desktop.

Select an option

Save hoelzro/f0cef6d31367cd22ece498a0e83be6f7 to your computer and use it in GitHub Desktop.
import functools
import inspect
from multiprocessing import Process
import os
import signal
import sys
import time
import traceback
# XXX specify # levels to skip, specify the frame you want to start with (in case called from a signal handler)
def print_fancy_stack(output):
stack = inspect.stack()
for frame, filename, lineno, function, lines, line_index in stack[2:]:
output.write('File "{filename}", line {lineno}, in {function}\n {current_line}\n'.format(
filename=filename,
lineno=lineno,
function=function,
current_line=lines[line_index].rstrip('\n')))
if frame.f_locals and function != '<module>':
output.write('Locals:\n')
for variable in sorted(frame.f_locals.keys()):
output.write('\t'.join([variable, repr(frame.f_locals[variable])]) + '\n')
def foo():
for i in xrange(100000000):
pass
print 'done'
def bar():
foo()
# XXX you get a stack frame in `two`
def handle_signal(output, one, two):
print_fancy_stack(output)
def baz(read_fd, write_fd):
os.close(read_fd)
with os.fdopen(write_fd, 'w') as writer:
signal.signal(signal.SIGINT, functools.partial(handle_signal, writer))
signal.signal(signal.SIGTERM, functools.partial(handle_signal, writer))
bar()
def main():
read_fd, write_fd = os.pipe()
worker = Process(target=baz, args=(read_fd, write_fd))
worker.start()
os.close(write_fd)
reader = os.fdopen(read_fd, 'r')
time.sleep(1)
os.kill(worker.pid, signal.SIGTERM)
for line in reader:
print '>>>', line.rstrip('\n')
worker.join()
if __name__ == '__main__':
main()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment