[pypy-commit] cffi cpy-extension: Implemented as a hack: be strict about the field types, except

arigo noreply at buildbot.pypy.org
Wed Jun 13 17:38:50 CEST 2012


Author: Armin Rigo <arigo at tunes.org>
Branch: cpy-extension
Changeset: r306:01c1190d4ece
Date: 2012-06-13 17:38 +0200
http://bitbucket.org/cffi/cffi/changeset/01c1190d4ece/

Log:	Implemented as a hack: be strict about the field types, except for
	integer types, where as long as it has the correct size it is fine.
	(Exact rule subject to change)

diff --git a/cffi/model.py b/cffi/model.py
--- a/cffi/model.py
+++ b/cffi/model.py
@@ -48,6 +48,12 @@
     def get_c_name(self, replace_with=''):
         return self.name + replace_with
 
+    def is_integer_type(self):
+        return not self.is_float_type()
+
+    def is_float_type(self):
+        return self.name in ('double', 'float')
+
     def new_backend_type(self, ffi):
         return ffi._backend.new_primitive_type(self.name)
 
diff --git a/cffi/verifier.py b/cffi/verifier.py
--- a/cffi/verifier.py
+++ b/cffi/verifier.py
@@ -229,6 +229,22 @@
         prnt('  };')
         prnt('  return _cffi_get_struct_layout(nums);')
         prnt('}')
+        prnt()
+        prnt('static void _cffi_check_%s(struct %s *p)' % (name, name))
+        prnt('{')
+        prnt('  /* only to generate compile-time warnings or errors */')
+        for i in range(len(tp.fldnames)):
+            fname = tp.fldnames[i]
+            ftype = tp.fldtypes[i]
+            if (isinstance(ftype, model.PrimitiveType)
+                and ftype.is_integer_type()):
+                # accept all integers, but complain on float or double
+                prnt('  (p->%s) << 1;' % fname)
+            else:
+                # only accept exactly the type declared
+                prnt('  { %s = &p->%s; }' % (
+                    ftype.get_c_name('* tmp'), fname))
+        prnt('}')
 
     def generate_cpy_struct_method(self, tp, name):
         self.prnt('  {"_cffi_struct_%s", _cffi_struct_%s, METH_NOARGS},' % (
diff --git a/testing/test_verify.py b/testing/test_verify.py
--- a/testing/test_verify.py
+++ b/testing/test_verify.py
@@ -203,3 +203,11 @@
 def test_struct_signedness_ignored():
     _check_field_match("int", "unsigned int", expect_mismatch=False)
     _check_field_match("unsigned short", "signed short", expect_mismatch=False)
+
+def test_struct_float_vs_int():
+    for typename in all_signed_integer_types:
+        for real in all_float_types:
+            _check_field_match(typename, real, expect_mismatch=True)
+    for typename in all_float_types:
+        for real in all_signed_integer_types:
+            _check_field_match(typename, real, expect_mismatch=True)


More information about the pypy-commit mailing list