mirror of https://github.com/python/cpython
gh-102192: Replace PyErr_Fetch/Restore etc by more efficient alternatives (#102816)
This commit is contained in:
parent
3adb23a17d
commit
ad77b80b05
|
@ -778,9 +778,7 @@ dummy_func(
|
||||||
}
|
}
|
||||||
assert(exc && PyExceptionInstance_Check(exc));
|
assert(exc && PyExceptionInstance_Check(exc));
|
||||||
Py_INCREF(exc);
|
Py_INCREF(exc);
|
||||||
PyObject *typ = Py_NewRef(PyExceptionInstance_Class(exc));
|
_PyErr_SetRaisedException(tstate, exc);
|
||||||
PyObject *tb = PyException_GetTraceback(exc);
|
|
||||||
_PyErr_Restore(tstate, typ, exc, tb);
|
|
||||||
goto exception_unwind;
|
goto exception_unwind;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -791,9 +789,7 @@ dummy_func(
|
||||||
}
|
}
|
||||||
else {
|
else {
|
||||||
Py_INCREF(exc);
|
Py_INCREF(exc);
|
||||||
PyObject *typ = Py_NewRef(PyExceptionInstance_Class(exc));
|
_PyErr_SetRaisedException(tstate, exc);
|
||||||
PyObject *tb = PyException_GetTraceback(exc);
|
|
||||||
_PyErr_Restore(tstate, typ, exc, tb);
|
|
||||||
goto exception_unwind;
|
goto exception_unwind;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -389,8 +389,7 @@ PyImport_AddModule(const char *name)
|
||||||
static void
|
static void
|
||||||
remove_module(PyThreadState *tstate, PyObject *name)
|
remove_module(PyThreadState *tstate, PyObject *name)
|
||||||
{
|
{
|
||||||
PyObject *type, *value, *traceback;
|
PyObject *exc = _PyErr_GetRaisedException(tstate);
|
||||||
_PyErr_Fetch(tstate, &type, &value, &traceback);
|
|
||||||
|
|
||||||
PyObject *modules = MODULES(tstate->interp);
|
PyObject *modules = MODULES(tstate->interp);
|
||||||
if (PyDict_CheckExact(modules)) {
|
if (PyDict_CheckExact(modules)) {
|
||||||
|
@ -403,7 +402,7 @@ remove_module(PyThreadState *tstate, PyObject *name)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
_PyErr_ChainExceptions(type, value, traceback);
|
_PyErr_ChainExceptions1(exc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -2324,32 +2323,34 @@ remove_importlib_frames(PyThreadState *tstate)
|
||||||
const char *remove_frames = "_call_with_frames_removed";
|
const char *remove_frames = "_call_with_frames_removed";
|
||||||
int always_trim = 0;
|
int always_trim = 0;
|
||||||
int in_importlib = 0;
|
int in_importlib = 0;
|
||||||
PyObject *exception, *value, *base_tb, *tb;
|
|
||||||
PyObject **prev_link, **outer_link = NULL;
|
PyObject **prev_link, **outer_link = NULL;
|
||||||
|
PyObject *base_tb = NULL;
|
||||||
|
|
||||||
/* Synopsis: if it's an ImportError, we trim all importlib chunks
|
/* Synopsis: if it's an ImportError, we trim all importlib chunks
|
||||||
from the traceback. We always trim chunks
|
from the traceback. We always trim chunks
|
||||||
which end with a call to "_call_with_frames_removed". */
|
which end with a call to "_call_with_frames_removed". */
|
||||||
|
|
||||||
_PyErr_Fetch(tstate, &exception, &value, &base_tb);
|
PyObject *exc = _PyErr_GetRaisedException(tstate);
|
||||||
if (!exception || _PyInterpreterState_GetConfig(tstate->interp)->verbose) {
|
if (exc == NULL || _PyInterpreterState_GetConfig(tstate->interp)->verbose) {
|
||||||
goto done;
|
goto done;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (PyType_IsSubtype((PyTypeObject *) exception,
|
if (PyType_IsSubtype(Py_TYPE(exc), (PyTypeObject *) PyExc_ImportError)) {
|
||||||
(PyTypeObject *) PyExc_ImportError))
|
|
||||||
always_trim = 1;
|
always_trim = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
assert(PyExceptionInstance_Check(exc));
|
||||||
|
base_tb = PyException_GetTraceback(exc);
|
||||||
prev_link = &base_tb;
|
prev_link = &base_tb;
|
||||||
tb = base_tb;
|
PyObject *tb = base_tb;
|
||||||
while (tb != NULL) {
|
while (tb != NULL) {
|
||||||
|
assert(PyTraceBack_Check(tb));
|
||||||
PyTracebackObject *traceback = (PyTracebackObject *)tb;
|
PyTracebackObject *traceback = (PyTracebackObject *)tb;
|
||||||
PyObject *next = (PyObject *) traceback->tb_next;
|
PyObject *next = (PyObject *) traceback->tb_next;
|
||||||
PyFrameObject *frame = traceback->tb_frame;
|
PyFrameObject *frame = traceback->tb_frame;
|
||||||
PyCodeObject *code = PyFrame_GetCode(frame);
|
PyCodeObject *code = PyFrame_GetCode(frame);
|
||||||
int now_in_importlib;
|
int now_in_importlib;
|
||||||
|
|
||||||
assert(PyTraceBack_Check(tb));
|
|
||||||
now_in_importlib = _PyUnicode_EqualToASCIIString(code->co_filename, importlib_filename) ||
|
now_in_importlib = _PyUnicode_EqualToASCIIString(code->co_filename, importlib_filename) ||
|
||||||
_PyUnicode_EqualToASCIIString(code->co_filename, external_filename);
|
_PyUnicode_EqualToASCIIString(code->co_filename, external_filename);
|
||||||
if (now_in_importlib && !in_importlib) {
|
if (now_in_importlib && !in_importlib) {
|
||||||
|
@ -2370,15 +2371,14 @@ remove_importlib_frames(PyThreadState *tstate)
|
||||||
Py_DECREF(code);
|
Py_DECREF(code);
|
||||||
tb = next;
|
tb = next;
|
||||||
}
|
}
|
||||||
assert(PyExceptionInstance_Check(value));
|
|
||||||
assert((PyObject *)Py_TYPE(value) == exception);
|
|
||||||
if (base_tb == NULL) {
|
if (base_tb == NULL) {
|
||||||
base_tb = Py_None;
|
base_tb = Py_None;
|
||||||
Py_INCREF(Py_None);
|
Py_INCREF(Py_None);
|
||||||
}
|
}
|
||||||
PyException_SetTraceback(value, base_tb);
|
PyException_SetTraceback(exc, base_tb);
|
||||||
done:
|
done:
|
||||||
_PyErr_Restore(tstate, exception, value, base_tb);
|
Py_XDECREF(base_tb);
|
||||||
|
_PyErr_SetRaisedException(tstate, exc);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -18,7 +18,7 @@
|
||||||
#include "pycore_interp.h" // PyInterpreterState.importlib
|
#include "pycore_interp.h" // PyInterpreterState.importlib
|
||||||
#include "pycore_object.h" // _PyDebug_PrintTotalRefs()
|
#include "pycore_object.h" // _PyDebug_PrintTotalRefs()
|
||||||
#include "pycore_parser.h" // _PyParser_ASTFromString()
|
#include "pycore_parser.h" // _PyParser_ASTFromString()
|
||||||
#include "pycore_pyerrors.h" // _PyErr_Fetch, _Py_Offer_Suggestions
|
#include "pycore_pyerrors.h" // _PyErr_GetRaisedException, _Py_Offer_Suggestions
|
||||||
#include "pycore_pylifecycle.h" // _Py_UnhandledKeyboardInterrupt
|
#include "pycore_pylifecycle.h" // _Py_UnhandledKeyboardInterrupt
|
||||||
#include "pycore_pystate.h" // _PyInterpreterState_GET()
|
#include "pycore_pystate.h" // _PyInterpreterState_GET()
|
||||||
#include "pycore_sysmodule.h" // _PySys_Audit()
|
#include "pycore_sysmodule.h" // _PySys_Audit()
|
||||||
|
|
Loading…
Reference in New Issue