diff options
author | Stefan Behnel <stefan_ml@behnel.de> | 2013-11-23 08:50:14 +0100 |
---|---|---|
committer | Stefan Behnel <stefan_ml@behnel.de> | 2013-11-23 08:50:14 +0100 |
commit | a6195f1a44ab21f5aa4b2a1b1842dd93115a3f42 (patch) | |
tree | 3b252cc8c30b45705e23bbaa056bf87f5a026eda | |
parent | 0c6fdf066588732f96d0f90eeace517de7a91f42 (diff) | |
download | cython-a6195f1a44ab21f5aa4b2a1b1842dd93115a3f42.tar.gz |
let CPython do the exception instantiation on 'raise' in Py3 to make sure we handle all special cases correctly
-rw-r--r-- | Cython/Utility/Exceptions.c | 22 | ||||
-rw-r--r-- | tests/run/reraise_3args.pyx | 23 |
2 files changed, 25 insertions, 20 deletions
diff --git a/Cython/Utility/Exceptions.c b/Cython/Utility/Exceptions.c index 3c3b64221..917f36618 100644 --- a/Cython/Utility/Exceptions.c +++ b/Cython/Utility/Exceptions.c @@ -135,7 +135,6 @@ raise_error: #else /* Python 3+ */ static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, PyObject *cause) { - PyObject* owned_instance = NULL; if (tb == Py_None) { tb = 0; } else if (tb && !PyTraceBack_Check(tb)) { @@ -143,11 +142,9 @@ static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, PyObject "raise: arg 3 must be a traceback or None"); goto bad; } - if (value == Py_None) - value = 0; if (PyExceptionInstance_Check(type)) { - if (value) { + if (value && value != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto bad; @@ -156,21 +153,7 @@ static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, PyObject type = (PyObject*) Py_TYPE(value); } else if (PyExceptionClass_Check(type)) { // instantiate the type now (we don't know when and how it will be caught) - PyObject *args; - if (!value) - args = PyTuple_New(0); - else if (PyTuple_Check(value)) { - Py_INCREF(value); - args = value; - } else - args = PyTuple_Pack(1, value); - if (!args) - goto bad; - owned_instance = PyEval_CallObject(type, args); - Py_DECREF(args); - if (!owned_instance) - goto bad; - value = owned_instance; + PyErr_NormalizeException(&type, &value, &tb); if (!PyExceptionInstance_Check(value)) { PyErr_Format(PyExc_TypeError, "calling %R should have returned an instance of " @@ -222,7 +205,6 @@ static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, PyObject } bad: - Py_XDECREF(owned_instance); return; } #endif diff --git a/tests/run/reraise_3args.pyx b/tests/run/reraise_3args.pyx new file mode 100644 index 000000000..a892efe48 --- /dev/null +++ b/tests/run/reraise_3args.pyx @@ -0,0 +1,23 @@ + +import sys + + +class MyError(Exception): + def __init__(self, name, var): + self.name = name + self.var = var + + +def reraise_explicitly(): + """ + >>> try: reraise_explicitly() + ... except MyError: print("RAISED!") + ... else: print("NOT RAISED!") + RAISED! + """ + try: + raise MyError('Oh no!', 42) + except MyError: + tmp = sys.exc_info() + + raise tmp[0], tmp[1], tmp[2] |