bpo-29935: Fixed error messages in the index() method of tuple and list (#887) (#907) (#910)
when pass indices of wrong type.
(cherry picked from commit d4edfc9abffca965e76ebc5957a92031a4d6c4d4)
(cherry picked from commit bf4bb2e43030661e568d5d4b046e8b9351cc164c)
diff --git a/Include/ceval.h b/Include/ceval.h
index 3735f00..f461601 100644
--- a/Include/ceval.h
+++ b/Include/ceval.h
@@ -145,6 +145,7 @@
#endif /* !WITH_THREAD */
PyAPI_FUNC(int) _PyEval_SliceIndex(PyObject *, Py_ssize_t *);
+PyAPI_FUNC(int) _PyEval_SliceIndexNotNone(PyObject *, Py_ssize_t *);
#ifdef __cplusplus
diff --git a/Misc/NEWS b/Misc/NEWS
index 8a07190..0ca08d6 100644
--- a/Misc/NEWS
+++ b/Misc/NEWS
@@ -10,6 +10,9 @@
Core and Builtins
-----------------
+- bpo-29935: Fixed error messages in the index() method of tuple and list
+ when pass indices of wrong type.
+
- bpo-28598: Support __rmod__ for subclasses of str being called before
str.__mod__. Patch by Martijn Pieters.
diff --git a/Objects/listobject.c b/Objects/listobject.c
index 8ee86c6..a71df7b 100644
--- a/Objects/listobject.c
+++ b/Objects/listobject.c
@@ -2284,8 +2284,8 @@
static PyObject *err_format = NULL;
if (!PyArg_ParseTuple(args, "O|O&O&:index", &v,
- _PyEval_SliceIndex, &start,
- _PyEval_SliceIndex, &stop))
+ _PyEval_SliceIndexNotNone, &start,
+ _PyEval_SliceIndexNotNone, &stop))
return NULL;
if (start < 0) {
start += Py_SIZE(self);
diff --git a/Objects/tupleobject.c b/Objects/tupleobject.c
index 550719f..2495e95 100644
--- a/Objects/tupleobject.c
+++ b/Objects/tupleobject.c
@@ -515,8 +515,8 @@
PyObject *v;
if (!PyArg_ParseTuple(args, "O|O&O&:index", &v,
- _PyEval_SliceIndex, &start,
- _PyEval_SliceIndex, &stop))
+ _PyEval_SliceIndexNotNone, &start,
+ _PyEval_SliceIndexNotNone, &stop))
return NULL;
if (start < 0) {
start += Py_SIZE(self);
diff --git a/Python/ceval.c b/Python/ceval.c
index 0983651..cea503e 100644
--- a/Python/ceval.c
+++ b/Python/ceval.c
@@ -4689,7 +4689,7 @@
int
_PyEval_SliceIndex(PyObject *v, Py_ssize_t *pi)
{
- if (v != NULL) {
+ if (v != NULL && v != Py_None) {
Py_ssize_t x;
if (PyInt_Check(v)) {
/* XXX(nnorwitz): I think PyInt_AS_LONG is correct,
@@ -4714,6 +4714,26 @@
return 1;
}
+int
+_PyEval_SliceIndexNotNone(PyObject *v, Py_ssize_t *pi)
+{
+ Py_ssize_t x;
+ if (PyIndex_Check(v)) {
+ x = PyNumber_AsSsize_t(v, NULL);
+ if (x == -1 && PyErr_Occurred())
+ return 0;
+ }
+ else {
+ PyErr_SetString(PyExc_TypeError,
+ "slice indices must be integers or "
+ "have an __index__ method");
+ return 0;
+ }
+ *pi = x;
+ return 1;
+}
+
+
#undef ISINDEX
#define ISINDEX(x) ((x) == NULL || \
PyInt_Check(x) || PyLong_Check(x) || PyIndex_Check(x))