[pypy-commit] pypy cpyext-ext: add missing methods, test

mattip pypy.commits at gmail.com
Fri Apr 1 10:24:55 EDT 2016


Author: mattip <matti.picus at gmail.com>
Branch: cpyext-ext
Changeset: r83495:8f34e1689105
Date: 2016-04-01 10:01 +0300
http://bitbucket.org/pypy/pypy/changeset/8f34e1689105/

Log:	add missing methods, test

diff --git a/pypy/module/cpyext/sequence.py b/pypy/module/cpyext/sequence.py
--- a/pypy/module/cpyext/sequence.py
+++ b/pypy/module/cpyext/sequence.py
@@ -1,12 +1,13 @@
 
-from rpython.rlib import rerased
+from rpython.rlib import rerased, jit
 from pypy.interpreter.error import OperationError, oefmt
-from pypy.objspace.std.listobject import ListStrategy
+from pypy.objspace.std.listobject import (
+    ListStrategy, UNROLL_CUTOFF, W_ListObject, ObjectListStrategy)
 from pypy.module.cpyext.api import (
     cpython_api, CANNOT_FAIL, CONST_STRING, Py_ssize_t, PyObject, PyObjectP)
 from pypy.module.cpyext.pyobject import PyObject, make_ref, from_ref
 from rpython.rtyper.lltypesystem import rffi, lltype
-from pypy.objspace.std import listobject, tupleobject
+from pypy.objspace.std import tupleobject
 
 from pypy.module.cpyext.tupleobject import PyTuple_Check, PyTuple_SetItem
 from pypy.module.cpyext.object import Py_IncRef, Py_DecRef
@@ -44,12 +45,12 @@
     which case o is returned.  Use PySequence_Fast_GET_ITEM() to access the
     members of the result.  Returns NULL on failure.  If the object is not a
     sequence, raises TypeError with m as the message text."""
-    if isinstance(w_obj, listobject.W_ListObject):
+    if isinstance(w_obj, W_ListObject):
         # make sure we can return a borrowed obj from PySequence_Fast_GET_ITEM    
         w_obj.convert_to_cpy_strategy(space)
         return w_obj
     try:
-        return listobject.W_ListObject.newlist_cpyext(space, space.listview(w_obj))
+        return W_ListObject.newlist_cpyext(space, space.listview(w_obj))
     except OperationError:
         raise OperationError(space.w_TypeError, space.wrap(rffi.charp2str(m)))
 
@@ -58,7 +59,7 @@
     """Return the ith element of o, assuming that o was returned by
     PySequence_Fast(), o is not NULL, and that i is within bounds.
     """
-    if isinstance(w_obj, listobject.W_ListObject):
+    if isinstance(w_obj, W_ListObject):
         return w_obj.getitem(index)
     elif isinstance(w_obj, tupleobject.W_TupleObject):
         return w_obj.wrappeditems[index]
@@ -72,7 +73,7 @@
     gotten by calling PySequence_Size() on o, but
     PySequence_Fast_GET_SIZE() is faster because it can assume o is a list
     or tuple."""
-    if isinstance(w_obj, listobject.W_ListObject):
+    if isinstance(w_obj, W_ListObject):
         return w_obj.length()
     elif isinstance(w_obj, tupleobject.W_TupleObject):
         return len(w_obj.wrappeditems)
@@ -88,7 +89,7 @@
     So, only use the underlying array pointer in contexts where the sequence
     cannot change.
     """
-    if isinstance(w_obj, listobject.W_ListObject):
+    if isinstance(w_obj, W_ListObject):
         cpy_strategy = space.fromcache(CPyListStrategy)
         if w_obj.strategy is cpy_strategy:
             return w_obj.get_raw_items() # asserts it's a cpyext strategy
@@ -276,9 +277,20 @@
     #------------------------------------------
     # all these methods fail or switch strategy and then call ListObjectStrategy's method
         
+    @jit.unroll_safe
+    def getitems_unroll(self, w_list):
+        storage = self.unerase(w_list.lstorage)
+        retval = [None] * storage._length
+        for i in range(storage._length):
+            retval[i] = from_ref(w_list.space, storage._elems[i])
+        return retval
+
+    @jit.look_inside_iff(lambda self, w_list:
+            jit.loop_unrolling_heuristic(w_list, w_list.length(),
+                                         UNROLL_CUTOFF))
     def getitems_fixedsize(self, w_list):
-        raise NotImplementedError
-        
+        return self.getitems_unroll(w_list)
+
     def setslice(self, w_list, start, stop, step, length):
         #storage = self.unerase(w_list.lstorage)
         raise NotImplementedError
@@ -290,8 +302,12 @@
         raise NotImplementedError
 
     def clone(self, w_list):
-        raise NotImplementedError
-
+        storage = w_list.lstorage  # lstorage is tuple, no need to clone
+        w_clone = W_ListObject.from_storage_and_strategy(self.space, storage,
+                                                         self)
+        w_clone.switch_to_object_strategy()
+        return w_clone
+        
     def copy_into(self, w_list, w_other):
         raise NotImplementedError
 
diff --git a/pypy/module/cpyext/test/test_sequence.py b/pypy/module/cpyext/test/test_sequence.py
--- a/pypy/module/cpyext/test/test_sequence.py
+++ b/pypy/module/cpyext/test/test_sequence.py
@@ -178,6 +178,19 @@
         assert space.int_w(space.len(w_l)) == 5
         assert space.int_w(space.getitem(w_l, w(0))) == 0
 
+        api.PySequence_Fast(w_l, "foo") # converts
+        w_t = space.wrap(space.fixedview(w_l))
+        assert space.int_w(space.len(w_t)) == 5
+        assert space.int_w(space.getitem(w_t, w(0))) == 0
+        w_l2 = space.wrap(space.listview(w_t))
+        assert space.int_w(space.len(w_l2)) == 5
+        assert space.int_w(space.getitem(w_l2, w(0))) == 0
+
+        api.PySequence_Fast(w_l, "foo") # converts
+        w_sum = space.add(w_l, w_l)
+        assert space.int_w(space.len(w_sum)) == 10
+
+
 class XAppTestSequenceObject(AppTestCpythonExtensionBase):
     def test_sequenceobject(self):
         module = self.import_extension('foo', [


More information about the pypy-commit mailing list