summaryrefslogtreecommitdiffstats
path: root/Python/pythonrun.c
diff options
context:
space:
mode:
authorSerhiy Storchaka <storchaka@gmail.com>2025-02-25 22:50:26 (GMT)
committerGitHub <noreply@github.com>2025-02-25 22:50:26 (GMT)
commit7c1b76fce8c8df00da38830f72dbdde6881a33be (patch)
tree9cd84f09c2434b7f89feb631dd6be134096d8550 /Python/pythonrun.c
parentb0d3f4919579cb02c46918f47ea4faa2e5d304fc (diff)
downloadcpython-7c1b76fce8c8df00da38830f72dbdde6881a33be.zip
cpython-7c1b76fce8c8df00da38830f72dbdde6881a33be.tar.gz
cpython-7c1b76fce8c8df00da38830f72dbdde6881a33be.tar.bz2
[3.13] gh-130163: Fix crashes related to PySys_GetObject() (GH-130503) (GH-130556)
The use of PySys_GetObject() and _PySys_GetAttr(), which return a borrowed reference, has been replaced by using one of the following functions, which return a strong reference and distinguish a missing attribute from an error: _PySys_GetOptionalAttr(), _PySys_GetOptionalAttrString(), _PySys_GetRequiredAttr(), and _PySys_GetRequiredAttrString(). (cherry picked from commit 0ef4ffeefd1737c18dc9326133c7894d58108c2e)
Diffstat (limited to 'Python/pythonrun.c')
-rw-r--r--Python/pythonrun.c98
1 files changed, 71 insertions, 27 deletions
diff --git a/Python/pythonrun.c b/Python/pythonrun.c
index f9daf81..2092f3a 100644
--- a/Python/pythonrun.c
+++ b/Python/pythonrun.c
@@ -109,17 +109,35 @@ _PyRun_InteractiveLoopObject(FILE *fp, PyObject *filename, PyCompilerFlags *flag
flags = &local_flags;
}
- PyThreadState *tstate = _PyThreadState_GET();
- PyObject *v = _PySys_GetAttr(tstate, &_Py_ID(ps1));
+ PyObject *v;
+ if (_PySys_GetOptionalAttr(&_Py_ID(ps1), &v) < 0) {
+ PyErr_Print();
+ return -1;
+ }
if (v == NULL) {
- _PySys_SetAttr(&_Py_ID(ps1), v = PyUnicode_FromString(">>> "));
- Py_XDECREF(v);
+ v = PyUnicode_FromString(">>> ");
+ if (v == NULL) {
+ PyErr_Clear();
+ }
+ if (_PySys_SetAttr(&_Py_ID(ps1), v) < 0) {
+ PyErr_Clear();
+ }
+ }
+ Py_XDECREF(v);
+ if (_PySys_GetOptionalAttr(&_Py_ID(ps2), &v) < 0) {
+ PyErr_Print();
+ return -1;
}
- v = _PySys_GetAttr(tstate, &_Py_ID(ps2));
if (v == NULL) {
- _PySys_SetAttr(&_Py_ID(ps2), v = PyUnicode_FromString("... "));
- Py_XDECREF(v);
+ v = PyUnicode_FromString("... ");
+ if (v == NULL) {
+ PyErr_Clear();
+ }
+ if (_PySys_SetAttr(&_Py_ID(ps2), v) < 0) {
+ PyErr_Clear();
+ }
}
+ Py_XDECREF(v);
#ifdef Py_REF_DEBUG
int show_ref_count = _Py_GetConfig()->show_ref_count;
@@ -179,31 +197,37 @@ pyrun_one_parse_ast(FILE *fp, PyObject *filename,
PyCompilerFlags *flags, PyArena *arena,
mod_ty *pmod, PyObject** interactive_src)
{
- PyThreadState *tstate = _PyThreadState_GET();
-
// Get sys.stdin.encoding (as UTF-8)
- PyObject *attr; // borrowed ref
+ PyObject *attr;
PyObject *encoding_obj = NULL;
const char *encoding = NULL;
if (fp == stdin) {
- attr = _PySys_GetAttr(tstate, &_Py_ID(stdin));
- if (attr && attr != Py_None) {
- encoding_obj = PyObject_GetAttr(attr, &_Py_ID(encoding));
- if (encoding_obj) {
+ if (_PySys_GetOptionalAttr(&_Py_ID(stdin), &attr) < 0) {
+ PyErr_Clear();
+ }
+ else if (attr != NULL && attr != Py_None) {
+ if (PyObject_GetOptionalAttr(attr, &_Py_ID(encoding), &encoding_obj) < 0) {
+ PyErr_Clear();
+ }
+ else if (encoding_obj && PyUnicode_Check(encoding_obj)) {
encoding = PyUnicode_AsUTF8(encoding_obj);
if (!encoding) {
PyErr_Clear();
}
}
}
+ Py_XDECREF(attr);
}
// Get sys.ps1 (as UTF-8)
- attr = _PySys_GetAttr(tstate, &_Py_ID(ps1));
PyObject *ps1_obj = NULL;
const char *ps1 = "";
- if (attr != NULL) {
+ if (_PySys_GetOptionalAttr(&_Py_ID(ps1), &attr) < 0) {
+ PyErr_Clear();
+ }
+ else if (attr != NULL) {
ps1_obj = PyObject_Str(attr);
+ Py_DECREF(attr);
if (ps1_obj == NULL) {
PyErr_Clear();
}
@@ -217,11 +241,14 @@ pyrun_one_parse_ast(FILE *fp, PyObject *filename,
}
// Get sys.ps2 (as UTF-8)
- attr = _PySys_GetAttr(tstate, &_Py_ID(ps2));
PyObject *ps2_obj = NULL;
const char *ps2 = "";
- if (attr != NULL) {
+ if (_PySys_GetOptionalAttr(&_Py_ID(ps2), &attr) < 0) {
+ PyErr_Clear();
+ }
+ else if (attr != NULL) {
ps2_obj = PyObject_Str(attr);
+ Py_DECREF(attr);
if (ps2_obj == NULL) {
PyErr_Clear();
}
@@ -621,9 +648,11 @@ _Py_HandleSystemExit(int *exitcode_p)
Py_SETREF(exc, code);
}
- PyThreadState *tstate = _PyThreadState_GET();
- PyObject *sys_stderr = _PySys_GetAttr(tstate, &_Py_ID(stderr));
- if (sys_stderr != NULL && sys_stderr != Py_None) {
+ PyObject *sys_stderr;
+ if (_PySys_GetOptionalAttr(&_Py_ID(stderr), &sys_stderr) < 0) {
+ PyErr_Clear();
+ }
+ else if (sys_stderr != NULL && sys_stderr != Py_None) {
if (PyFile_WriteObject(exc, sys_stderr, Py_PRINT_RAW) < 0) {
PyErr_Clear();
}
@@ -635,6 +664,7 @@ _Py_HandleSystemExit(int *exitcode_p)
fflush(stderr);
}
PySys_WriteStderr("\n");
+ Py_XDECREF(sys_stderr);
Py_CLEAR(exc);
*exitcode_p = 1;
return 1;
@@ -654,7 +684,7 @@ handle_system_exit(void)
static void
_PyErr_PrintEx(PyThreadState *tstate, int set_sys_last_vars)
{
- PyObject *typ = NULL, *tb = NULL;
+ PyObject *typ = NULL, *tb = NULL, *hook = NULL;
handle_system_exit();
PyObject *exc = _PyErr_GetRaisedException(tstate);
@@ -683,7 +713,9 @@ _PyErr_PrintEx(PyThreadState *tstate, int set_sys_last_vars)
_PyErr_Clear(tstate);
}
}
- PyObject *hook = _PySys_GetAttr(tstate, &_Py_ID(excepthook));
+ if (_PySys_GetOptionalAttr(&_Py_ID(excepthook), &hook) < 0) {
+ PyErr_Clear();
+ }
if (_PySys_Audit(tstate, "sys.excepthook", "OOOO", hook ? hook : Py_None,
typ, exc, tb) < 0) {
if (PyErr_ExceptionMatches(PyExc_RuntimeError)) {
@@ -717,6 +749,7 @@ _PyErr_PrintEx(PyThreadState *tstate, int set_sys_last_vars)
}
done:
+ Py_XDECREF(hook);
Py_XDECREF(typ);
Py_XDECREF(exc);
Py_XDECREF(tb);
@@ -1165,17 +1198,24 @@ fallback:
void
PyErr_Display(PyObject *unused, PyObject *value, PyObject *tb)
{
- PyThreadState *tstate = _PyThreadState_GET();
- PyObject *file = _PySys_GetAttr(tstate, &_Py_ID(stderr));
+ PyObject *file;
+ if (_PySys_GetOptionalAttr(&_Py_ID(stderr), &file) < 0) {
+ PyObject *exc = PyErr_GetRaisedException();
+ _PyObject_Dump(value);
+ fprintf(stderr, "lost sys.stderr\n");
+ _PyObject_Dump(exc);
+ Py_DECREF(exc);
+ return;
+ }
if (file == NULL) {
_PyObject_Dump(value);
fprintf(stderr, "lost sys.stderr\n");
return;
}
if (file == Py_None) {
+ Py_DECREF(file);
return;
}
- Py_INCREF(file);
_PyErr_Display(file, NULL, value, tb);
Py_DECREF(file);
}
@@ -1282,11 +1322,15 @@ PyRun_FileExFlags(FILE *fp, const char *filename, int start, PyObject *globals,
static void
flush_io_stream(PyThreadState *tstate, PyObject *name)
{
- PyObject *f = _PySys_GetAttr(tstate, name);
+ PyObject *f;
+ if (_PySys_GetOptionalAttr(name, &f) < 0) {
+ PyErr_Clear();
+ }
if (f != NULL) {
if (_PyFile_Flush(f) < 0) {
PyErr_Clear();
}
+ Py_DECREF(f);
}
}