[pypy-svn] pypy reflex-support: short array returns and short ptr data member access
wlav
commits-noreply at bitbucket.org
Sat Feb 5 00:06:36 CET 2011
Author: Wim Lavrijsen <WLavrijsen at lbl.gov>
Branch: reflex-support
Changeset: r41619:34969598fd06
Date: 2011-02-04 14:35 -0800
http://bitbucket.org/pypy/pypy/changeset/34969598fd06/
Log: short array returns and short ptr data member access
diff --git a/pypy/module/cppyy/executor.py b/pypy/module/cppyy/executor.py
--- a/pypy/module/cppyy/executor.py
+++ b/pypy/module/cppyy/executor.py
@@ -1,6 +1,10 @@
+import sys
from pypy.rpython.lltypesystem import rffi, lltype
from pypy.rlib import libffi
+from pypy.module._rawffi.interp_rawffi import unpack_simple_shape
+from pypy.module._rawffi.array import W_Array
+
from pypy.module.cppyy import helper, capi
@@ -21,6 +25,10 @@
raise FastCallNotPossible
+class ArrayExecutor(FunctionExecutor):
+ _immutable_ = True
+
+
class VoidExecutor(FunctionExecutor):
_immutable_ = True
@@ -82,6 +90,7 @@
def execute_libffi(self, space, libffifunc, argchain):
return space.wrap(libffifunc.call(argchain, rffi.DOUBLE))
+
class CStringExecutor(FunctionExecutor):
_immutable_ = True
def execute(self, space, func, cppthis, num_args, args):
@@ -91,6 +100,15 @@
return space.wrap(result)
+class ShortArrayExecutor(ArrayExecutor):
+ _immutable_ = True
+ def execute(self, space, func, cppthis, num_args, args):
+ lresult = capi.c_call_l(func.cpptype.handle, func.method_index, cppthis, num_args, args)
+ spresult = rffi.cast(rffi.SHORTP, lresult)
+ arr = space.interp_w(W_Array, unpack_simple_shape(space, space.wrap('h')))
+ return arr.fromaddress(space, spresult, sys.maxint)
+
+
class InstancePtrExecutor(FunctionExecutor):
_immutable_ = True
def __init__(self, space, name, cpptype):
@@ -128,6 +146,7 @@
_executors["char"] = CharExecutor
_executors["unsigned char"] = CharExecutor
_executors["short int"] = ShortExecutor
+_executors["short int*"] = ShortArrayExecutor
_executors["unsigned short int"] = ShortExecutor
_executors["int"] = LongExecutor
_executors["unsigned int"] = LongExecutor
diff --git a/pypy/module/cppyy/test/test_datatypes.py b/pypy/module/cppyy/test/test_datatypes.py
--- a/pypy/module/cppyy/test/test_datatypes.py
+++ b/pypy/module/cppyy/test/test_datatypes.py
@@ -31,6 +31,84 @@
lib2 = cppyy.load_lib(self.shared_lib)
assert self.datatypes is lib2
+ def test1ReadAccess( self ):
+ """Test read access to instance public data and verify values"""
+
+ import cppyy, sys
+ cppyy_test_data = cppyy.gbl.cppyy_test_data
+
+ c = cppyy_test_data()
+ assert isinstance(c, cppyy_test_data)
+
+ # reading boolean type
+ assert c.m_bool == False
+
+ # reading char types
+ assert c.m_char == 'a'
+ assert c.m_uchar == 'c'
+
+ # reading integer types
+ assert c.m_short == -11
+ assert c.m_ushort == 11
+ assert c.m_int == -22
+ assert c.m_uint == 22
+ assert c.m_long == -33
+ assert c.m_ulong == 33
+
+ # reading floating point types
+ assert round(c.m_float + 44., 5) == 0
+ assert round(c.m_double + 55., 8) == 0
+
+ # reding of array types
+ for i in range(self.N):
+ # reading of integer array types
+ assert c.m_short_array[i] == -1*i
+ assert c.get_short_array()[i] == -1*i
+ assert c.m_short_array2[i] == -2*i
+ assert c.get_short_array2()[i] == -2*i
+ """
+ assert c.m_ushort_array[i] == 3*i
+ assert c.get_ushort_array()[i] == 3*i
+ assert c.m_ushort_array2[i] == 4*i
+ assert c.get_ushort_array2()[i] == 4*i
+ assert c.m_int_array[i] == -5*i
+ assert c.get_int_array()[i] == -5*i
+ assert c.m_int_array2[i] == -6*i
+ assert c.get_int_array2()[i] == -6*i
+ assert c.m_uint_array[i] == 7*i
+ assert c.get_uint_array()[i] == 7*i
+ assert c.m_uint_array2[i] == 8*i
+ assert c.get_uint_array2()[i] == 8*i
+
+ assert c.m_long_array[i] == -9*i
+ assert c.get_long_array()[i] == -9*i
+ assert c.m_long_array2[i] == -10*i
+ assert c.get_long_array2()[i] == -10*i
+ assert c.m_ulong_array[i] == 11*i
+ assert c.get_ulong_array()[i] == 11*i
+ assert c.m_ulong_array2[i] == 12*i
+ assert c.get_ulong_array2()[i] == 12*i
+
+ assert round(c.m_float_array[i] + 13.*i, 5) == 0
+ assert round(c.m_float_array2[i] + 14.*i, 5) == 0
+ assert round(c.m_double_array[i] + 15.*i, 8) == 0
+ assert round(c.m_double_array2[i] + 16.*i, 8) == 0
+ """
+
+ """
+ # out-of-bounds checks
+ raises(IndexError, c.m_short_array.__getitem__, self.N)
+ raises(IndexError, c.m_ushort_array.__getitem__, self.N)
+ raises(IndexError, c.m_int_array.__getitem__, self.N)
+ raises(IndexError, c.m_uint_array.__getitem__, self.N)
+ raises(IndexError, c.m_long_array.__getitem__, self.N)
+ raises(IndexError, c.m_ulong_array.__getitem__, self.N)
+ raises(IndexError, c.m_float_array.__getitem__, self.N)
+ raises(IndexError, c.m_double_array.__getitem__, self.N)
+ """
+
+ c.destruct()
+
def test2WriteAccess(self):
"""Test write access to instance public data and verify values"""
@@ -143,3 +221,5 @@
raises(TypeError, c.m_double, 'c')
raises(TypeError, c.m_int, -1.)
raises(TypeError, c.m_int, 1.)
+
+ c.destruct()
diff --git a/pypy/module/cppyy/converter.py b/pypy/module/cppyy/converter.py
--- a/pypy/module/cppyy/converter.py
+++ b/pypy/module/cppyy/converter.py
@@ -228,46 +228,61 @@
return rffi.cast(rffi.VOIDP, x)
-class ShortPtrConverter(ArrayTypeConverter):
+class ShortArrayConverter(ArrayTypeConverter):
_immutable_ = True
- def convert_argument(self, space, w_obj):
- assert 0, "not yet implemented"
-
def from_memory(self, space, w_obj, offset):
# read access, so no copy needed
fieldptr = self._get_fieldptr(space, w_obj, offset)
ptrval = rffi.cast(rffi.UINT, fieldptr)
arr = space.interp_w(W_Array, unpack_simple_shape(space, space.wrap('h')))
+ return arr.fromaddress(space, fieldptr, self.size)
+
+ def to_memory(self, space, w_obj, w_value, offset):
+ # copy the full array (uses byte copy for now)
+ fieldptr = self._get_fieldptr(space, w_obj, offset)
+ buf = space.interp_w(Buffer, w_value.getslotvalue(2))
+ # TODO: get sizeof(short) from system
+ for i in range(min(self.size*2, buf.getlength())):
+ fieldptr[i] = buf.getitem(i)
+
+class LongArrayConverter(ArrayTypeConverter):
+ _immutable_ = True
+ def from_memory(self, space, w_obj, offset):
+ # read access, so no copy needed
+ fieldptr = self._get_fieldptr(space, w_obj, offset)
+ ptrval = rffi.cast(rffi.UINT, fieldptr)
+ arr = space.interp_w(W_Array, unpack_simple_shape(space, space.wrap('l')))
return arr.fromaddress(space, ptrval, self.size)
def to_memory(self, space, w_obj, w_value, offset):
+ # copy the full array (uses byte copy for now)
+ fieldptr = self._get_fieldptr(space, w_obj, offset)
+ buf = space.interp_w(Buffer, w_value.getslotvalue(2))
+ # TODO: get sizeof(long) from system
+ for i in range(min(self.size*4, buf.getlength())):
+ fieldptr[i] = buf.getitem(i)
+
+
+class ShortPtrConverter(ShortArrayConverter):
+ _immutable_ = True
+ def _get_fieldptr(self, space, w_obj, offset):
+ fieldptr = TypeConverter._get_fieldptr(self, space, w_obj, offset)
+ ptrptr = rffi.cast(rffi.LONGP, fieldptr)
+ return ptrptr[0]
+
+ def to_memory(self, space, w_obj, w_value, offset):
# copy only the pointer value
rawobject = get_rawobject(space, w_obj)
byteptr = rffi.cast(rffi.LONGP, rawobject[offset])
# TODO: now what ... ?? AFAICS, w_value is a pure python list, not an array?
# byteptr[0] = space.unwrap(space.id(w_value.getslotvalue(2)))
-class ShortArrayConverter(ShortPtrConverter):
+class LongPtrConverter(LongArrayConverter):
_immutable_ = True
- def to_memory(self, space, w_obj, w_value, offset):
- # copy the full array (uses byte copy for now)
- fieldptr = self._get_fieldptr(space, w_obj, offset)
- buf = space.interp_w(Buffer, w_value.getslotvalue(2))
- # TODO: get sizeof(short) from system
- for i in range(min(self.size*2, buf.getlength())):
- fieldptr[i] = buf.getitem(i)
-
-class LongPtrConverter(ArrayTypeConverter):
- _immutable_ = True
- def convert_argument(self, space, w_obj):
- assert 0, "not yet implemented"
-
- def from_memory(self, space, w_obj, offset):
- # read access, so no copy needed
- fieldptr = self._get_fieldptr(space, w_obj, offset)
- ptrval = rffi.cast(rffi.UINT, fieldptr)
- arr = space.interp_w(W_Array, unpack_simple_shape(space, space.wrap('l')))
- return arr.fromaddress(space, ptrval, self.size)
+ def _get_fieldptr(self, space, w_obj, offset):
+ fieldptr = TypeConverter._get_fieldptr(self, space, w_obj, offset)
+ ptrptr = rffi.cast(rffi.LONGP, fieldptr)
+ return ptrptr[0]
def to_memory(self, space, w_obj, w_value, offset):
# copy only the pointer value
@@ -276,15 +291,6 @@
# TODO: now what ... ?? AFAICS, w_value is a pure python list, not an array?
# byteptr[0] = space.unwrap(space.id(w_value.getslotvalue(2)))
-class LongArrayConverter(LongPtrConverter):
- _immutable_ = True
- def to_memory(self, space, w_obj, w_value, offset):
- # copy the full array (uses byte copy for now)
- fieldptr = self._get_fieldptr(space, w_obj, offset)
- buf = space.interp_w(Buffer, w_value.getslotvalue(2))
- # TODO: get sizeof(long) from system
- for i in range(min(self.size*4, buf.getlength())):
- fieldptr[i] = buf.getitem(i)
class InstancePtrConverter(TypeConverter):
More information about the Pypy-commit
mailing list