[pypy-commit] pypy cpyext-ext: Call make_typedescr() in complexobject.py too. This fixes the existing

arigo pypy.commits at gmail.com
Sun Apr 17 12:57:18 EDT 2016


Author: Armin Rigo <arigo at tunes.org>
Branch: cpyext-ext
Changeset: r83720:703a0b78f622
Date: 2016-04-17 18:57 +0200
http://bitbucket.org/pypy/pypy/changeset/703a0b78f622/

Log:	Call make_typedescr() in complexobject.py too. This fixes the
	existing failing test in test_complexobject.py, as well as the new
	one added now.

diff --git a/pypy/module/cpyext/complexobject.py b/pypy/module/cpyext/complexobject.py
--- a/pypy/module/cpyext/complexobject.py
+++ b/pypy/module/cpyext/complexobject.py
@@ -1,16 +1,51 @@
 from rpython.rtyper.lltypesystem import lltype, rffi
-from pypy.module.cpyext.api import (
+from pypy.module.cpyext.api import (PyObjectFields, bootstrap_function,
     cpython_api, cpython_struct, PyObject, build_type_checkers)
+from pypy.module.cpyext.pyobject import (
+    make_typedescr, track_reference, from_ref)
 from pypy.module.cpyext.floatobject import PyFloat_AsDouble
 from pypy.objspace.std.complexobject import W_ComplexObject
 from pypy.interpreter.error import OperationError
 
 PyComplex_Check, PyComplex_CheckExact = build_type_checkers("Complex")
 
-Py_complex_t = lltype.ForwardReference()
+Py_complex_t = rffi.CStruct('Py_complex_t',
+                            ('real', rffi.DOUBLE),
+                            ('imag', rffi.DOUBLE),
+                            hints={'size': 2 * rffi.sizeof(rffi.DOUBLE)})
 Py_complex_ptr = lltype.Ptr(Py_complex_t)
-Py_complex_fields = (("real", rffi.DOUBLE), ("imag", rffi.DOUBLE))
-cpython_struct("Py_complex", Py_complex_fields, Py_complex_t)
+
+PyComplexObjectStruct = lltype.ForwardReference()
+PyComplexObject = lltype.Ptr(PyComplexObjectStruct)
+PyComplexObjectFields = PyObjectFields + \
+    (("cval", Py_complex_t),)
+cpython_struct("PyComplexObject", PyComplexObjectFields, PyComplexObjectStruct)
+
+ at bootstrap_function
+def init_complexobject(space):
+    "Type description of PyComplexObject"
+    make_typedescr(space.w_complex.layout.typedef,
+                   basestruct=PyComplexObject.TO,
+                   attach=complex_attach,
+                   realize=complex_realize)
+
+def complex_attach(space, py_obj, w_obj):
+    """
+    Fills a newly allocated PyComplexObject with the given complex object. The
+    value must not be modified.
+    """
+    assert isinstance(w_obj, W_ComplexObject)
+    py_obj = rffi.cast(PyComplexObject, py_obj)
+    py_obj.c_cval.c_real = w_obj.realval
+    py_obj.c_cval.c_imag = w_obj.imagval
+
+def complex_realize(space, obj):
+    py_obj = rffi.cast(PyComplexObject, obj)
+    w_type = from_ref(space, rffi.cast(PyObject, obj.c_ob_type))
+    w_obj = space.allocate_instance(W_ComplexObject, w_type)
+    w_obj.__init__(py_obj.c_cval.c_real, py_obj.c_cval.c_imag)
+    track_reference(space, obj, w_obj)
+    return w_obj
 
 
 @cpython_api([lltype.Float, lltype.Float], PyObject)
diff --git a/pypy/module/cpyext/test/test_complexobject.py b/pypy/module/cpyext/test/test_complexobject.py
--- a/pypy/module/cpyext/test/test_complexobject.py
+++ b/pypy/module/cpyext/test/test_complexobject.py
@@ -53,3 +53,12 @@
                  return obj;
              """)])
         assert module.test() == 1.2 + 3.4j
+
+    def test_WComplex_to_PyComplex(self):
+        module = self.import_extension('foo', [
+            ("test", "METH_O",
+             """
+                 Py_complex c = ((PyComplexObject *)args)->cval;
+                 return Py_BuildValue("dd", c.real, c.imag);
+             """)])
+        assert module.test(1.2 + 3.4j) == (1.2, 3.4)


More information about the pypy-commit mailing list