Issue #13188: When called without an explicit traceback argument,

generator.throw() now gets the traceback from the passed exception's
`__traceback__` attribute.  Patch by Petri Lehtinen.
This commit is contained in:
Antoine Pitrou 2011-10-18 16:40:50 +02:00
parent 6bfecd1271
commit 551ba20e8e
3 changed files with 35 additions and 0 deletions

View File

@ -1673,6 +1673,32 @@ Traceback (most recent call last):
... ...
ValueError: 7 ValueError: 7
Plain "raise" inside a generator should preserve the traceback (#13188).
The traceback should have 3 levels:
- g.throw()
- f()
- 1/0
>>> def f():
... try:
... yield
... except:
... raise
>>> g = f()
>>> try:
... 1/0
... except ZeroDivisionError as v:
... try:
... g.throw(v)
... except Exception as w:
... tb = w.__traceback__
>>> levels = 0
>>> while tb:
... levels += 1
... tb = tb.tb_next
>>> levels
3
Now let's try closing a generator: Now let's try closing a generator:
>>> def f(): >>> def f():

View File

@ -10,6 +10,10 @@ What's New in Python 3.2.3?
Core and Builtins Core and Builtins
----------------- -----------------
- Issue #13188: When called without an explicit traceback argument,
generator.throw() now gets the traceback from the passed exception's
``__traceback__`` attribute. Patch by Petri Lehtinen.
- Issue #7833: Extension modules built using distutils on Windows will no - Issue #7833: Extension modules built using distutils on Windows will no
longer include a "manifest" to prevent them failing at import time in some longer include a "manifest" to prevent them failing at import time in some
embedded situations. embedded situations.

View File

@ -261,6 +261,11 @@ gen_throw(PyGenObject *gen, PyObject *args)
val = typ; val = typ;
typ = PyExceptionInstance_Class(typ); typ = PyExceptionInstance_Class(typ);
Py_INCREF(typ); Py_INCREF(typ);
if (tb == NULL) {
/* Returns NULL if there's no traceback */
tb = PyException_GetTraceback(val);
}
} }
} }
else { else {