Author: Armin Rigo <[email protected]>
Branch:
Changeset: r909:225281daefdf
Date: 2012-08-31 16:38 +0200
http://bitbucket.org/cffi/cffi/changeset/225281daefdf/
Log: Split (roughly) the code and the test. Use the 'p' prefix for
object descriptors (_P_ython) instead of 'i'.
diff --git a/demo/pyobj.py b/demo/pyobj.py
--- a/demo/pyobj.py
+++ b/demo/pyobj.py
@@ -1,6 +1,3 @@
-import api
-
-ffi = api.PythonFFI()
referents = [] # list "object descriptor -> python object"
freelist = None
@@ -8,20 +5,23 @@
def store(x):
"Store the object 'x' and returns a new object descriptor for it."
global freelist
- if freelist is None:
- i = len(referents)
+ p = freelist
+ if p is None:
+ p = len(referents)
referents.append(x)
else:
- i = freelist
- freelist = referents[freelist]
- referents[i] = x
- return i
+ freelist = referents[p]
+ referents[p] = x
+ return p
-def discard(i):
- "Discard (i.e. close) the object descriptor 'i'."
+def discard(p):
+ """Discard (i.e. close) the object descriptor 'p'.
+ Return the original object that was attached to 'p'."""
global freelist
- referents[i] = freelist
- freelist = i
+ x = referents[p]
+ referents[p] = freelist
+ freelist = p
+ return x
class Ref(object):
"""For use in 'with Ref(x) as ob': open an object descriptor
@@ -30,91 +30,95 @@
def __init__(self, x):
self.x = x
def __enter__(self):
- self.i = i = store(self.x)
- return i
+ self.p = p = store(self.x)
+ return p
def __exit__(self, *args):
- discard(self.i)
+ discard(self.p)
def count_pyobj_alive():
result = len(referents)
- i = freelist
- while i is not None:
+ p = freelist
+ while p is not None:
assert result > 0
result -= 1
- i = referents[i]
+ p = referents[p]
return result
# ------------------------------------------------------------
-ffi.cdef("""
- typedef int pyobj_t;
- int sum_integers(pyobj_t oblist);
- pyobj_t sum_objects(pyobj_t oblist, pyobj_t obinitial);
-""")
+if __name__ == '__main__':
+ import api
[email protected]("int(pyobj_t)")
-def length(oblist):
- list = referents[oblist]
- return len(list)
+ ffi = api.PythonFFI()
[email protected]("int(pyobj_t, int)")
-def getitem(oblist, index):
- list = referents[oblist]
- return list[index]
+ ffi.cdef("""
+ typedef int pyobj_t;
+ int sum_integers(pyobj_t p_list);
+ pyobj_t sum_objects(pyobj_t p_list, pyobj_t p_initial);
+ """)
[email protected]("pyobj_t(pyobj_t)")
-def pyobj_dup(ob):
- return store(referents[ob])
+ @ffi.pyexport("int(pyobj_t)")
+ def length(p_list):
+ list = referents[p_list]
+ return len(list)
[email protected]("void(pyobj_t)")
-def pyobj_close(ob):
- discard(ob)
+ @ffi.pyexport("int(pyobj_t, int)")
+ def getitem(p_list, index):
+ list = referents[p_list]
+ return list[index]
[email protected]("pyobj_t(pyobj_t, int)")
-def pyobj_getitem(oblist, index):
- list = referents[oblist]
- return store(list[index])
+ @ffi.pyexport("pyobj_t(pyobj_t)")
+ def pyobj_dup(p):
+ return store(referents[p])
[email protected]("pyobj_t(pyobj_t, pyobj_t)")
-def pyobj_add(ob1, ob2):
- return store(referents[ob1] + referents[ob2])
+ @ffi.pyexport("void(pyobj_t)")
+ def pyobj_close(p):
+ discard(p)
-lib = ffi.verify("""
- typedef int pyobj_t; /* an "object descriptor" number */
+ @ffi.pyexport("pyobj_t(pyobj_t, int)")
+ def pyobj_getitem(p_list, index):
+ list = referents[p_list]
+ return store(list[index])
- int sum_integers(pyobj_t oblist) {
- /* this a demo function written in C, using the API
- defined above: length() and getitem(). */
- int i, result = 0;
- int count = length(oblist);
- for (i=0; i<count; i++) {
- int n = getitem(oblist, i);
- result += n;
+ @ffi.pyexport("pyobj_t(pyobj_t, pyobj_t)")
+ def pyobj_add(p1, p2):
+ return store(referents[p1] + referents[p2])
+
+ lib = ffi.verify("""
+ typedef int pyobj_t; /* an "object descriptor" number */
+
+ int sum_integers(pyobj_t p_list) {
+ /* this a demo function written in C, using the API
+ defined above: length() and getitem(). */
+ int i, result = 0;
+ int count = length(p_list);
+ for (i=0; i<count; i++) {
+ int n = getitem(p_list, i);
+ result += n;
+ }
+ return result;
}
- return result;
- }
- pyobj_t sum_objects(pyobj_t oblist, pyobj_t obinitial) {
- /* same as above, but keeps all additions as Python objects */
- int i;
- int count = length(oblist);
- pyobj_t ob = pyobj_dup(obinitial);
- for (i=0; i<count; i++) {
- pyobj_t ob2 = pyobj_getitem(oblist, i);
- pyobj_t ob3 = pyobj_add(ob, ob2);
- pyobj_close(ob2);
- pyobj_close(ob);
- ob = ob3;
+ pyobj_t sum_objects(pyobj_t p_list, pyobj_t p_initial) {
+ /* same as above, but keeps all additions as Python objects */
+ int i;
+ int count = length(p_list);
+ pyobj_t p1 = pyobj_dup(p_initial);
+ for (i=0; i<count; i++) {
+ pyobj_t p2 = pyobj_getitem(p_list, i);
+ pyobj_t p3 = pyobj_add(p1, p2);
+ pyobj_close(p2);
+ pyobj_close(p1);
+ p1 = p3;
+ }
+ return p1;
}
- return ob;
- }
-""")
+ """)
-with Ref([10, 20, 30, 40]) as oblist:
- print lib.sum_integers(oblist)
- with Ref(0) as obinitial:
- obresult = lib.sum_objects(oblist, obinitial)
- print referents[obresult]
- discard(obresult)
+ with Ref([10, 20, 30, 40]) as p_list:
+ print lib.sum_integers(p_list)
+ with Ref(5) as p_initial:
+ result = discard(lib.sum_objects(p_list, p_initial))
+ print result
-assert not count_pyobj_alive()
+ assert count_pyobj_alive() == 0
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit