@@ -3432,44 +3432,58 @@ list_richcompare_impl(PyObject *v, PyObject *w, int op)
34323432 Py_RETURN_TRUE ;
34333433 }
34343434
3435- /* Search for the first index where items are different */
3435+ /* Search for the first index where items are different.
3436+ * Keep vitem/witem alive across the break so that the final ordering
3437+ * comparison uses the same differing objects.
3438+ * This is required as PyObject_RichCompareBool may release the GIL and
3439+ * the list may be mutated in the meantime.
3440+ */
3441+ PyObject * vitem = NULL ;
3442+ PyObject * witem = NULL ;
34363443 for (i = 0 ; i < Py_SIZE (vl ) && i < Py_SIZE (wl ); i ++ ) {
3437- PyObject * vitem = vl -> ob_item [i ];
3438- PyObject * witem = wl -> ob_item [i ];
3444+ vitem = vl -> ob_item [i ];
3445+ witem = wl -> ob_item [i ];
34393446 if (vitem == witem ) {
34403447 continue ;
34413448 }
34423449
34433450 Py_INCREF (vitem );
34443451 Py_INCREF (witem );
34453452 int k = PyObject_RichCompareBool (vitem , witem , Py_EQ );
3446- Py_DECREF ( vitem );
3447- Py_DECREF (witem );
3448- if ( k < 0 )
3453+ if ( k < 0 ) {
3454+ Py_DECREF (vitem );
3455+ Py_DECREF ( witem );
34493456 return NULL ;
3450- if (!k )
3457+ }
3458+ if (!k ) {
3459+ /* keep vitem/witem alive for the final comparison */
34513460 break ;
3461+ }
3462+
3463+ Py_DECREF (vitem );
3464+ Py_DECREF (witem );
3465+ vitem = witem = NULL ;
34523466 }
34533467
3454- if (i >= Py_SIZE ( vl ) || i >= Py_SIZE ( wl ) ) {
3455- /* No more items to compare -- compare sizes */
3468+ if (vitem == NULL ) {
3469+ /* All compared elements were equal -- compare sizes */
34563470 Py_RETURN_RICHCOMPARE (Py_SIZE (vl ), Py_SIZE (wl ), op );
34573471 }
34583472
34593473 /* We have an item that differs -- shortcuts for EQ/NE */
34603474 if (op == Py_EQ ) {
3475+ Py_DECREF (vitem );
3476+ Py_DECREF (witem );
34613477 Py_RETURN_FALSE ;
34623478 }
34633479 if (op == Py_NE ) {
3480+ Py_DECREF (vitem );
3481+ Py_DECREF (witem );
34643482 Py_RETURN_TRUE ;
34653483 }
34663484
3467- /* Compare the final item again using the proper operator */
3468- PyObject * vitem = vl -> ob_item [i ];
3469- PyObject * witem = wl -> ob_item [i ];
3470- Py_INCREF (vitem );
3471- Py_INCREF (witem );
3472- PyObject * result = PyObject_RichCompare (vl -> ob_item [i ], wl -> ob_item [i ], op );
3485+ /* Compare the differing items using the proper operator */
3486+ PyObject * result = PyObject_RichCompare (vitem , witem , op );
34733487 Py_DECREF (vitem );
34743488 Py_DECREF (witem );
34753489 return result ;
0 commit comments