Skip to content

Commit 32d1d4a

Browse files
committed
Reapply tests and the crash fix added in pythongh-135225 and rolled back to avoid
bytecode changes in 3.13.
1 parent 6ae5158 commit 32d1d4a

File tree

4 files changed

+61
-13
lines changed

4 files changed

+61
-13
lines changed

Lib/test/test_generators.py

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -274,11 +274,16 @@ def gen(it):
274274
yield x
275275
return gen(range(10))
276276

277-
def process_tests(self, get_generator):
277+
def process_tests(self, get_generator, is_expr):
278+
err_iterator = "'.*' object is not an iterator"
279+
err_iterable = "'.*' object is not iterable"
278280
for obj in self.iterables:
279281
g_obj = get_generator(obj)
280282
with self.subTest(g_obj=g_obj, obj=obj):
281-
self.assertListEqual(list(g_obj), list(obj))
283+
if is_expr:
284+
self.assertRaisesRegex(TypeError, err_iterator, list, g_obj)
285+
else:
286+
self.assertListEqual(list(g_obj), list(obj))
282287

283288
g_iter = get_generator(iter(obj))
284289
with self.subTest(g_iter=g_iter, obj=obj):
@@ -288,7 +293,8 @@ def process_tests(self, get_generator):
288293
for obj in self.non_iterables:
289294
g_obj = get_generator(obj)
290295
with self.subTest(g_obj=g_obj):
291-
self.assertRaisesRegex(TypeError, err_regex, list, g_obj)
296+
err = err_iterator if is_expr else err_iterable
297+
self.assertRaisesRegex(TypeError, err, list, g_obj)
292298

293299
def test_modify_f_locals(self):
294300
def modify_f_locals(g, local, obj):
@@ -301,8 +307,8 @@ def get_generator_genexpr(obj):
301307
def get_generator_genfunc(obj):
302308
return modify_f_locals(self.genfunc(), 'it', obj)
303309

304-
self.process_tests(get_generator_genexpr)
305-
self.process_tests(get_generator_genfunc)
310+
self.process_tests(get_generator_genexpr, True)
311+
self.process_tests(get_generator_genfunc, False)
306312

307313
def test_new_gen_from_gi_code(self):
308314
def new_gen_from_gi_code(g, obj):
@@ -315,8 +321,8 @@ def get_generator_genexpr(obj):
315321
def get_generator_genfunc(obj):
316322
return new_gen_from_gi_code(self.genfunc(), obj)
317323

318-
self.process_tests(get_generator_genexpr)
319-
self.process_tests(get_generator_genfunc)
324+
self.process_tests(get_generator_genexpr, True)
325+
self.process_tests(get_generator_genfunc, False)
320326

321327

322328
class ExceptionTest(unittest.TestCase):

Python/bytecodes.c

Lines changed: 24 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -2599,7 +2599,14 @@ dummy_func(
25992599

26002600
replaced op(_FOR_ITER, (iter -- iter, next)) {
26012601
/* before: [iter]; after: [iter, iter()] *or* [] (and jump over END_FOR.) */
2602-
next = (*Py_TYPE(iter)->tp_iternext)(iter);
2602+
iternextfunc func = Py_TYPE(iter)->tp_iternext;
2603+
if (func == NULL) {
2604+
_PyErr_Format(tstate, PyExc_TypeError,
2605+
"'%.100s' object is not an iterator",
2606+
Py_TYPE(iter)->tp_name);
2607+
ERROR_NO_POP();
2608+
}
2609+
next = func(iter);
26032610
if (next == NULL) {
26042611
if (_PyErr_Occurred(tstate)) {
26052612
if (!_PyErr_ExceptionMatches(tstate, PyExc_StopIteration)) {
@@ -2622,7 +2629,14 @@ dummy_func(
26222629

26232630
op(_FOR_ITER_TIER_TWO, (iter -- iter, next)) {
26242631
/* before: [iter]; after: [iter, iter()] *or* [] (and jump over END_FOR.) */
2625-
next = (*Py_TYPE(iter)->tp_iternext)(iter);
2632+
iternextfunc func = Py_TYPE(iter)->tp_iternext;
2633+
if (func == NULL) {
2634+
_PyErr_Format(tstate, PyExc_TypeError,
2635+
"'%.100s' object is not an iterator",
2636+
Py_TYPE(iter)->tp_name);
2637+
ERROR_NO_POP();
2638+
}
2639+
next = func(iter);
26262640
if (next == NULL) {
26272641
if (_PyErr_Occurred(tstate)) {
26282642
if (!_PyErr_ExceptionMatches(tstate, PyExc_StopIteration)) {
@@ -2643,7 +2657,14 @@ dummy_func(
26432657
inst(INSTRUMENTED_FOR_ITER, (unused/1 -- )) {
26442658
_Py_CODEUNIT *target;
26452659
PyObject *iter = TOP();
2646-
PyObject *next = (*Py_TYPE(iter)->tp_iternext)(iter);
2660+
iternextfunc func = Py_TYPE(iter)->tp_iternext;
2661+
if (func == NULL) {
2662+
_PyErr_Format(tstate, PyExc_TypeError,
2663+
"'%.100s' object is not an iterator",
2664+
Py_TYPE(iter)->tp_name);
2665+
ERROR_NO_POP();
2666+
}
2667+
PyObject *next = func(iter);
26472668
if (next != NULL) {
26482669
PUSH(next);
26492670
target = next_instr;

Python/executor_cases.c.h

Lines changed: 8 additions & 1 deletion
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Python/generated_cases.c.h

Lines changed: 16 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

0 commit comments

Comments
 (0)