DebugClients/Python3/DebugBase.py

changeset 4365
d97f2e05ae1b
parent 4309
cc9c62f55413
child 4455
ca13a6f6c452
diff -r cdfdb1afaf27 -r d97f2e05ae1b DebugClients/Python3/DebugBase.py
--- a/DebugClients/Python3/DebugBase.py	Sun Aug 16 10:19:06 2015 +0200
+++ b/DebugClients/Python3/DebugBase.py	Sun Aug 16 12:24:28 2015 +0200
@@ -12,6 +12,7 @@
 import os
 import atexit
 import inspect
+from inspect import CO_GENERATOR
 
 from DebugProtocol import ResponseClearWatch, ResponseClearBreak, \
     ResponseLine, ResponseSyntax, ResponseException, CallTrace
@@ -265,6 +266,9 @@
         @exception bdb.BdbQuit raised to indicate the end of the debug session
         """
         if self.stop_here(frame) or frame == self.returnframe:
+            # Ignore return events in generator except when stepping.
+            if self.stopframe and frame.f_code.co_flags & CO_GENERATOR:
+                return self.trace_dispatch
             self.user_return(frame, arg)
             if self.quitting and not self._dbgClient.passive:
                 raise bdb.BdbQuit
@@ -280,9 +284,26 @@
         @exception bdb.BdbQuit raised to indicate the end of the debug session
         """
         if not self.__skip_it(frame):
+            # When stepping with next/until/return in a generator frame,
+            # skip the internal StopIteration exception (with no traceback)
+            # triggered by a subiterator run with the 'yield from'
+            # statement.
+            if not (frame.f_code.co_flags & CO_GENERATOR
+                    and arg[0] is StopIteration and arg[2] is None):
+                self.user_exception(frame, arg)
+                if self.quitting:
+                    raise bdb.BdbQuit
+        # Stop at the StopIteration or GeneratorExit exception when the user
+        # has set stopframe in a generator by issuing a return command, or a
+        # next/until command at the last statement in the generator before the
+        # exception.
+        elif (self.stopframe and frame is not self.stopframe
+                and self.stopframe.f_code.co_flags & CO_GENERATOR
+                and arg[0] in (StopIteration, GeneratorExit)):
             self.user_exception(frame, arg)
             if self.quitting:
                 raise bdb.BdbQuit
+        
         return self.trace_dispatch
 
     def set_trace(self, frame=None):

eric ide

mercurial