[pypy-svn] r45317 - in pypy/dist/pypy/rpython/lltypesystem: . test
arigo at codespeak.net
arigo at codespeak.net
Wed Jul 25 12:12:18 CEST 2007
Author: arigo
Date: Wed Jul 25 12:12:17 2007
New Revision: 45317
Modified:
pypy/dist/pypy/rpython/lltypesystem/ll2ctypes.py
pypy/dist/pypy/rpython/lltypesystem/test/test_ll2ctypes.py
Log:
ll2ctypes support for inlined substructures.
Modified: pypy/dist/pypy/rpython/lltypesystem/ll2ctypes.py
==============================================================================
--- pypy/dist/pypy/rpython/lltypesystem/ll2ctypes.py (original)
+++ pypy/dist/pypy/rpython/lltypesystem/ll2ctypes.py Wed Jul 25 12:12:17 2007
@@ -150,20 +150,40 @@
return cls
-def convert_struct(container):
+def convert_struct(container, cstruct=None):
STRUCT = container._TYPE
- cls = get_ctypes_type(STRUCT)
- cstruct = cls._malloc()
+ if cstruct is None:
+ # if 'container' is an inlined substructure, convert the whole
+ # bigger structure at once
+ parent, parentindex = lltype.parentlink(container)
+ if parent is not None:
+ convert_struct(parent)
+ return
+ # regular case: allocate a new ctypes Structure of the proper type
+ cls = get_ctypes_type(STRUCT)
+ cstruct = cls._malloc()
add_storage(container, _struct_mixin, cstruct)
for field_name in STRUCT._names:
+ FIELDTYPE = getattr(STRUCT, field_name)
field_value = getattr(container, field_name)
- setattr(cstruct, field_name, lltype2ctypes(field_value))
+ if not isinstance(FIELDTYPE, lltype.ContainerType):
+ # regular field
+ setattr(cstruct, field_name, lltype2ctypes(field_value))
+ else:
+ # inlined substructure/subarray
+ if isinstance(FIELDTYPE, lltype.Struct):
+ csubstruct = getattr(cstruct, field_name)
+ convert_struct(field_value, csubstruct)
+ else:
+ raise NotImplementedError('inlined field', FIELDTYPE)
remove_regular_struct_content(container)
def remove_regular_struct_content(container):
STRUCT = container._TYPE
for field_name in STRUCT._names:
- delattr(container, field_name)
+ FIELDTYPE = getattr(STRUCT, field_name)
+ if not isinstance(FIELDTYPE, lltype.ContainerType):
+ delattr(container, field_name)
def convert_array(container):
ARRAY = container._TYPE
Modified: pypy/dist/pypy/rpython/lltypesystem/test/test_ll2ctypes.py
==============================================================================
--- pypy/dist/pypy/rpython/lltypesystem/test/test_ll2ctypes.py (original)
+++ pypy/dist/pypy/rpython/lltypesystem/test/test_ll2ctypes.py Wed Jul 25 12:12:17 2007
@@ -371,4 +371,36 @@
checkval(sc.contents.y, 'l')
def test_substructures(self):
- py.test.skip("XXX test and implement substructures")
+ S1 = lltype.Struct('S1', ('x', lltype.Signed))
+ BIG = lltype.Struct('BIG', ('s1a', S1), ('s1b', S1))
+ s = lltype.malloc(BIG, flavor='raw')
+ s.s1a.x = 123
+ s.s1b.x = 456
+ sc = lltype2ctypes(s)
+ assert sc.contents.s1a.x == 123
+ assert sc.contents.s1b.x == 456
+ sc.contents.s1a.x += 1
+ sc.contents.s1b.x += 10
+ assert s.s1a.x == 124
+ assert s.s1b.x == 466
+ s.s1a.x += 3
+ s.s1b.x += 30
+ assert sc.contents.s1a.x == 127
+ assert sc.contents.s1b.x == 496
+ lltype.free(s, flavor='raw')
+
+ s = lltype.malloc(BIG, flavor='raw')
+ s1ac = lltype2ctypes(s.s1a)
+ s1ac.contents.x = 53
+ sc = lltype2ctypes(s)
+ assert sc.contents.s1a.x == 53
+ sc.contents.s1a.x += 1
+ assert s1ac.contents.x == 54
+ assert s.s1a.x == 54
+ s.s1a.x += 2
+ assert s1ac.contents.x == 56
+ assert sc.contents.s1a.x == 56
+ sc.contents.s1a.x += 3
+ assert s1ac.contents.x == 59
+ assert s.s1a.x == 59
+ lltype.free(s, flavor='raw')
More information about the Pypy-commit
mailing list