From 8700b4281af0561d9aafd3cc14c44d79c2a0934b Mon Sep 17 00:00:00 2001 From: Guido van Rossum Date: Fri, 7 Sep 2001 20:20:11 +0000 Subject: PySequence_Check(), PyMapping_Check(): only return true if the corresponding "getitem" operation (sq_item or mp_subscript) is implemented. I realize that "sequence-ness" and "mapping-ness" are poorly defined (and the tests may still be wrong for user-defined instances, which always have both slots filled), but I believe that a sequence that doesn't support its getitem operation should not be considered a sequence. All other operations are optional though. For example, the ZODB BTree tests crashed because PySequence_Check() returned true for a dictionary! (In 2.2, the dictionary type has a tp_as_sequence pointer, but the only field filled is sq_contains, so you can write "if key in dict".) With this fix, all standalone ZODB tests succeed. --- Objects/abstract.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/Objects/abstract.c b/Objects/abstract.c index f7ade6d..c3a397c 100644 --- a/Objects/abstract.c +++ b/Objects/abstract.c @@ -919,7 +919,8 @@ PyNumber_Float(PyObject *o) int PySequence_Check(PyObject *s) { - return s != NULL && s->ob_type->tp_as_sequence; + return s != NULL && s->ob_type->tp_as_sequence && + s->ob_type->tp_as_sequence->sq_item != NULL; } int @@ -1509,7 +1510,8 @@ PySequence_Index(PyObject *s, PyObject *o) int PyMapping_Check(PyObject *o) { - return o && o->ob_type->tp_as_mapping; + return o && o->ob_type->tp_as_mapping && + o->ob_type->tp_as_mapping->mp_subscript; } int -- cgit v0.12