Skip to content

Commit be72e78

Browse files
committed
gh-144984: Address review: use Py_NewRef(self) for parent, add setUpClass
1 parent 4b45e07 commit be72e78

File tree

2 files changed

+13
-16
lines changed

2 files changed

+13
-16
lines changed

Lib/test/test_pyexpat.py

Lines changed: 9 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -831,23 +831,28 @@ class ExternalEntityParserCreateErrorTest(unittest.TestCase):
831831
See https://github.com/python/cpython/issues/144984.
832832
"""
833833

834+
@classmethod
835+
def setUpClass(cls):
836+
cls._testcapi = import_helper.import_module('_testcapi')
837+
834838
def test_error_path_no_crash(self):
835839
# When an allocation inside ExternalEntityParserCreate fails,
836840
# the partially-initialized subparser is deallocated. This
837841
# must not dereference NULL handlers or double-decrement the
838842
# parent parser's refcount.
839-
_testcapi = import_helper.import_module('_testcapi')
840843
parser = expat.ParserCreate()
841844
parser.buffer_text = True
842845
rc_before = sys.getrefcount(parser)
843846

844-
_testcapi.set_nomemory(1, 10)
847+
self._testcapi.set_nomemory(1, 10)
848+
raised = False
845849
try:
846850
parser.ExternalEntityParserCreate(None)
847851
except MemoryError:
848-
pass
852+
raised = True
849853
finally:
850-
_testcapi.remove_mem_hooks()
854+
self._testcapi.remove_mem_hooks()
855+
self.assertTrue(raised, "MemoryError not raised")
851856

852857
rc_after = sys.getrefcount(parser)
853858
self.assertEqual(rc_after, rc_before)

Modules/pyexpat.c

Lines changed: 4 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1076,11 +1076,6 @@ pyexpat_xmlparser_ExternalEntityParserCreate_impl(xmlparseobject *self,
10761076
return NULL;
10771077
}
10781078

1079-
// The new subparser will make use of the parent XML_Parser inside of Expat.
1080-
// So we need to take subparsers into account with the reference counting
1081-
// of their parent parser.
1082-
Py_INCREF(self);
1083-
10841079
new_parser->buffer_size = self->buffer_size;
10851080
new_parser->buffer_used = 0;
10861081
new_parser->buffer = NULL;
@@ -1090,23 +1085,22 @@ pyexpat_xmlparser_ExternalEntityParserCreate_impl(xmlparseobject *self,
10901085
new_parser->ns_prefixes = self->ns_prefixes;
10911086
new_parser->itself = XML_ExternalEntityParserCreate(self->itself, context,
10921087
encoding);
1093-
new_parser->parent = (PyObject *)self;
1088+
// The new subparser will make use of the parent XML_Parser inside of Expat.
1089+
// So we need to take subparsers into account with the reference counting
1090+
// of their parent parser.
1091+
new_parser->parent = Py_NewRef(self);
10941092
new_parser->handlers = 0;
10951093
new_parser->intern = Py_XNewRef(self->intern);
10961094

10971095
if (self->buffer != NULL) {
10981096
new_parser->buffer = PyMem_Malloc(new_parser->buffer_size);
10991097
if (new_parser->buffer == NULL) {
1100-
new_parser->parent = NULL;
11011098
Py_DECREF(new_parser);
1102-
Py_DECREF(self);
11031099
return PyErr_NoMemory();
11041100
}
11051101
}
11061102
if (!new_parser->itself) {
1107-
new_parser->parent = NULL;
11081103
Py_DECREF(new_parser);
1109-
Py_DECREF(self);
11101104
return PyErr_NoMemory();
11111105
}
11121106

@@ -1119,9 +1113,7 @@ pyexpat_xmlparser_ExternalEntityParserCreate_impl(xmlparseobject *self,
11191113

11201114
new_parser->handlers = PyMem_New(PyObject *, i);
11211115
if (!new_parser->handlers) {
1122-
new_parser->parent = NULL;
11231116
Py_DECREF(new_parser);
1124-
Py_DECREF(self);
11251117
return PyErr_NoMemory();
11261118
}
11271119
clear_handlers(new_parser, 1);

0 commit comments

Comments
 (0)