[pypy-commit] cffi slicing: More tests, small fixes

arigo noreply at buildbot.pypy.org
Sun Feb 10 15:27:39 CET 2013


Author: Armin Rigo <arigo at tunes.org>
Branch: slicing
Changeset: r1135:15cf69c6307c
Date: 2013-02-10 14:52 +0100
http://bitbucket.org/cffi/cffi/changeset/15cf69c6307c/

Log:	More tests, small fixes

diff --git a/c/_cffi_backend.c b/c/_cffi_backend.c
--- a/c/_cffi_backend.c
+++ b/c/_cffi_backend.c
@@ -1728,13 +1728,8 @@
 {
     Py_ssize_t start, stop;
     CDataObject_own_length *scd;
-    CTypeDescrObject *ct = cd->c_type;
-
-    if (!(ct->ct_flags & (CT_ARRAY | CT_POINTER))) {
-        PyErr_Format(PyExc_TypeError, "cdata of type '%s' cannot be indexed",
-                     ct->ct_name);
-        return NULL;
-    }
+    CTypeDescrObject *ct;
+
     start = PyInt_AsSsize_t(slice->start);
     if (start == -1 && PyErr_Occurred()) {
         if (slice->start == Py_None)
@@ -1756,9 +1751,28 @@
         return NULL;
     }
 
-    if (ct->ct_flags & CT_ARRAY)
+    ct = cd->c_type;
+    if (ct->ct_flags & CT_ARRAY) {
+        if (start < 0) {
+            PyErr_SetString(PyExc_IndexError,
+                            "negative index not supported");
+            return NULL;
+        }
+        if (stop >= get_array_length(cd)) {
+            PyErr_Format(PyExc_IndexError,
+                         "index too large for cdata '%s' (expected %zd < %zd)",
+                         cd->c_type->ct_name,
+                         stop, get_array_length(cd));
+            return NULL;
+        }
         ct = (CTypeDescrObject *)ct->ct_stuff;
-    assert(ct->ct_flags & CT_POINTER);
+    }
+    else if (!(ct->ct_flags & CT_POINTER)) {
+        PyErr_Format(PyExc_TypeError, "cdata of type '%s' cannot be indexed",
+                     ct->ct_name);
+        return NULL;
+    }
+
     if (ct->ct_stuff == NULL) {
         ct->ct_stuff = new_array_type(ct, Py_None);
         if (ct->ct_stuff == NULL)
diff --git a/c/test_c.py b/c/test_c.py
--- a/c/test_c.py
+++ b/c/test_c.py
@@ -2588,5 +2588,24 @@
     d[2] = 456
     assert c[1] == 123
     assert c[3] == 456
+    assert d[2] == 456
     py.test.raises(IndexError, "d[3]")
     py.test.raises(IndexError, "d[-1]")
+
+def test_slice_ptr():
+    BIntP = new_pointer_type(new_primitive_type("int"))
+    BIntArray = new_array_type(BIntP, None)
+    c = newp(BIntArray, 5)
+    d = (c+1)[0:2]
+    assert len(d) == 2
+    assert repr(d) == "<cdata 'int[]' sliced length 2>"
+    d[1] += 50
+    assert c[2] == 50
+
+def test_slice_array_checkbounds():
+    BIntP = new_pointer_type(new_primitive_type("int"))
+    BIntArray = new_array_type(BIntP, None)
+    c = newp(BIntArray, 5)
+    py.test.raises(IndexError, "c[-1:1]")
+    cp = c + 0
+    cp[-1:1]


More information about the pypy-commit mailing list