summaryrefslogtreecommitdiff
path: root/testing/cffi1/test_realize_c_type.py
diff options
context:
space:
mode:
Diffstat (limited to 'testing/cffi1/test_realize_c_type.py')
-rw-r--r--testing/cffi1/test_realize_c_type.py73
1 files changed, 73 insertions, 0 deletions
diff --git a/testing/cffi1/test_realize_c_type.py b/testing/cffi1/test_realize_c_type.py
new file mode 100644
index 0000000..a1f31e6
--- /dev/null
+++ b/testing/cffi1/test_realize_c_type.py
@@ -0,0 +1,73 @@
+import py, sys
+from cffi import cffi_opcode
+
+
+def check(input, expected_output=None, expected_ffi_error=False):
+ import _cffi_backend
+ ffi = _cffi_backend.FFI()
+ if not expected_ffi_error:
+ ct = ffi.typeof(input)
+ assert isinstance(ct, ffi.CType)
+ assert ct.cname == (expected_output or input)
+ else:
+ e = py.test.raises(ffi.error, ffi.typeof, input)
+ if isinstance(expected_ffi_error, str):
+ assert str(e.value) == expected_ffi_error
+
+def test_void():
+ check("void", "void")
+ check(" void ", "void")
+
+def test_int_star():
+ check("int")
+ check("int *")
+ check("int*", "int *")
+ check("long int", "long")
+ check("long")
+
+def test_noop():
+ check("int(*)", "int *")
+
+def test_array():
+ check("int[6]")
+
+def test_funcptr():
+ check("int(*)(long)")
+ check("int(long)", expected_ffi_error="the type 'int(long)' is a"
+ " function type, not a pointer-to-function type")
+ check("int(void)", expected_ffi_error="the type 'int()' is a"
+ " function type, not a pointer-to-function type")
+
+def test_funcptr_rewrite_args():
+ check("int(*)(int(int))", "int(*)(int(*)(int))")
+ check("int(*)(long[])", "int(*)(long *)")
+ check("int(*)(long[5])", "int(*)(long *)")
+
+def test_all_primitives():
+ for name in cffi_opcode.PRIMITIVE_TO_INDEX:
+ check(name, name)
+
+def check_func(input, expected_output=None):
+ import _cffi_backend
+ ffi = _cffi_backend.FFI()
+ ct = ffi.typeof(ffi.callback(input, lambda: None))
+ assert isinstance(ct, ffi.CType)
+ if sys.platform != 'win32' or sys.maxsize > 2**32:
+ expected_output = expected_output.replace('__stdcall *', '*')
+ assert ct.cname == expected_output
+
+def test_funcptr_stdcall():
+ check_func("int(int)", "int(*)(int)")
+ check_func("int foobar(int)", "int(*)(int)")
+ check_func("int __stdcall(int)", "int(__stdcall *)(int)")
+ check_func("int __stdcall foobar(int)", "int(__stdcall *)(int)")
+ check_func("void __cdecl(void)", "void(*)()")
+ check_func("void __cdecl foobar(void)", "void(*)()")
+ check_func("void __stdcall(void)", "void(__stdcall *)()")
+ check_func("void __stdcall foobar(long, short)",
+ "void(__stdcall *)(long, short)")
+ check_func("void(void __cdecl(void), void __stdcall(void))",
+ "void(*)(void(*)(), void(__stdcall *)())")
+
+def test_variadic_overrides_stdcall():
+ check("void (__stdcall*)(int, ...)", "void(*)(int, ...)")