[pypy-svn] r72636 - pypy/branch/cpython-extension/pypy/module/cpyext

afa at codespeak.net afa at codespeak.net
Tue Mar 23 17:09:21 CET 2010


Author: afa
Date: Tue Mar 23 17:09:19 2010
New Revision: 72636

Modified:
   pypy/branch/cpython-extension/pypy/module/cpyext/TODO
   pypy/branch/cpython-extension/pypy/module/cpyext/api.py
   pypy/branch/cpython-extension/pypy/module/cpyext/macros.py
Log:
Py_INCREF and Py_DECREF don't need to access the pypy object in the standard case
Remove support for "borrowed" references, needs more thinking


Modified: pypy/branch/cpython-extension/pypy/module/cpyext/TODO
==============================================================================
--- pypy/branch/cpython-extension/pypy/module/cpyext/TODO	(original)
+++ pypy/branch/cpython-extension/pypy/module/cpyext/TODO	Tue Mar 23 17:09:19 2010
@@ -2,6 +2,10 @@
  - Implement C API.
  - Complete the PyTypeObject initialization code.
  - Free pto.c_tp_name correctly
+ - properly support "borrowed" references: the PyObject must be stored
+   somewhere
+ - lltype.free in PyObject_Del() sometimes raise an exception (but all
+   tests pass)
 
 PyStringObject support
 ======================

Modified: pypy/branch/cpython-extension/pypy/module/cpyext/api.py
==============================================================================
--- pypy/branch/cpython-extension/pypy/module/cpyext/api.py	(original)
+++ pypy/branch/cpython-extension/pypy/module/cpyext/api.py	Tue Mar 23 17:09:19 2010
@@ -65,15 +65,28 @@
     def decorate(func):
         api_function = ApiFunction(argtypes, restype, func, borrowed)
         FUNCTIONS[func.func_name] = api_function
+
         def unwrapper(space, *args):
+            "NOT_RPYTHON: XXX unsure"
             newargs = []
+            to_decref = []
             for i, arg in enumerate(args):
                 if api_function.argtypes[i] is PyObject:
                     if (isinstance(arg, W_Root) and
                         not api_function.argnames[i].startswith('w_')):
                         arg = make_ref(space, arg)
+                        to_decref.append(arg)
+                    elif (not isinstance(arg, W_Root) and
+                          api_function.argnames[i].startswith('w_')):
+                        arg = from_ref(space, arg)
                 newargs.append(arg)
-            return func(space, *newargs)
+            try:
+                return func(space, *newargs)
+            finally:
+                from pypy.module.cpyext.macros import Py_DECREF
+                for arg in to_decref:
+                    Py_DECREF(space, arg)
+
         func.api_func = api_function
         unwrapper.api_func = api_function
         return unwrapper
@@ -175,8 +188,9 @@
         py_obj = rffi.cast(PyObject, py_obj)
         state.py_objects_w2r[w_obj] = py_obj
         state.py_objects_r2w[ptr] = w_obj
-    elif not borrowed:
+    else:
         py_obj.c_obj_refcnt += 1
+    # XXX borrowed references?
     return py_obj
 
 def from_ref(space, ref):

Modified: pypy/branch/cpython-extension/pypy/module/cpyext/macros.py
==============================================================================
--- pypy/branch/cpython-extension/pypy/module/cpyext/macros.py	(original)
+++ pypy/branch/cpython-extension/pypy/module/cpyext/macros.py	Tue Mar 23 17:09:19 2010
@@ -6,35 +6,29 @@
 
 # XXX Optimize these functions and put them into macro definitions
 @cpython_api([PyObject], lltype.Void)
-def Py_DECREF(space, w_obj):
-    print "DECREF", w_obj
-    state = space.fromcache(State)
-    obj = state.py_objects_w2r[w_obj]
+def Py_DECREF(space, obj):
     obj.c_obj_refcnt -= 1
     if obj.c_obj_refcnt == 0:
+        state = space.fromcache(State)
         ptr = ctypes.addressof(obj._obj._storage)
-        _Py_Dealloc(space, w_obj)
+        w_obj = state.py_objects_r2w.pop(ptr)
+        _Py_Dealloc(space, obj)
         del state.py_objects_w2r[w_obj]
-        del state.py_objects_r2w[ptr]
     else:
         assert obj.c_obj_refcnt > 0
-    return
 
 @cpython_api([PyObject], lltype.Void)
 def Py_INCREF(space, obj):
     obj.c_obj_refcnt += 1
 
 
-def _Py_Dealloc(space, w_obj):
+def _Py_Dealloc(space, obj):
     from pypy.module.cpyext.typeobject import PyTypeObjectPtr
     from pypy.module.cpyext.methodobject import generic_cpy_call
     state = space.fromcache(State)
-    w_type = space.type(w_obj)
-    pto = make_ref(space, w_type)
+    pto = obj.c_obj_type
     pto = rffi.cast(PyTypeObjectPtr, pto)
-    try:
-        print "Calling ", pto.c_tp_dealloc, "of", w_obj, "'s type which is", w_type
-        generic_cpy_call(space, pto.c_tp_dealloc, w_obj, decref_args=False)
-    finally:
-        Py_DECREF(space, w_type) # make_ref bumps refcount
+    print "Calling ", pto.c_tp_dealloc, "of", obj, \
+          "'s type which is", rffi.charp2str(pto.c_tp_name)
+    generic_cpy_call(space, pto.c_tp_dealloc, obj, decref_args=False)
 



More information about the Pypy-commit mailing list