void PyErr_Restore(PyObject *type, PyObject *value, PyObject *traceback) { //puts("PyErr_Restore"); if (traceback != NULL && !PyTraceBack_Check(traceback)) { /* XXX Should never happen -- fatal error instead? */ /* Well, it could be None. */ Py_DECREF(traceback); traceback = NULL; } // env(); // jobject oldexc = (*env)->CallStaticObjectMethod(env, JyNIClass, JyErr_GetCurExc, NULL); // jobject jv = JyNI_JythonPyObject_FromPyObject(value); // jobject jtb = JyNI_JythonPyObject_FromPyObject(traceback); // jobject jt = JyNI_JythonPyObject_FromPyObject(type); // (*env)->CallStaticVoidMethod(env, JyNIClass, JyNIPyErr_Restore, // jt, // jv, // jtb); // if (oldexc) // { // //puts("oldexc"); // PyObject *oldtype, *oldvalue, *oldtraceback; // oldtype = JyNI_PyObject_FromJythonPyObject((*env)->GetObjectField(env, oldexc, pyExceptionTypeField)); // oldvalue = JyNI_PyObject_FromJythonPyObject((*env)->GetObjectField(env, oldexc, pyExceptionValueField)); // oldtraceback = JyNI_PyObject_FromJythonPyObject((*env)->GetObjectField(env, oldexc, pyExceptionTracebackField)); // // Py_XDECREF(oldtype); // Py_XDECREF(oldvalue); // Py_XDECREF(oldtraceback); // } PyThreadState *tstate = PyThreadState_GET(); PyObject *oldtype, *oldvalue, *oldtraceback; if (traceback != NULL && !PyTraceBack_Check(traceback)) { /* XXX Should never happen -- fatal error instead? */ /* Well, it could be None. */ Py_DECREF(traceback); traceback = NULL; } /* Save these in locals to safeguard against recursive invocation through Py_XDECREF */ oldtype = tstate->curexc_type; oldvalue = tstate->curexc_value; oldtraceback = tstate->curexc_traceback; tstate->curexc_type = type; tstate->curexc_value = value; tstate->curexc_traceback = traceback; Py_XDECREF(oldtype); Py_XDECREF(oldvalue); Py_XDECREF(oldtraceback); }
void PyErr_Display(PyObject *exception, PyObject *value, PyObject *tb) { PyObject *seen; PyObject *f = _PySys_GetObjectId(&PyId_stderr); if (PyExceptionInstance_Check(value) && tb != NULL && PyTraceBack_Check(tb)) { /* Put the traceback on the exception, otherwise it won't get displayed. See issue #18776. */ PyObject *cur_tb = PyException_GetTraceback(value); if (cur_tb == NULL) PyException_SetTraceback(value, tb); else Py_DECREF(cur_tb); } if (f == Py_None) { /* pass */ } else if (f == NULL) { _PyObject_Dump(value); fprintf(stderr, "lost sys.stderr\n"); } else { /* We choose to ignore seen being possibly NULL, and report at least the main exception (it could be a MemoryError). */ seen = PySet_New(NULL); if (seen == NULL) PyErr_Clear(); print_exception_recursive(f, value, seen); Py_XDECREF(seen); } }
Box* generatorThrow(Box* s, BoxedClass* exc_cls, Box* exc_val = nullptr, Box** args = nullptr) noexcept(S == CAPI) { assert(s->cls == generator_cls); BoxedGenerator* self = static_cast<BoxedGenerator*>(s); if (self->iterated_from__hasnext__ && !self->entryExited) Py_FatalError(".throw called on generator last advanced with __hasnext__"); Box* exc_tb = args ? args[0] : nullptr; if (exc_tb && exc_tb != Py_None && !PyTraceBack_Check(exc_tb)) { if (S == CAPI) { PyErr_SetString(TypeError, "throw() third argument must be a traceback object"); return NULL; } raiseExcHelper(TypeError, "throw() third argument must be a traceback object"); } if (!exc_val) exc_val = Py_None; if (!exc_tb) exc_tb = Py_None; ExcInfo exc_info = excInfoForRaise(incref(exc_cls), incref(exc_val), incref(exc_tb)); if (self->entryExited) { if (S == CAPI) { setCAPIException(exc_info); return NULL; } throw exc_info; } self->exception = exc_info; return generatorSend<S>(self, Py_None); }
void PyErr_Restore(PyObject *type, PyObject *value, PyObject *traceback) { PyThreadState *tstate = PyThreadState_GET(); PyObject *oldtype, *oldvalue, *oldtraceback; if (traceback != NULL && !PyTraceBack_Check(traceback)) { /* XXX Should never happen -- fatal error instead? */ /* Well, it could be None. */ Py_DECREF(traceback); traceback = NULL; } /* Save these in locals to safeguard against recursive invocation through Py_XDECREF */ oldtype = tstate->curexc_type; oldvalue = tstate->curexc_value; oldtraceback = tstate->curexc_traceback; tstate->curexc_type = type; tstate->curexc_value = value; tstate->curexc_traceback = traceback; Py_XDECREF(oldtype); Py_XDECREF(oldvalue); Py_XDECREF(oldtraceback); }
int PyTraceBack_Print(PyObject *v, PyObject *f) { int err; PyObject *limitv; long limit = PyTraceBack_LIMIT; if (v == NULL) return 0; if (!PyTraceBack_Check(v)) { PyErr_BadInternalCall(); return -1; } limitv = PySys_GetObject("tracebacklimit"); if (limitv && PyLong_Check(limitv)) { int overflow; limit = PyLong_AsLongAndOverflow(limitv, &overflow); if (overflow > 0) { limit = LONG_MAX; } else if (limit <= 0) { return 0; } } err = PyFile_WriteString("Traceback (most recent call last):\n", f); if (!err) err = tb_printinternal((PyTracebackObject *)v, f, limit); return err; }
static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, CYTHON_UNUSED PyObject *cause) { __Pyx_PyThreadState_declare /* 'cause' is only used in Py3 */ Py_XINCREF(type); if (!value || value == Py_None) value = NULL; else Py_INCREF(value); if (!tb || tb == Py_None) tb = NULL; else { Py_INCREF(tb); if (!PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto raise_error; } } if (PyType_Check(type)) { /* instantiate the type now (we don't know when and how it will be caught) */ #if CYTHON_COMPILING_IN_PYPY /* PyPy can't handle value == NULL */ if (!value) { Py_INCREF(Py_None); value = Py_None; } #endif PyErr_NormalizeException(&type, &value, &tb); } else { /* Raising an instance. The value should be a dummy. */ if (value) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto raise_error; } /* Normalize to raise <class>, <instance> */ value = type; type = (PyObject*) Py_TYPE(type); Py_INCREF(type); if (!PyType_IsSubtype((PyTypeObject *)type, (PyTypeObject *)PyExc_BaseException)) { PyErr_SetString(PyExc_TypeError, "raise: exception class must be a subclass of BaseException"); goto raise_error; } } __Pyx_PyThreadState_assign __Pyx_ErrRestore(type, value, tb); return; raise_error: Py_XDECREF(value); Py_XDECREF(type); Py_XDECREF(tb); return; }
// takes the three arguments of a `raise' and produces the ExcInfo to throw ExcInfo excInfoForRaise(Box* type, Box* value, Box* tb) { assert(type && value && tb); // use None for default behavior, not nullptr // TODO switch this to PyErr_Normalize if (tb == None) { tb = NULL; } else if (tb != NULL && !PyTraceBack_Check(tb)) { raiseExcHelper(TypeError, "raise: arg 3 must be a traceback or None"); } /* Next, repeatedly, replace a tuple exception with its first item */ while (PyTuple_Check(type) && PyTuple_Size(type) > 0) { PyObject* tmp = type; type = PyTuple_GET_ITEM(type, 0); Py_INCREF(type); Py_DECREF(tmp); } if (PyExceptionClass_Check(type)) { PyErr_NormalizeException(&type, &value, &tb); if (!PyExceptionInstance_Check(value)) { raiseExcHelper(TypeError, "calling %s() should have returned an instance of " "BaseException, not '%s'", ((PyTypeObject*)type)->tp_name, Py_TYPE(value)->tp_name); } } else if (PyExceptionInstance_Check(type)) { /* Raising an instance. The value should be a dummy. */ if (value != Py_None) { raiseExcHelper(TypeError, "instance exception may not have a separate value"); } else { /* Normalize to raise <class>, <instance> */ Py_DECREF(value); value = type; type = PyExceptionInstance_Class(type); Py_INCREF(type); } } else { /* Not something you can raise. You get an exception anyway, just not what you specified :-) */ raiseExcHelper(TypeError, "exceptions must be old-style classes or " "derived from BaseException, not %s", type->cls->tp_name); } assert(PyExceptionClass_Check(type)); if (tb == NULL) { tb = None; } return ExcInfo(type, value, tb); }
static PyObject * gen_throw(PyGenObject *gen, PyObject *typ, PyObject *val, PyObject *tb) { /* First, check the traceback argument, replacing None with NULL. */ if (tb == Py_None) tb = NULL; else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "throw() third argument must be a traceback object"); return NULL; } Py_INCREF(typ); Py_XINCREF(val); Py_XINCREF(tb); if (PyExceptionClass_Check(typ)) { PyErr_NormalizeException(&typ, &val, &tb); } else if (PyExceptionInstance_Check(typ)) { /* Raising an instance. The value should be a dummy. */ if (val && val != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto failed_throw; } else { /* Normalize to raise <class>, <instance> */ Py_XDECREF(val); val = typ; typ = PyExceptionInstance_Class(typ); Py_INCREF(typ); } } else { /* Not something you can raise. throw() fails. */ PyErr_Format(PyExc_TypeError, "exceptions must be classes, or instances, not %s", typ->ob_type->tp_name); goto failed_throw; } PyErr_Restore(typ, val, tb); return gen_send_ex(gen, Py_None, 1); failed_throw: /* Didn't use our arguments, so restore their original refcounts */ Py_DECREF(typ); Py_XDECREF(val); Py_XDECREF(tb); return NULL; }
NUITKA_NO_RETURN NUITKA_MAY_BE_UNUSED static inline void RAISE_EXCEPTION_WITH_TRACEBACK( PyObject *exception_type, PyObject *value, PyObject *traceback ) { if ( traceback == Py_None ) { traceback = NULL; } // Check traceback if( traceback != NULL && !PyTraceBack_Check( traceback ) ) { PyErr_Format( PyExc_TypeError, "raise: arg 3 must be a traceback or None" ); throw PythonException(); } RAISE_EXCEPTION_WITH_VALUE( exception_type, value, traceback ); }
static PyObject * tb_new_impl(PyTypeObject *type, PyObject *tb_next, PyFrameObject *tb_frame, int tb_lasti, int tb_lineno) /*[clinic end generated code: output=fa077debd72d861a input=01cbe8ec8783fca7]*/ { if (tb_next == Py_None) { tb_next = NULL; } else if (!PyTraceBack_Check(tb_next)) { return PyErr_Format(PyExc_TypeError, "expected traceback object or None, got '%s'", Py_TYPE(tb_next)->tp_name); } return tb_create_raw((PyTracebackObject *)tb_next, tb_frame, tb_lasti, tb_lineno); }
static PyTracebackObject * newtracebackobject(PyTracebackObject *next, PyFrameObject *frame) { PyTracebackObject *tb; if ((next != NULL && !PyTraceBack_Check(next)) || frame == NULL || !PyFrame_Check(frame)) { PyErr_BadInternalCall(); return NULL; } tb = PyObject_GC_New(PyTracebackObject, &PyTraceBack_Type); if (tb != NULL) { Py_XINCREF(next); tb->tb_next = next; Py_XINCREF(frame); tb->tb_frame = frame; tb->tb_lasti = frame->f_lasti; tb->tb_lineno = PyFrame_GetLineNumber(frame); PyObject_GC_Track(tb); } return tb; }
int PyTraceBack_Print(PyObject *v, PyObject *f) { int err; PyObject *limitv; long limit = PyTraceBack_LIMIT; if (v == NULL) return 0; if (!PyTraceBack_Check(v)) { PyErr_BadInternalCall(); return -1; } limitv = PySys_GetObject("tracebacklimit"); if (limitv) { PyObject *exc_type, *exc_value, *exc_tb; PyErr_Fetch(&exc_type, &exc_value, &exc_tb); limit = PyLong_AsLong(limitv); if (limit == -1 && PyErr_Occurred()) { if (PyErr_ExceptionMatches(PyExc_OverflowError)) { limit = PyTraceBack_LIMIT; } else { Py_XDECREF(exc_type); Py_XDECREF(exc_value); Py_XDECREF(exc_tb); return 0; } } else if (limit <= 0) { limit = PyTraceBack_LIMIT; } PyErr_Restore(exc_type, exc_value, exc_tb); } err = PyFile_WriteString("Traceback (most recent call last):\n", f); if (!err) err = tb_printinternal((PyTracebackObject *)v, f, limit); return err; }
Box* generatorThrow(Box* s, BoxedClass* exc_cls, Box* exc_val = nullptr, Box** args = nullptr) { assert(s->cls == generator_cls); BoxedGenerator* self = static_cast<BoxedGenerator*>(s); if (self->iterated_from__hasnext__ && !self->entryExited) Py_FatalError(".throw called on generator last advanced with __hasnext__"); Box* exc_tb = args ? args[0] : nullptr; if (exc_tb && exc_tb != None && !PyTraceBack_Check(exc_tb)) raiseExcHelper(TypeError, "throw() third argument must be a traceback object"); if (!exc_val) exc_val = None; if (!exc_tb) exc_tb = None; ExcInfo exc_info = excInfoForRaise(exc_cls, exc_val, exc_tb); if (self->entryExited) throw exc_info; self->exception = exc_info; return generatorSend<CXX>(self, None); }
static PyObject * tb_create_raw(PyTracebackObject *next, PyFrameObject *frame, int lasti, int lineno) { PyTracebackObject *tb; if ((next != NULL && !PyTraceBack_Check(next)) || frame == NULL || !PyFrame_Check(frame)) { PyErr_BadInternalCall(); return NULL; } tb = PyObject_GC_New(PyTracebackObject, &PyTraceBack_Type); if (tb != NULL) { Py_XINCREF(next); tb->tb_next = next; Py_XINCREF(frame); tb->tb_frame = frame; tb->tb_lasti = lasti; tb->tb_lineno = lineno; PyObject_GC_Track(tb); } return (PyObject *)tb; }
int PyTraceBack_Print(PyObject *v, PyObject *f) { int err; PyObject *limitv; int limit = 1000; if (v == NULL) return 0; if (!PyTraceBack_Check(v)) { PyErr_BadInternalCall(); return -1; } limitv = PySys_GetObject("tracebacklimit"); if (limitv && PyInt_Check(limitv)) { limit = PyInt_AsLong(limitv); if (limit <= 0) return 0; } err = PyFile_WriteString("Traceback (most recent call last):\n", f); if (!err) err = tb_printinternal((tracebackobject *)v, f, limit); return err; }
void _PyTrash_deposit_object(PyObject *op) { int typecode; if (PyTuple_Check(op)) typecode = Py_TRASHCAN_TUPLE; else if (PyList_Check(op)) typecode = Py_TRASHCAN_LIST; else if (PyDict_Check(op)) typecode = Py_TRASHCAN_DICT; else if (PyFrame_Check(op)) typecode = Py_TRASHCAN_FRAME; else if (PyTraceBack_Check(op)) typecode = Py_TRASHCAN_TRACEBACK; else /* We have a bug here -- those are the only types in GC */ { Py_FatalError("Type not supported in GC -- internal bug"); return; /* pacify compiler -- execution never here */ } op->ob_refcnt = typecode; op->ob_type = (PyTypeObject*)_PyTrash_delete_later; _PyTrash_delete_later = op; }
static int tb_next_set(PyTracebackObject *self, PyObject *new_next, void *Py_UNUSED(_)) { if (!new_next) { PyErr_Format(PyExc_TypeError, "can't delete tb_next attribute"); return -1; } /* We accept None or a traceback object, and map None -> NULL (inverse of tb_next_get) */ if (new_next == Py_None) { new_next = NULL; } else if (!PyTraceBack_Check(new_next)) { PyErr_Format(PyExc_TypeError, "expected traceback object, got '%s'", Py_TYPE(new_next)->tp_name); return -1; } /* Check for loops */ PyTracebackObject *cursor = (PyTracebackObject *)new_next; while (cursor) { if (cursor == self) { PyErr_Format(PyExc_ValueError, "traceback loop detected"); return -1; } cursor = cursor->tb_next; } PyObject *old_next = (PyObject*)self->tb_next; Py_XINCREF(new_next); self->tb_next = (PyTracebackObject *)new_next; Py_XDECREF(old_next); return 0; }
static PyObject *Nuitka_Generator_throw( struct Nuitka_GeneratorObject *generator, PyObject *args ) { assert( generator->m_exception_type == NULL ); assert( generator->m_exception_value == NULL ); assert( generator->m_exception_tb == NULL ); int res = PyArg_UnpackTuple( args, "throw", 1, 3, &generator->m_exception_type, &generator->m_exception_value, (PyObject **)&generator->m_exception_tb ); if (unlikely( res == 0 )) { generator->m_exception_type = NULL; generator->m_exception_value = NULL; generator->m_exception_tb = NULL; return NULL; } if ( (PyObject *)generator->m_exception_tb == Py_None ) { generator->m_exception_tb = NULL; } else if ( generator->m_exception_tb != NULL && !PyTraceBack_Check( generator->m_exception_tb ) ) { generator->m_exception_type = NULL; generator->m_exception_value = NULL; generator->m_exception_tb = NULL; PyErr_Format( PyExc_TypeError, "throw() third argument must be a traceback object" ); return NULL; } if ( PyExceptionClass_Check( generator->m_exception_type )) { Py_INCREF( generator->m_exception_type ); Py_XINCREF( generator->m_exception_value ); Py_XINCREF( generator->m_exception_tb ); NORMALIZE_EXCEPTION( &generator->m_exception_type, &generator->m_exception_value, &generator->m_exception_tb ); } else if ( PyExceptionInstance_Check( generator->m_exception_type ) ) { if ( generator->m_exception_value && generator->m_exception_value != Py_None ) { generator->m_exception_type = NULL; generator->m_exception_value = NULL; generator->m_exception_tb = NULL; PyErr_Format( PyExc_TypeError, "instance exception may not have a separate value" ); return NULL; } generator->m_exception_value = generator->m_exception_type; Py_INCREF( generator->m_exception_value ); generator->m_exception_type = PyExceptionInstance_Class( generator->m_exception_type ); Py_INCREF( generator->m_exception_type ); Py_XINCREF( generator->m_exception_tb ); } else { PyErr_Format( PyExc_TypeError, #if PYTHON_VERSION < 300 "exceptions must be classes, or instances, not %s", #else "exceptions must be classes or instances deriving from BaseException, not %s", #endif Py_TYPE( generator->m_exception_type )->tp_name ); generator->m_exception_type = NULL; generator->m_exception_value = NULL; generator->m_exception_tb = NULL; return NULL; } if ( ( generator->m_exception_tb != NULL ) && ( (PyObject *)generator->m_exception_tb != Py_None ) && ( !PyTraceBack_Check( generator->m_exception_tb ) ) ) { PyErr_Format( PyExc_TypeError, "throw() third argument must be a traceback object" ); return NULL; } if ( generator->m_status != status_Finished ) { PyObject *result = Nuitka_Generator_send( generator, Py_None ); return result; } else { RESTORE_ERROR_OCCURRED( generator->m_exception_type, generator->m_exception_value, generator->m_exception_tb ); generator->m_exception_type = NULL; generator->m_exception_value = NULL; generator->m_exception_tb = NULL; return NULL; } }
static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb) { Py_XINCREF(type); Py_XINCREF(value); Py_XINCREF(tb); /* First, check the traceback argument, replacing None with NULL. */ if (tb == Py_None) { Py_DECREF(tb); tb = 0; } else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto raise_error; } /* Next, replace a missing value with None */ if (value == NULL) { value = Py_None; Py_INCREF(value); } /* Next, repeatedly, replace a tuple exception with its first item */ while (PyTuple_Check(type) && PyTuple_Size(type) > 0) { PyObject *tmp = type; type = PyTuple_GET_ITEM(type, 0); Py_INCREF(type); Py_DECREF(tmp); } if (PyString_Check(type)) ; else if (PyClass_Check(type)) ; /*PyErr_NormalizeException(&type, &value, &tb);*/ else if (PyInstance_Check(type)) { /* Raising an instance. The value should be a dummy. */ if (value != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto raise_error; } else { /* Normalize to raise <class>, <instance> */ Py_DECREF(value); value = type; type = (PyObject*) ((PyInstanceObject*)type)->in_class; Py_INCREF(type); } } else { /* Not something you can raise. You get an exception anyway, just not what you specified :-) */ PyErr_Format(PyExc_TypeError, "exceptions must be strings, classes, or " "instances, not %s", type->ob_type->tp_name); goto raise_error; } PyErr_Restore(type, value, tb); return; raise_error: Py_XDECREF(value); Py_XDECREF(type); Py_XDECREF(tb); return; }
NUITKA_NO_RETURN NUITKA_MAY_BE_UNUSED static void RAISE_EXCEPTION_WITH_TYPE( PyObject *exception_type, PyObject *exception_tb ) { PyTracebackObject *traceback = (PyTracebackObject *)exception_tb; assertObject( traceback ); assert( PyTraceBack_Check( traceback ) ); assertObject( exception_type ); if ( PyExceptionClass_Check( exception_type ) ) { PyObject *value = NULL; Py_INCREF( exception_type ); Py_XINCREF( traceback ); NORMALIZE_EXCEPTION( &exception_type, &value, &traceback ); #if PYTHON_VERSION >= 270 if (unlikely( !PyExceptionInstance_Check( value ) )) { Py_DECREF( exception_type ); Py_DECREF( value ); Py_XDECREF( traceback ); PyErr_Format( PyExc_TypeError, "calling %s() should have returned an instance of BaseException, not '%s'", ((PyTypeObject *)exception_type)->tp_name, Py_TYPE( value )->tp_name ); throw PythonException(); } #endif #if PYTHON_VERSION >= 300 CHAIN_EXCEPTION( exception_type, value ); #endif throw PythonException( exception_type, value, traceback ); } else if ( PyExceptionInstance_Check( exception_type ) ) { PyObject *value = exception_type; exception_type = PyExceptionInstance_Class( exception_type ); #if PYTHON_VERSION >= 300 CHAIN_EXCEPTION( exception_type, value ); PyTracebackObject *prev = (PyTracebackObject *)PyException_GetTraceback( value ); if ( prev != NULL ) { assert( traceback->tb_next == NULL ); traceback->tb_next = prev; } PyException_SetTraceback( value, (PyObject *)traceback ); #endif throw PythonException( INCREASE_REFCOUNT( exception_type ), INCREASE_REFCOUNT( value ), INCREASE_REFCOUNT( traceback ) ); } else { PyErr_Format( PyExc_TypeError, WRONG_EXCEPTION_TYPE_ERROR_MESSAGE, Py_TYPE( exception_type )->tp_name ); PythonException to_throw; to_throw.setTraceback( INCREASE_REFCOUNT( traceback ) ); throw to_throw; } }
static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, PyObject *cause) { if (tb == Py_None) { tb = 0; } else if (tb && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto bad; } if (value == Py_None) value = 0; if (PyExceptionInstance_Check(type)) { if (value) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto bad; } value = type; type = (PyObject*) Py_TYPE(value); } else if (!PyExceptionClass_Check(type)) { PyErr_SetString(PyExc_TypeError, "raise: exception class must be a subclass of BaseException"); goto bad; } if (cause) { PyObject *fixed_cause; if (PyExceptionClass_Check(cause)) { fixed_cause = PyObject_CallObject(cause, NULL); if (fixed_cause == NULL) goto bad; } else if (PyExceptionInstance_Check(cause)) { fixed_cause = cause; Py_INCREF(fixed_cause); } else { PyErr_SetString(PyExc_TypeError, "exception causes must derive from " "BaseException"); goto bad; } if (!value) { value = PyObject_CallObject(type, NULL); } PyException_SetCause(value, fixed_cause); } PyErr_SetObject(type, value); if (tb) { PyThreadState *tstate = PyThreadState_GET(); PyObject* tmp_tb = tstate->curexc_traceback; if (tb != tmp_tb) { Py_INCREF(tb); tstate->curexc_traceback = tb; Py_XDECREF(tmp_tb); } } bad: return; }
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)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto bad; } if (value == Py_None) value = 0; if (PyExceptionInstance_Check(type)) { if (value) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto bad; } value = type; type = (PyObject*) Py_TYPE(value); } else if (PyExceptionClass_Check(type)) { // make sure value is an exception instance of type PyObject *instance_class = NULL; if (value && PyExceptionInstance_Check(value)) { instance_class = (PyObject*) Py_TYPE(value); if (instance_class != type) { if (PyObject_IsSubclass(instance_class, type)) { // believe the instance type = instance_class; } else { instance_class = NULL; } } } if (!instance_class) { // instantiate the type now (we don't know when and how it will be caught) // assuming that 'value' is an argument to the type's constructor // not using PyErr_NormalizeException() to avoid ref-counting problems 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 = PyObject_Call(type, args, NULL); Py_DECREF(args); if (!owned_instance) goto bad; value = owned_instance; if (!PyExceptionInstance_Check(value)) { PyErr_Format(PyExc_TypeError, "calling %R should have returned an instance of " "BaseException, not %R", type, Py_TYPE(value)); goto bad; } } } else { PyErr_SetString(PyExc_TypeError, "raise: exception class must be a subclass of BaseException"); goto bad; } #if PY_VERSION_HEX >= 0x03030000 if (cause) { #else if (cause && cause != Py_None) { #endif PyObject *fixed_cause; if (cause == Py_None) { // raise ... from None fixed_cause = NULL; } else if (PyExceptionClass_Check(cause)) { fixed_cause = PyObject_CallObject(cause, NULL); if (fixed_cause == NULL) goto bad; } else if (PyExceptionInstance_Check(cause)) { fixed_cause = cause; Py_INCREF(fixed_cause); } else { PyErr_SetString(PyExc_TypeError, "exception causes must derive from " "BaseException"); goto bad; } PyException_SetCause(value, fixed_cause); } PyErr_SetObject(type, value); if (tb) { #if CYTHON_COMPILING_IN_PYPY PyObject *tmp_type, *tmp_value, *tmp_tb; PyErr_Fetch(&tmp_type, &tmp_value, &tmp_tb); Py_INCREF(tb); PyErr_Restore(tmp_type, tmp_value, tb); Py_XDECREF(tmp_tb); #else PyThreadState *tstate = PyThreadState_GET(); PyObject* tmp_tb = tstate->curexc_traceback; if (tb != tmp_tb) { Py_INCREF(tb); tstate->curexc_traceback = tb; Py_XDECREF(tmp_tb); } #endif } bad: Py_XDECREF(owned_instance); return; } #endif /////////////// GetException.proto /////////////// static int __Pyx_GetException(PyObject **type, PyObject **value, PyObject **tb); /*proto*/ /////////////// GetException /////////////// static int __Pyx_GetException(PyObject **type, PyObject **value, PyObject **tb) { PyObject *local_type, *local_value, *local_tb; #if CYTHON_COMPILING_IN_CPYTHON PyObject *tmp_type, *tmp_value, *tmp_tb; PyThreadState *tstate = PyThreadState_GET(); local_type = tstate->curexc_type; local_value = tstate->curexc_value; local_tb = tstate->curexc_traceback; tstate->curexc_type = 0; tstate->curexc_value = 0; tstate->curexc_traceback = 0; #else PyErr_Fetch(&local_type, &local_value, &local_tb); #endif PyErr_NormalizeException(&local_type, &local_value, &local_tb); #if CYTHON_COMPILING_IN_CPYTHON if (unlikely(tstate->curexc_type)) #else if (unlikely(PyErr_Occurred())) #endif goto bad; #if PY_MAJOR_VERSION >= 3 if (local_tb) { if (unlikely(PyException_SetTraceback(local_value, local_tb) < 0)) goto bad; } #endif // traceback may be NULL for freshly raised exceptions Py_XINCREF(local_tb); // exception state may be temporarily empty in parallel loops (race condition) Py_XINCREF(local_type); Py_XINCREF(local_value); *type = local_type; *value = local_value; *tb = local_tb; #if CYTHON_COMPILING_IN_CPYTHON tmp_type = tstate->exc_type; tmp_value = tstate->exc_value; tmp_tb = tstate->exc_traceback; tstate->exc_type = local_type; tstate->exc_value = local_value; tstate->exc_traceback = local_tb; // Make sure tstate is in a consistent state when we XDECREF // these objects (DECREF may run arbitrary code). Py_XDECREF(tmp_type); Py_XDECREF(tmp_value); Py_XDECREF(tmp_tb); #else PyErr_SetExcInfo(local_type, local_value, local_tb); #endif return 0; bad: *type = 0; *value = 0; *tb = 0; Py_XDECREF(local_type); Py_XDECREF(local_value); Py_XDECREF(local_tb); return -1; }
static PyObject * Fiber_func_throw(Fiber *self, PyObject *args) { Fiber *current; PyObject *typ, *val, *tb; val = tb = NULL; if (!PyArg_ParseTuple(args, "O|OO:throw", &typ, &val, &tb)) { return NULL; } /* First, check the traceback argument, replacing None, with NULL */ if (tb == Py_None) { tb = NULL; } else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "throw() third argument must be a traceback object"); return NULL; } Py_INCREF(typ); Py_XINCREF(val); Py_XINCREF(tb); if (PyExceptionClass_Check(typ)) { PyErr_NormalizeException(&typ, &val, &tb); } else if (PyExceptionInstance_Check(typ)) { /* Raising an instance. The value should be a dummy. */ if (val && val != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exceptions cannot have a separate value"); goto error; } else { /* Normalize to raise <class>, <instance> */ Py_XDECREF(val); val = typ; typ = PyExceptionInstance_Class(typ); Py_INCREF(typ); } } else { /* Not something you can raise. throw() fails. */ PyErr_Format(PyExc_TypeError, "exceptions must be classes, or instances, not %s", Py_TYPE(typ)->tp_name); goto error; } if (!CHECK_STATE) { goto error; } current = _global_state.current; if (self == current) { PyErr_SetString(PyExc_FiberError, "cannot throw from a Fiber to itself"); goto error; } if (self->stacklet_h == EMPTY_STACKLET_HANDLE) { PyErr_SetString(PyExc_FiberError, "Fiber has ended"); goto error; } if (self->thread_h != current->thread_h) { PyErr_SetString(PyExc_FiberError, "cannot switch to a Fiber on a different thread"); return NULL; } /* set error and do a switch with NULL as the value */ PyErr_Restore(typ, val, tb); return do_switch(self, NULL); error: /* Didn't use our arguments, so restore their original refcounts */ Py_DECREF(typ); Py_XDECREF(val); Py_XDECREF(tb); return NULL; }
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)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto bad; } if (value == Py_None) value = 0; if (PyExceptionInstance_Check(type)) { if (value) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto bad; } value = type; type = (PyObject*) Py_TYPE(value); } else if (PyExceptionClass_Check(type)) { // make sure value is an exception instance of type PyObject *instance_class = NULL; if (value && PyExceptionInstance_Check(value)) { instance_class = (PyObject*) Py_TYPE(value); if (instance_class != type) { int is_subclass = PyObject_IsSubclass(instance_class, type); if (!is_subclass) { instance_class = NULL; } else if (unlikely(is_subclass == -1)) { // error on subclass test goto bad; } else { // believe the instance type = instance_class; } } } if (!instance_class) { // instantiate the type now (we don't know when and how it will be caught) // assuming that 'value' is an argument to the type's constructor // not using PyErr_NormalizeException() to avoid ref-counting problems 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 = PyObject_Call(type, args, NULL); Py_DECREF(args); if (!owned_instance) goto bad; value = owned_instance; if (!PyExceptionInstance_Check(value)) { PyErr_Format(PyExc_TypeError, "calling %R should have returned an instance of " "BaseException, not %R", type, Py_TYPE(value)); goto bad; } } } else { PyErr_SetString(PyExc_TypeError, "raise: exception class must be a subclass of BaseException"); goto bad; } if (cause) { PyObject *fixed_cause; if (cause == Py_None) { // raise ... from None fixed_cause = NULL; } else if (PyExceptionClass_Check(cause)) { fixed_cause = PyObject_CallObject(cause, NULL); if (fixed_cause == NULL) goto bad; } else if (PyExceptionInstance_Check(cause)) { fixed_cause = cause; Py_INCREF(fixed_cause); } else { PyErr_SetString(PyExc_TypeError, "exception causes must derive from " "BaseException"); goto bad; } PyException_SetCause(value, fixed_cause); } PyErr_SetObject(type, value); if (tb) { #if CYTHON_COMPILING_IN_PYPY PyObject *tmp_type, *tmp_value, *tmp_tb; PyErr_Fetch(&tmp_type, &tmp_value, &tmp_tb); Py_INCREF(tb); PyErr_Restore(tmp_type, tmp_value, tb); Py_XDECREF(tmp_tb); #else PyThreadState *tstate = __Pyx_PyThreadState_Current; PyObject* tmp_tb = tstate->curexc_traceback; if (tb != tmp_tb) { Py_INCREF(tb); tstate->curexc_traceback = tb; Py_XDECREF(tmp_tb); } #endif } bad: Py_XDECREF(owned_instance); return; }
static void __Pyx_Raise(PyObject *type, PyObject *value, PyObject *tb, CYTHON_UNUSED PyObject *cause) { /* cause is unused */ Py_XINCREF(type); Py_XINCREF(value); Py_XINCREF(tb); /* First, check the traceback argument, replacing None with NULL. */ if (tb == Py_None) { Py_DECREF(tb); tb = 0; } else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "raise: arg 3 must be a traceback or None"); goto raise_error; } /* Next, replace a missing value with None */ if (value == NULL) { value = Py_None; Py_INCREF(value); } #if PY_VERSION_HEX < 0x02050000 if (!PyClass_Check(type)) #else if (!PyType_Check(type)) #endif { /* Raising an instance. The value should be a dummy. */ if (value != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto raise_error; } /* Normalize to raise <class>, <instance> */ Py_DECREF(value); value = type; #if PY_VERSION_HEX < 0x02050000 if (PyInstance_Check(type)) { type = (PyObject*) ((PyInstanceObject*)type)->in_class; Py_INCREF(type); } else { type = 0; PyErr_SetString(PyExc_TypeError, "raise: exception must be an old-style class or instance"); goto raise_error; } #else type = (PyObject*) Py_TYPE(type); Py_INCREF(type); if (!PyType_IsSubtype((PyTypeObject *)type, (PyTypeObject *)PyExc_BaseException)) { PyErr_SetString(PyExc_TypeError, "raise: exception class must be a subclass of BaseException"); goto raise_error; } #endif } __Pyx_ErrRestore(type, value, tb); return; raise_error: Py_XDECREF(value); Py_XDECREF(type); Py_XDECREF(tb); return; }
static PyObject * green_throw(PyGreenlet *self, PyObject *args) { PyObject *typ = PyExc_GreenletExit; PyObject *val = NULL; PyObject *tb = NULL; if (!PyArg_ParseTuple(args, "|OOO:throw", &typ, &val, &tb)) { return NULL; } /* First, check the traceback argument, replacing None, with NULL */ if (tb == Py_None) { tb = NULL; } else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString( PyExc_TypeError, "throw() third argument must be a traceback object"); return NULL; } Py_INCREF(typ); Py_XINCREF(val); Py_XINCREF(tb); if (PyExceptionClass_Check(typ)) { PyErr_NormalizeException(&typ, &val, &tb); } else if (PyExceptionInstance_Check(typ)) { /* Raising an instance. The value should be a dummy. */ if (val && val != Py_None) { PyErr_SetString( PyExc_TypeError, "instance exception may not have a separate value"); goto failed_throw; } else { /* Normalize to raise <class>, <instance> */ Py_XDECREF(val); val = typ; typ = PyExceptionInstance_Class(typ); Py_INCREF(typ); } } else { /* Not something you can raise. throw() fails. */ PyErr_Format( PyExc_TypeError, "exceptions must be classes, or instances, not %s", Py_TYPE(typ)->tp_name); goto failed_throw; } return throw_greenlet(self, typ, val, tb); failed_throw: /* Didn't use our arguments, so restore their original refcounts */ Py_DECREF(typ); Py_XDECREF(val); Py_XDECREF(tb); return NULL; }
static PyObject * gen_throw(PyGenObject *gen, PyObject *args) { PyObject *typ; PyObject *tb = NULL; PyObject *val = NULL; PyObject *yf = _PyGen_yf(gen); _Py_IDENTIFIER(throw); if (!PyArg_UnpackTuple(args, "throw", 1, 3, &typ, &val, &tb)) return NULL; if (yf) { PyObject *ret; int err; if (PyErr_GivenExceptionMatches(typ, PyExc_GeneratorExit)) { gen->gi_running = 1; err = gen_close_iter(yf); gen->gi_running = 0; Py_DECREF(yf); if (err < 0) return gen_send_ex(gen, Py_None, 1, 0); goto throw_here; } if (PyGen_CheckExact(yf)) { gen->gi_running = 1; ret = gen_throw((PyGenObject *)yf, args); gen->gi_running = 0; } else { PyObject *meth = _PyObject_GetAttrId(yf, &PyId_throw); if (meth == NULL) { if (!PyErr_ExceptionMatches(PyExc_AttributeError)) { Py_DECREF(yf); return NULL; } PyErr_Clear(); Py_DECREF(yf); goto throw_here; } gen->gi_running = 1; ret = PyObject_CallObject(meth, args); gen->gi_running = 0; Py_DECREF(meth); } Py_DECREF(yf); if (!ret) { PyObject *val; /* Pop subiterator from stack */ ret = *(--gen->gi_frame->f_stacktop); assert(ret == yf); Py_DECREF(ret); /* Termination repetition of YIELD_FROM */ gen->gi_frame->f_lasti += 2; if (_PyGen_FetchStopIterationValue(&val) == 0) { ret = gen_send_ex(gen, val, 0, 0); Py_DECREF(val); } else { ret = gen_send_ex(gen, Py_None, 1, 0); } } return ret; } throw_here: /* First, check the traceback argument, replacing None with NULL. */ if (tb == Py_None) { tb = NULL; } else if (tb != NULL && !PyTraceBack_Check(tb)) { PyErr_SetString(PyExc_TypeError, "throw() third argument must be a traceback object"); return NULL; } Py_INCREF(typ); Py_XINCREF(val); Py_XINCREF(tb); if (PyExceptionClass_Check(typ)) PyErr_NormalizeException(&typ, &val, &tb); else if (PyExceptionInstance_Check(typ)) { /* Raising an instance. The value should be a dummy. */ if (val && val != Py_None) { PyErr_SetString(PyExc_TypeError, "instance exception may not have a separate value"); goto failed_throw; } else { /* Normalize to raise <class>, <instance> */ Py_XDECREF(val); val = typ; typ = PyExceptionInstance_Class(typ); Py_INCREF(typ); if (tb == NULL) /* Returns NULL if there's no traceback */ tb = PyException_GetTraceback(val); } } else { /* Not something you can raise. throw() fails. */ PyErr_Format(PyExc_TypeError, "exceptions must be classes or instances " "deriving from BaseException, not %s", Py_TYPE(typ)->tp_name); goto failed_throw; } PyErr_Restore(typ, val, tb); return gen_send_ex(gen, Py_None, 1, 0); failed_throw: /* Didn't use our arguments, so restore their original refcounts */ Py_DECREF(typ); Py_XDECREF(val); Py_XDECREF(tb); return NULL; }