Author: Armin Rigo <[email protected]>
Branch:
Changeset: r516:25c66b232182
Date: 2012-06-25 23:57 +0200
http://bitbucket.org/cffi/cffi/changeset/25c66b232182/
Log: Convert the front-end. Missing backend_ctypes.
diff --git a/c/_ffi_backend.c b/c/_ffi_backend.c
--- a/c/_ffi_backend.c
+++ b/c/_ffi_backend.c
@@ -1463,10 +1463,7 @@
PyObject *obj = PyTuple_GET_ITEM(args, i);
CTypeDescrObject *ct;
- if (obj == Py_None) {
- ct = NULL; /* stand for 'void *' */
- }
- else if (CData_Check(obj)) {
+ if (CData_Check(obj)) {
ct = ((CDataObject *)obj)->c_type;
if (ct->ct_flags & CT_ARRAY)
ct = (CTypeDescrObject *)ct->ct_stuff;
@@ -1506,11 +1503,7 @@
else
argtype = (CTypeDescrObject *)PyTuple_GET_ITEM(fvarargs, i);
- if (argtype == NULL) { /* stands for a NULL pointer */
- assert(obj == Py_None);
- *(char **)data = NULL;
- }
- else if ((argtype->ct_flags & CT_POINTER) &&
+ if ((argtype->ct_flags & CT_POINTER) &&
(argtype->ct_itemdescr->ct_flags & CT_PRIMITIVE_CHAR) &&
PyString_Check(obj)) {
/* special case: Python string -> cdata 'char *' */
diff --git a/c/test_c.py b/c/test_c.py
--- a/c/test_c.py
+++ b/c/test_c.py
@@ -129,6 +129,9 @@
assert type(int(cast(p, 'A'))) is int
assert type(long(cast(p, 'A'))) is long
assert str(cast(p, 'A')) == 'A'
+ assert repr(cast(p, 'A')) == "<cdata 'char' 'A'>"
+ assert repr(cast(p, 255)) == r"<cdata 'char' '\xff'>"
+ assert repr(cast(p, 0)) == r"<cdata 'char' '\x00'>"
def test_pointer_type():
p = new_primitive_type("int")
@@ -769,6 +772,7 @@
assert f(1, cast(BInt, 42)) == 42
assert f(2, cast(BInt, 40), cast(BInt, 2)) == 42
py.test.raises(TypeError, f, 1, 42)
+ py.test.raises(TypeError, f, 2, None)
def test_new_charp():
BChar = new_primitive_type("char")
diff --git a/cffi/api.py b/cffi/api.py
--- a/cffi/api.py
+++ b/cffi/api.py
@@ -64,6 +64,8 @@
equiv = 'signed %s'
lines.append('typedef %s %s;' % (equiv % by_size[size], name))
self.cdef('\n'.join(lines))
+ #
+ self.NULL = self.cast("void *", 0)
def cdef(self, csource):
"""Parse the given C source. This registers all declared functions,
diff --git a/testing/backend_tests.py b/testing/backend_tests.py
--- a/testing/backend_tests.py
+++ b/testing/backend_tests.py
@@ -146,10 +146,10 @@
def test_pointer_init(self):
ffi = FFI(backend=self.Backend())
n = ffi.new("int", 24)
- a = ffi.new("int *[10]", [None, None, n, n, None])
+ a = ffi.new("int *[10]", [ffi.NULL, ffi.NULL, n, n, ffi.NULL])
for i in range(10):
if i not in (2, 3):
- assert a[i] is None
+ assert a[i] == ffi.NULL
assert a[2] == a[3] == n
def test_cannot_cast(self):
@@ -178,8 +178,8 @@
assert p is not None
assert bool(p) is False
assert p == ffi.cast("int*", 0)
- assert p == ffi.cast("int*", None)
- assert p == None == p
+ assert p != None
+ assert repr(p) == "<cdata 'int *' NULL>"
a = ffi.new("int[]", [123, 456])
p = ffi.cast("int*", a)
assert bool(p) is True
@@ -193,10 +193,10 @@
ffi = FFI(backend=self.Backend())
ffi.cdef("struct foo { short a, b, c; };")
p = ffi.cast("unsigned short int", 0)
- assert repr(p) == "<cdata 'unsigned short'>"
+ assert repr(p) == "<cdata 'unsigned short' 0>"
assert repr(ffi.typeof(p)) == typerepr % "unsigned short"
p = ffi.cast("int*", 0)
- assert repr(p) == "<cdata 'int *'>"
+ assert repr(p) == "<cdata 'int *' NULL>"
assert repr(ffi.typeof(p)) == typerepr % "int *"
#
p = ffi.new("int")
@@ -218,22 +218,23 @@
assert repr(ffi.typeof(p)) == typerepr % "struct foo *"
#
q = ffi.cast("short", -123)
- assert repr(q) == "<cdata 'short'>"
+ assert repr(q) == "<cdata 'short' -123>"
assert repr(ffi.typeof(q)) == typerepr % "short"
p = ffi.new("int")
q = ffi.cast("short*", p)
- assert repr(q) == "<cdata 'short *'>"
+ assert repr(q).startswith("<cdata 'short *' 0x")
assert repr(ffi.typeof(q)) == typerepr % "short *"
p = ffi.new("int [2]")
q = ffi.cast("int*", p)
- assert repr(q) == "<cdata 'int *'>"
+ assert repr(q).startswith("<cdata 'int *' 0x")
assert repr(ffi.typeof(q)) == typerepr % "int *"
p = ffi.new("struct foo")
q = ffi.cast("struct foo *", p)
- assert repr(q) == "<cdata 'struct foo *'>"
+ assert repr(q).startswith("<cdata 'struct foo *' 0x")
assert repr(ffi.typeof(q)) == typerepr % "struct foo *"
+ prevrepr = repr(q)
q = q[0]
- assert repr(q) == "<cdata 'struct foo'>"
+ assert repr(q) == prevrepr.replace(' *', '')
assert repr(ffi.typeof(q)) == typerepr % "struct foo"
def test_new_array_of_array(self):
@@ -256,7 +257,7 @@
p = ffi.new("int*[4]")
p[3] = n
a = p[3]
- assert repr(a) == "<cdata 'int *'>"
+ assert repr(a).startswith("<cdata 'int *' 0x")
assert a[0] == 99
def test_new_array_of_pointer_2(self):
@@ -265,7 +266,7 @@
p = ffi.new("int*[4]")
p[3] = n
a = p[3]
- assert repr(a) == "<cdata 'int *'>"
+ assert repr(a).startswith("<cdata 'int *' 0x")
assert a[0] == 99
def test_char(self):
@@ -296,16 +297,20 @@
assert [p[i] for i in range(2)] == ['a', 'b']
py.test.raises(IndexError, ffi.new, "char[2]", "abc")
- def test_none_as_null(self):
+ def test_none_as_null_doesnt_work(self):
ffi = FFI(backend=self.Backend())
p = ffi.new("int*[1]")
- assert p[0] is None
+ assert p[0] is not None
+ assert p[0] != None
+ assert p[0] == ffi.NULL
+ assert repr(p[0]) == "<cdata 'int *' NULL>"
#
n = ffi.new("int", 99)
p = ffi.new("int*[]", [n])
assert p[0][0] == 99
- p[0] = None
- assert p[0] is None
+ py.test.raises(TypeError, "p[0] = None")
+ p[0] = ffi.NULL
+ assert p[0] == ffi.NULL
def test_float(self):
ffi = FFI(backend=self.Backend())
@@ -374,7 +379,7 @@
ffi = FFI(backend=self.Backend())
py.test.raises(TypeError, ffi.new, "struct baz")
p = ffi.new("struct baz *") # this works
- assert p[0] is None
+ assert p[0] == ffi.NULL
def test_pointer_to_struct(self):
ffi = FFI(backend=self.Backend())
@@ -439,7 +444,7 @@
ffi = FFI(backend=self.Backend())
py.test.raises(TypeError, ffi.new, "union baz")
u = ffi.new("union baz *") # this works
- assert u[0] is None
+ assert u[0] == ffi.NULL
def test_sizeof_type(self):
ffi = FFI(backend=self.Backend())
@@ -497,14 +502,15 @@
s = ffi.new("struct foo", [t])
assert type(s.name) is not str
assert str(s.name) == "testing"
- s.name = None
- assert s.name is None
+ py.test.raises(TypeError, "s.name = None")
+ s.name = ffi.NULL
+ assert s.name == ffi.NULL
def test_voidp(self):
ffi = FFI(backend=self.Backend())
py.test.raises(TypeError, ffi.new, "void")
p = ffi.new("void *")
- assert p[0] is None
+ assert p[0] == ffi.NULL
a = ffi.new("int[]", [10, 11, 12])
p = ffi.new("void *", a)
vp = p[0]
@@ -542,7 +548,7 @@
res = q[0](43)
assert res == 44
q = ffi.cast("int(*)(int)", p)
- assert repr(q) == "<cdata 'int(*)(int)'>"
+ assert repr(q).startswith("<cdata 'int(*)(int)' 0x")
res = q(45)
assert res == 46
@@ -554,40 +560,40 @@
def test_functionptr_voidptr_return(self):
ffi = FFI(backend=self.Backend())
def cb():
- return None
+ return ffi.NULL
p = ffi.callback("void*(*)()", cb)
res = p()
- assert res is None
+ assert res is not None
+ assert res == ffi.NULL
int_ptr = ffi.new('int')
void_ptr = ffi.cast('void*', int_ptr)
def cb():
return void_ptr
p = ffi.callback("void*(*)()", cb)
res = p()
- assert repr(res) == "<cdata 'void *'>"
- assert ffi.cast("long", res) != 0
+ assert res == void_ptr
def test_functionptr_intptr_return(self):
ffi = FFI(backend=self.Backend())
def cb():
- return None
+ return ffi.NULL
p = ffi.callback("int*(*)()", cb)
res = p()
- assert res is None
+ assert res == ffi.NULL
int_ptr = ffi.new('int')
def cb():
return int_ptr
p = ffi.callback("int*(*)()", cb)
res = p()
- assert repr(res) == "<cdata 'int *'>"
- assert ffi.cast("long", res) != 0
+ assert repr(res).startswith("<cdata 'int *' 0x")
+ assert res == int_ptr
int_array_ptr = ffi.new('int[1]')
def cb():
return int_array_ptr
p = ffi.callback("int*(*)()", cb)
res = p()
- assert repr(res) == "<cdata 'int *'>"
- assert ffi.cast("long", res) != 0
+ assert repr(res).startswith("<cdata 'int *' 0x")
+ assert res == int_array_ptr
def test_functionptr_void_return(self):
ffi = FFI(backend=self.Backend())
@@ -641,7 +647,7 @@
q = ffi.cast("short*", l1)
assert q == ffi.cast("short*", int(l1))
assert q[0] == 0x1234
- assert int(ffi.cast("intptr_t", None)) == 0
+ assert int(ffi.cast("intptr_t", ffi.NULL)) == 0
def test_cast_functionptr_and_int(self):
ffi = FFI(backend=self.Backend())
@@ -703,7 +709,7 @@
assert ffi.cast("enum bar", "B") != ffi.cast("enum bar", "B")
assert ffi.cast("enum foo", "A") != ffi.cast("enum bar", "A")
assert ffi.cast("enum bar", "A") != ffi.cast("int", 0)
- assert repr(ffi.cast("enum bar", "CC")) == "<cdata 'enum bar'>"
+ assert repr(ffi.cast("enum bar", "CC")) == "<cdata 'enum bar' 'CC'>"
def test_enum_in_struct(self):
ffi = FFI(backend=self.Backend())
diff --git a/testing/test_cdata.py b/testing/test_cdata.py
--- a/testing/test_cdata.py
+++ b/testing/test_cdata.py
@@ -15,6 +15,13 @@
def new_primitive_type(self, name):
return FakePrimitiveType(name)
+ def new_void_type(self):
+ return "void!"
+ def new_pointer_type(self, x):
+ return 'ptr-to-%r!' % (x,)
+ def cast(self, x, y):
+ return 'casted!'
+
class FakePrimitiveType(object):
def __init__(self, cdecl):
diff --git a/testing/test_function.py b/testing/test_function.py
--- a/testing/test_function.py
+++ b/testing/test_function.py
@@ -87,11 +87,11 @@
with FdWriteCapture() as fd:
ffi.C.puts("hello")
ffi.C.puts(" world")
- ffi.C.fflush(None)
+ ffi.C.fflush(ffi.NULL)
res = fd.getvalue()
assert res == 'hello\n world\n'
- def test_puts_wihtout_const(self):
+ def test_puts_without_const(self):
ffi = FFI(backend=self.Backend())
ffi.cdef("""
int puts(char *);
@@ -102,7 +102,7 @@
with FdWriteCapture() as fd:
ffi.C.puts("hello")
ffi.C.puts(" world")
- ffi.C.fflush(None)
+ ffi.C.fflush(ffi.NULL)
res = fd.getvalue()
assert res == 'hello\n world\n'
@@ -136,8 +136,8 @@
ffi.cast("int", 42),
ffi.cast("long", 84),
ffi.cast("long long", 168))
- ffi.C.printf("hello %p\n", None)
- ffi.C.fflush(None)
+ ffi.C.printf("hello %p\n", ffi.NULL)
+ ffi.C.fflush(ffi.NULL)
res = fd.getvalue()
if sys.platform == 'win32':
NIL = "00000000"
@@ -173,7 +173,7 @@
def test_function_pointer(self):
ffi = FFI(backend=self.Backend())
def cb(charp):
- assert repr(charp) == "<cdata 'char *'>"
+ assert repr(charp).startswith("<cdata 'char *' 0x")
return 42
fptr = ffi.callback("int(*)(const char *txt)", cb)
assert fptr != ffi.callback("int(*)(const char *)", cb)
@@ -188,10 +188,10 @@
ffi.C = ffi.dlopen(None)
fptr = ffi.cast("int(*)(const char *txt)", ffi.C.puts)
assert fptr == ffi.C.puts
- assert repr(fptr) == "<cdata 'int(*)(char *)'>"
+ assert repr(fptr).startswith("<cdata 'int(*)(char *)' 0x")
with FdWriteCapture() as fd:
fptr("world")
- ffi.C.fflush(None)
+ ffi.C.fflush(ffi.NULL)
res = fd.getvalue()
assert res == 'world\n'
@@ -216,8 +216,8 @@
ffi.C = ffi.dlopen(None)
pout = ffi.C.stdout
perr = ffi.C.stderr
- assert repr(pout) == "<cdata 'void *'>"
- assert repr(perr) == "<cdata 'void *'>"
+ assert repr(pout).startswith("<cdata 'void *' 0x")
+ assert repr(perr).startswith("<cdata 'void *' 0x")
with FdWriteCapture(2) as fd: # capturing stderr
ffi.C.stdout = perr
try:
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit