[pypy-svn] r25666 - in pypy/dist/pypy/rpython/rctypes: . test

arigo at codespeak.net arigo at codespeak.net
Mon Apr 10 17:03:03 CEST 2006


Author: arigo
Date: Mon Apr 10 17:03:02 2006
New Revision: 25666

Modified:
   pypy/dist/pypy/rpython/rctypes/rarray.py
   pypy/dist/pypy/rpython/rctypes/rmodel.py
   pypy/dist/pypy/rpython/rctypes/rpointer.py
   pypy/dist/pypy/rpython/rctypes/test/test_rpointer.py
Log:
Setting 'contents' and __setitem__ on ctypes pointers.


Modified: pypy/dist/pypy/rpython/rctypes/rarray.py
==============================================================================
--- pypy/dist/pypy/rpython/rctypes/rarray.py	(original)
+++ pypy/dist/pypy/rpython/rctypes/rarray.py	Mon Apr 10 17:03:02 2006
@@ -1,11 +1,10 @@
 from ctypes import ARRAY, c_int
 from pypy.annotation.model import SomeCTypesObject, SomeBuiltin
 from pypy.rpython import extregistry
-from pypy.rpython.rmodel import Repr, inputconst
+from pypy.rpython.rmodel import Repr, IntegerRepr, inputconst
 from pypy.rpython.lltypesystem import lltype
 from pypy.annotation.pairtype import pairtype
-from pypy.rpython.rmodel import IntegerRepr
-from pypy.rpython.rctypes.rmodel import CTypesRefRepr
+from pypy.rpython.rctypes.rmodel import CTypesRefRepr, reccopy
 
 ArrayType = type(ARRAY(c_int, 10))
 
@@ -46,25 +45,6 @@
         return r_array.r_item.return_c_data(hop.llops, v_c_data)
 
 
-def reccopy(llops, v_source, v_dest):
-    # helper (XXX move somewhere else) to copy recursively a structure
-    # or array onto another.
-    T = v_source.concretetype.TO
-    assert T == v_dest.concretetype.TO
-    assert isinstance(T, lltype.Struct)
-    for name in T._names:
-        FIELDTYPE = getattr(T, name)
-        cname = inputconst(lltype.Void, name)
-        if isinstance(FIELDTYPE, lltype.ContainerType):
-            RESTYPE = lltype.Ptr(FIELDTYPE)
-            v_subsrc = llops.genop('getsubstruct', [v_source, cname], RESTYPE)
-            v_subdst = llops.genop('getsubstruct', [v_dest,   cname], RESTYPE)
-            reccopy(llops, v_subsrc, v_subdst)
-        else:
-            v_value = llops.genop('getfield', [v_source, cname], FIELDTYPE)
-            llops.genop('setfield', [v_dest, cname, v_value])
-
-
 def arraytype_specialize_call(hop):
     r_array = hop.r_result
     return hop.genop("malloc", [

Modified: pypy/dist/pypy/rpython/rctypes/rmodel.py
==============================================================================
--- pypy/dist/pypy/rpython/rctypes/rmodel.py	(original)
+++ pypy/dist/pypy/rpython/rctypes/rmodel.py	Mon Apr 10 17:03:02 2006
@@ -203,3 +203,22 @@
         if isinstance(value, self.ctype):
             value = value.value
         p.c_data.value = value
+
+# ____________________________________________________________
+
+def reccopy(llops, v_source, v_dest):
+    # helper to copy recursively a structure or array onto another.
+    T = v_source.concretetype.TO
+    assert T == v_dest.concretetype.TO
+    assert isinstance(T, lltype.Struct)
+    for name in T._names:
+        FIELDTYPE = getattr(T, name)
+        cname = inputconst(lltype.Void, name)
+        if isinstance(FIELDTYPE, lltype.ContainerType):
+            RESTYPE = lltype.Ptr(FIELDTYPE)
+            v_subsrc = llops.genop('getsubstruct', [v_source, cname], RESTYPE)
+            v_subdst = llops.genop('getsubstruct', [v_dest,   cname], RESTYPE)
+            reccopy(llops, v_subsrc, v_subdst)
+        else:
+            v_value = llops.genop('getfield', [v_source, cname], FIELDTYPE)
+            llops.genop('setfield', [v_dest, cname, v_value])

Modified: pypy/dist/pypy/rpython/rctypes/rpointer.py
==============================================================================
--- pypy/dist/pypy/rpython/rctypes/rpointer.py	(original)
+++ pypy/dist/pypy/rpython/rctypes/rpointer.py	Mon Apr 10 17:03:02 2006
@@ -3,7 +3,7 @@
 from pypy.rpython.lltypesystem import lltype
 from pypy.annotation import model as annmodel
 from pypy.annotation.pairtype import pairtype
-from pypy.rpython.rctypes.rmodel import CTypesValueRepr
+from pypy.rpython.rctypes.rmodel import CTypesValueRepr, reccopy
 
 from ctypes import POINTER, pointer, c_int
 
@@ -37,6 +37,12 @@
         # an immortal global constant just like 'p', but better safe than sorry
         p.keepalive_contents = llcontents.c_data_owner_keepalive
 
+    def setcontents(self, llops, v_ptr, v_contentsbox):
+        v_c_data = self.r_contents.get_c_data(llops, v_contentsbox)
+        v_owner = self.r_contents.get_c_data_owner(llops, v_contentsbox)
+        self.setvalue(llops, v_ptr, v_c_data)
+        self.setkeepalive(llops, v_ptr, v_owner)
+
     def rtype_getattr(self, hop):
         s_attr = hop.args_s[1]
         assert s_attr.is_constant()
@@ -45,6 +51,14 @@
         v_c_ptr = self.getvalue(hop.llops, v_ptr)
         return self.r_contents.allocate_instance_ref(hop.llops, v_c_ptr)
 
+    def rtype_setattr(self, hop):
+        s_attr = hop.args_s[1]
+        assert s_attr.is_constant()
+        assert s_attr.const == 'contents'
+        v_ptr, v_attr, v_newcontents = hop.inputargs(self, lltype.Void,
+                                                     self.r_contents)
+        self.setcontents(hop.llops, v_ptr, v_newcontents)
+
 
 class __extend__(pairtype(PointerRepr, IntegerRepr)):
 
@@ -58,14 +72,19 @@
             raise NotImplementedError("XXX: pointer[non-zero-index]")
 
     def rtype_setitem((r_ptr, _), hop):
+        # p[0] = x  is not the same as  p.contents.value = x
+        # it makes a copy of the data in 'x' just like rarray.rtype_setitem()
         self = r_ptr
-        v_ptr, v_index, v_newvalue = hop.inputargs(self, lltype.Signed, XXX)
-                                                   
+        v_ptr, v_index, v_contentsbox = hop.inputargs(self, lltype.Signed,
+                                                      self.r_contents)
+        v_new_c_data = self.r_contents.get_c_data(hop.llops, v_contentsbox)
+        v_target = self.getvalue(hop.llops, v_ptr)
         if hop.args_s[1].is_constant() and hop.args_s[1].const == 0:
-            v_c_ptr = self.getvalue(hop. llops, v_ptr)
-            XXX
+            pass
         else:
             raise NotImplementedError("XXX: pointer[non-zero-index] = value")
+        # copy the whole structure's content over
+        reccopy(hop.llops, v_new_c_data, v_target)
 
 #def registerPointerType(ptrtype):
 #    """Adds a new pointer type to the extregistry.
@@ -155,10 +174,7 @@
     v_result = r_ptr.allocate_instance(hop.llops)
     if len(hop.args_s):
         v_contentsbox, = hop.inputargs(r_ptr.r_contents)
-        v_c_data = r_ptr.r_contents.get_c_data(hop.llops, v_contentsbox)
-        v_owner = r_ptr.r_contents.get_c_data_owner(hop.llops, v_contentsbox)
-        r_ptr.setvalue(hop.llops, v_result, v_c_data)
-        r_ptr.setkeepalive(hop.llops, v_result, v_owner)
+        r_ptr.setcontents(hop.llops, v_result, v_contentsbox)
     return v_result
 
 def pointerinstance_compute_annotation(type, instance):

Modified: pypy/dist/pypy/rpython/rctypes/test/test_rpointer.py
==============================================================================
--- pypy/dist/pypy/rpython/rctypes/test/test_rpointer.py	(original)
+++ pypy/dist/pypy/rpython/rctypes/test/test_rpointer.py	Mon Apr 10 17:03:02 2006
@@ -98,6 +98,23 @@
         if conftest.option.view:
             t.view()
 
+    def test_annotate_ass_contents(self):
+        def fn():
+            x = c_int(5)
+            y = c_int(6)
+            p = pointer(x)
+            p.contents = y
+            y.value = 12
+            return p.contents.value
+
+        t = TranslationContext()
+        a = t.buildannotator()
+        s = a.build_types(fn, [])
+        assert s.knowntype == int
+
+        if conftest.option.view:
+            t.view()
+
 
 class Test_specialization:
     def test_specialize_c_int_ptr(self):
@@ -174,13 +191,15 @@
         """
         Make sure that pointers work the same way as arrays.
         """
-        py.test.skip("in-progress")
         def access_array():
-            my_pointer = pointer(c_int(11))
+            my_int = c_int(11)
+            my_pointer = pointer(my_int)
             x = my_pointer[0]
             my_pointer[0] = c_int(7)
+            assert my_int.value == 7
             y = my_pointer[0]
             my_pointer[0] = 5
+            assert my_int.value == 5
             z = my_pointer.contents.value
             return x * y * z
 
@@ -197,3 +216,15 @@
 
         res = interpret(access_prebuilt, [])
         assert res == 11
+
+    def test_specialize_ass_contents(self):
+        def fn():
+            x = c_int(5)
+            y = c_int(6)
+            p = pointer(x)
+            p.contents = y
+            y.value = 12
+            return p.contents.value
+
+        res = interpret(fn, [])
+        assert res == 12



More information about the Pypy-commit mailing list