[pypy-commit] cffi sirtom67/float_complex: float complex progress. Added __complex__ method to cdata.
sirtom67
pypy.commits at gmail.com
Sun Feb 5 18:15:44 EST 2017
Author: Tom Krauss <thomas.p.krauss at gmail.com>
Branch: sirtom67/float_complex
Changeset: r2879:6dcf51c6003c
Date: 2017-02-05 17:13 -0600
http://bitbucket.org/cffi/cffi/changeset/6dcf51c6003c/
Log: float complex progress. Added __complex__ method to cdata. Test
currently failing at > assert repr(complex(cast(p, -0j))) == '-0j' E
assert '0j' == '-0j' E - 0j E + -0j E ? +
diff --git a/c/_cffi_backend.c b/c/_cffi_backend.c
--- a/c/_cffi_backend.c
+++ b/c/_cffi_backend.c
@@ -884,6 +884,26 @@
return 0;
}
+static Py_complex
+read_raw_complex_data(char *target, int size)
+{
+ Py_complex r = {.real=0, .imag=0};
+ if (size == 2*sizeof(float)) {
+ float real_part, imag_part;
+ memcpy(&real_part, target + 0, sizeof(float));
+ memcpy(&imag_part, target + sizeof(float), sizeof(float));
+ r.real = real_part;
+ r.imag = imag_part;
+ return r;
+ }
+ if (size == 2*sizeof(double)) {
+ memcpy(&(r.real), target, 2*sizeof(double));
+ return r;
+ }
+ Py_FatalError("read_raw_complex_data: bad float size");
+ return r;
+}
+
static void
write_raw_float_data(char *target, double source, int size)
{
@@ -1011,6 +1031,10 @@
return (PyObject *)cd;
}
}
+ else if (ct->ct_flags & CT_PRIMITIVE_COMPLEX) {
+ Py_complex value = read_raw_complex_data(data, ct->ct_size);
+ return PyComplex_FromCComplex(value);
+ }
else if (ct->ct_flags & CT_PRIMITIVE_CHAR) {
/*READ(data, ct->ct_size)*/
if (ct->ct_size == sizeof(char))
@@ -2009,6 +2033,10 @@
}
return PyFloat_FromDouble(value);
}
+ if (cd->c_type->ct_flags & CT_PRIMITIVE_COMPLEX) {
+ double value = read_raw_float_data(cd->c_data, cd->c_type->ct_size);
+ return PyComplex_FromDoubles(value, 0.0);
+ }
PyErr_Format(PyExc_TypeError, "float() not supported on cdata '%s'",
cd->c_type->ct_name);
return NULL;
@@ -2808,6 +2836,19 @@
}
}
+static PyObject *cdata_complex(PyObject *cd_, PyObject *noarg)
+{
+ CDataObject *cd = (CDataObject *)cd_;
+
+ if (cd->c_type->ct_flags & CT_PRIMITIVE_COMPLEX) {
+ Py_complex value = read_raw_complex_data(cd->c_data, cd->c_type->ct_size);
+ return PyComplex_FromCComplex(value);
+ }
+ PyErr_Format(PyExc_TypeError, "complex() not supported on cdata '%s'",
+ cd->c_type->ct_name);
+ return NULL;
+}
+
static PyObject *cdata_iter(CDataObject *);
static PyNumberMethods CData_as_number = {
@@ -2857,8 +2898,9 @@
};
static PyMethodDef cdata_methods[] = {
- {"__dir__", cdata_dir, METH_NOARGS},
- {NULL, NULL} /* sentinel */
+ {"__dir__", cdata_dir, METH_NOARGS},
+ {"__complex__", cdata_complex, METH_NOARGS},
+ {NULL, NULL} /* sentinel */
};
static PyTypeObject CData_Type = {
@@ -3599,7 +3641,6 @@
/* cast to a complex */
Py_complex value;
PyObject *io;
- printf("_cffi_backend.c do_cast ct->ct_size=%ld\n", ct->ct_size);
if (CData_Check(ob)) {
CDataObject *cdsrc = (CDataObject *)ob;
@@ -3983,8 +4024,6 @@
int name_size;
ffi_type *ffitype;
- printf("hello\n");
-
for (ptypes=types; ; ptypes++) {
if (ptypes->name == NULL) {
#ifndef HAVE_WCHAR_H
diff --git a/c/realize_c_type.c b/c/realize_c_type.c
--- a/c/realize_c_type.c
+++ b/c/realize_c_type.c
@@ -101,7 +101,6 @@
static PyObject *build_primitive_type(int num)
{
- fprintf(stderr, "fooooooooooooo num=%d\n",num);
/* XXX too many translations between here and new_primitive_type() */
static const char *primitive_name[] = {
NULL,
diff --git a/c/test_c.py b/c/test_c.py
--- a/c/test_c.py
+++ b/c/test_c.py
@@ -197,12 +197,12 @@
py.test.raises(TypeError, float, cast(p, -150))
assert complex(cast(p, 1.25)) == 1.25
assert complex(cast(p, 1.25j)) == 1.25j
- assert float(cast(p, INF*1j)) == INF*1j
- assert float(cast(p, -INF)) == -INF
+ assert complex(cast(p, complex(0,INF))) == complex(0,INF)
+ assert complex(cast(p, -INF)) == -INF
if name == "float":
assert complex(cast(p, 1.1j)) != 1.1j # rounding error
assert complex(cast(p, 1E200+3j)) == INF+3j # limited range
- assert complex(cast(p, 3+1E200j)) == 3+INF*1j # limited range
+ assert complex(cast(p, complex(3,1E200))) == complex(3,INF) # limited range
assert cast(p, -1.1j) != cast(p, -1.1j)
assert repr(complex(cast(p, -0.0)).real) == '-0.0'
More information about the pypy-commit
mailing list