def print_exception(self, context, type, value, tb): # Python 3 does not gracefully handle None value or tb in # traceback.print_exception() as previous versions did. # pylint:disable=no-member errstream = self.exception_stream if value is None: errstream.write('%s\n' % type.__name__) else: traceback.print_exception(type, value, tb, file=errstream) del tb try: errstream.write(gmctime()) errstream.write(' ' if context is not None else '\n') except: # pylint:disable=bare-except # Possible not safe to import under certain # error conditions in Python 2 pass if context is not None: if not isinstance(context, str): try: context = self.format_context(context) except: # pylint:disable=bare-except traceback.print_exc(file=self.exception_stream) context = repr(context) errstream.write('%s failed with %s\n\n' % ( context, getattr(type, '__name__', 'exception'), ))
def did_block_hub_report(self, hub, active_greenlet, format_kwargs): # XXX: On Python 2 with greenlet 1.0a1, '%s' formatting a greenlet # results in a unicode object. This is a bug in greenlet, I think. # https://github.com/python-greenlet/greenlet/issues/218 report = [ '=' * 80, '\n%s : Greenlet %s appears to be blocked' % (gmctime(), str(active_greenlet)) ] report.append(" Reported by %s" % (self, )) try: frame = sys._current_frames()[hub.thread_ident] except KeyError: # The thread holding the hub has died. Perhaps we shouldn't # even report this? stack = ["Unknown: No thread found for hub %r\n" % (hub, )] else: stack = traceback.format_stack(frame) report.append('Blocked Stack (for thread id %s):' % (hex(hub.thread_ident), )) report.append(''.join(stack)) report.append("Info:") report.extend(format_run_info(**format_kwargs)) return report
def print_exception(self, context, type, value, tb): # Python 3 does not gracefully handle None value or tb in # traceback.print_exception() as previous versions did. # pylint:disable=no-member errstream = self.exception_stream if not errstream: # pragma: no cover # If the error stream is gone, such as when the sys dict # gets cleared during interpreter shutdown, # don't cause follow-on errors. # See https://github.com/gevent/gevent/issues/1295 return if value is None: errstream.write('%s\n' % type.__name__) else: traceback.print_exception(type, value, tb, file=errstream) del tb try: errstream.write(gmctime()) errstream.write(' ' if context is not None else '\n') except: # pylint:disable=bare-except # Possible not safe to import under certain # error conditions in Python 2 pass if context is not None: if not isinstance(context, str): try: context = self.format_context(context) except: # pylint:disable=bare-except traceback.print_exc(file=self.exception_stream) context = repr(context) errstream.write('%s failed with %s\n\n' % (context, getattr(type, '__name__', 'exception'), ))
def monitor_blocking(self, hub): # Called periodically to see if the trace function has # fired to switch greenlets. If not, we will print # the greenlet tree. # For tests, we return a true value when we think we found something # blocking # There is a race condition with this being incremented in the # thread we're monitoring, but probably not often enough to lead # to annoying false positives. active_greenlet = self._active_greenlet did_switch = self._greenlet_switch_counter != 0 self._greenlet_switch_counter = 0 if did_switch or active_greenlet is None or active_greenlet is hub: # Either we switched, or nothing is running (we got a # trace event we don't know about or were requested to # ignore), or we spent the whole time in the hub, blocked # for IO. Nothing to report. return report = [ '=' * 80, '\n%s : Greenlet %s appears to be blocked' % (gmctime(), active_greenlet) ] report.append(" Reported by %s" % (self, )) try: frame = sys._current_frames()[hub.thread_ident] except KeyError: # The thread holding the hub has died. Perhaps we shouldn't # even report this? stack = ["Unknown: No thread found for hub %r\n" % (hub, )] else: stack = traceback.format_stack(frame) report.append('Blocked Stack (for thread id %s):' % (hex(hub.thread_ident), )) report.append(''.join(stack)) report.append("Info:") report.extend( format_run_info(greenlet_stacks=False, current_thread_ident=self.monitor_thread_ident)) report.append(report[0]) stream = hub.exception_stream for line in report: # Printing line by line may interleave with other things, # but it should also prevent a "reentrant call to print" # when the report is large. print(line, file=stream) notify( EventLoopBlocked(active_greenlet, GEVENT_CONFIG.max_blocking_time, report)) return (active_greenlet, report)
def did_block_hub_report(self, hub, active_greenlet, format_kwargs): report = ['=' * 80, '\n%s : Greenlet %s appears to be blocked' % (gmctime(), active_greenlet)] report.append(" Reported by %s" % (self,)) try: frame = sys._current_frames()[hub.thread_ident] except KeyError: # The thread holding the hub has died. Perhaps we shouldn't # even report this? stack = ["Unknown: No thread found for hub %r\n" % (hub,)] else: stack = traceback.format_stack(frame) report.append('Blocked Stack (for thread id %s):' % (hex(hub.thread_ident),)) report.append(''.join(stack)) report.append("Info:") report.extend(format_run_info(**format_kwargs)) return report