Author: Stefan H. Muller <[email protected]>
Branch: pypy-pyarray
Changeset: r66344:232f215b317d
Date: 2013-08-08 16:16 +0200
http://bitbucket.org/pypy/pypy/changeset/232f215b317d/
Log: Implement PyArray_FLAGS()
- ndarrayobject.py: Implement PyArray_FLAGS() instead of
PyArray_ISCONTIGUOUS(). This should yield correct results w.r.t.
CPython.
- arrayobject.h: Literally copy many more macros from numpy, which
can be all traced back to PyArray_FLAGS().
diff --git a/pypy/module/cpyext/include/numpy/arrayobject.h
b/pypy/module/cpyext/include/numpy/arrayobject.h
--- a/pypy/module/cpyext/include/numpy/arrayobject.h
+++ b/pypy/module/cpyext/include/numpy/arrayobject.h
@@ -10,12 +10,15 @@
#include "old_defines.h"
#define NPY_INLINE
+#define NPY_UNUSED(x) x
+#define PyArray_MAX(a,b) (((a)>(b))?(a):(b))
+#define PyArray_MIN(a,b) (((a)<(b))?(a):(b))
/* fake PyArrayObject so that code that doesn't do direct field access works */
#define PyArrayObject PyObject
#define PyArray_Descr PyObject
-PyTypeObject PyArray_Type;
+//PyTypeObject PyArray_Type;
typedef unsigned char npy_bool;
typedef unsigned char npy_uint8;
@@ -95,35 +98,79 @@
#define PyArray_ISCOMPLEX(arr) (PyTypeNum_ISCOMPLEX(PyArray_TYPE(arr)))
-/* selection of flags */
-#define NPY_CONTIGUOUS 0x0001
-#define NPY_FORTRAN 0x0002
-#define NPY_OWNDATA 0x0004
-#define NPY_FORCECAST 0x0010
-#define NPY_ALIGNED 0x0100
-#define NPY_NOTSWAPPED 0x0200
-#define NPY_WRITEABLE 0x0400
-#define NPY_C_CONTIGUOUS NPY_CONTIGUOUS
-#define NPY_F_CONTIGUOUS NPY_FORTRAN
-#define NPY_IN_ARRAY (NPY_C_CONTIGUOUS | NPY_ALIGNED)
-#define NPY_BEHAVED (NPY_ALIGNED | NPY_WRITEABLE)
-#define NPY_CARRAY (NPY_CONTIGUOUS | NPY_BEHAVED)
-#define NPY_FARRAY (NPY_FORTRAN | NPY_BEHAVED)
-#define NPY_DEFAULT NPY_CARRAY
+/* flags */
+#define NPY_ARRAY_C_CONTIGUOUS 0x0001
+#define NPY_ARRAY_F_CONTIGUOUS 0x0002
+#define NPY_ARRAY_OWNDATA 0x0004
+#define NPY_ARRAY_FORCECAST 0x0010
+#define NPY_ARRAY_ENSURECOPY 0x0020
+#define NPY_ARRAY_ENSUREARRAY 0x0040
+#define NPY_ARRAY_ELEMENTSTRIDES 0x0080
+#define NPY_ARRAY_ALIGNED 0x0100
+#define NPY_ARRAY_NOTSWAPPED 0x0200
+#define NPY_ARRAY_WRITEABLE 0x0400
+#define NPY_ARRAY_UPDATEIFCOPY 0x1000
+
+#define NPY_ARRAY_BEHAVED (NPY_ARRAY_ALIGNED | \
+ NPY_ARRAY_WRITEABLE)
+#define NPY_ARRAY_BEHAVED_NS (NPY_ARRAY_ALIGNED | \
+ NPY_ARRAY_WRITEABLE | \
+ NPY_ARRAY_NOTSWAPPED)
+#define NPY_ARRAY_CARRAY (NPY_ARRAY_C_CONTIGUOUS | \
+ NPY_ARRAY_BEHAVED)
+#define NPY_ARRAY_CARRAY_RO (NPY_ARRAY_C_CONTIGUOUS | \
+ NPY_ARRAY_ALIGNED)
+#define NPY_ARRAY_FARRAY (NPY_ARRAY_F_CONTIGUOUS | \
+ NPY_ARRAY_BEHAVED)
+#define NPY_ARRAY_FARRAY_RO (NPY_ARRAY_F_CONTIGUOUS | \
+ NPY_ARRAY_ALIGNED)
+#define NPY_ARRAY_DEFAULT (NPY_ARRAY_CARRAY)
+#define NPY_ARRAY_IN_ARRAY (NPY_ARRAY_CARRAY_RO)
+#define NPY_ARRAY_OUT_ARRAY (NPY_ARRAY_CARRAY)
+#define NPY_ARRAY_INOUT_ARRAY (NPY_ARRAY_CARRAY | \
+ NPY_ARRAY_UPDATEIFCOPY)
+#define NPY_ARRAY_IN_FARRAY (NPY_ARRAY_FARRAY_RO)
+#define NPY_ARRAY_OUT_FARRAY (NPY_ARRAY_FARRAY)
+#define NPY_ARRAY_INOUT_FARRAY (NPY_ARRAY_FARRAY | \
+ NPY_ARRAY_UPDATEIFCOPY)
+
+#define NPY_ARRAY_UPDATE_ALL (NPY_ARRAY_C_CONTIGUOUS | \
+ NPY_ARRAY_F_CONTIGUOUS | \
+ NPY_ARRAY_ALIGNED)
+
+#define NPY_FARRAY NPY_ARRAY_FARRAY
+#define NPY_CARRAY NPY_ARRAY_CARRAY
+
+#define PyArray_CHKFLAGS(m, flags) (PyArray_FLAGS(m) & (flags))
+
+#define PyArray_ISCONTIGUOUS(m) PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS)
+#define PyArray_ISWRITEABLE(m) PyArray_CHKFLAGS(m, NPY_ARRAY_WRITEABLE)
+#define PyArray_ISALIGNED(m) PyArray_CHKFLAGS(m, NPY_ARRAY_ALIGNED)
+
+#define PyArray_IS_C_CONTIGUOUS(m) PyArray_CHKFLAGS(m, NPY_ARRAY_C_CONTIGUOUS)
+#define PyArray_IS_F_CONTIGUOUS(m) PyArray_CHKFLAGS(m, NPY_ARRAY_F_CONTIGUOUS)
+
+#define PyArray_FLAGSWAP(m, flags) (PyArray_CHKFLAGS(m, flags) && \
+ PyArray_ISNOTSWAPPED(m))
+
+#define PyArray_ISCARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY)
+#define PyArray_ISCARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_CARRAY_RO)
+#define PyArray_ISFARRAY(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY)
+#define PyArray_ISFARRAY_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_FARRAY_RO)
+#define PyArray_ISBEHAVED(m) PyArray_FLAGSWAP(m, NPY_ARRAY_BEHAVED)
+#define PyArray_ISBEHAVED_RO(m) PyArray_FLAGSWAP(m, NPY_ARRAY_ALIGNED)
+
+#define PyArray_ISONESEGMENT(arr) (1)
+#define PyArray_ISNOTSWAPPED(arr) (1)
+#define PyArray_ISBYTESWAPPED(arr) (0)
+
/* functions */
#ifndef PyArray_NDIM
#define PyArray_Check _PyArray_Check
#define PyArray_CheckExact _PyArray_CheckExact
-
-#define PyArray_ISONESEGMENT(arr) (1)
-#define PyArray_FLAGS(arr) (0)
-
-#define PyArray_ISCONTIGUOUS _PyArray_ISCONTIGUOUS
-
-#define PyArray_ISCARRAY(arr) PyArray_ISCONTIGUOUS(arr)
-#define PyArray_ISFARRAY(arr) (!PyArray_ISCONTIGUOUS(arr))
+#define PyArray_FLAGS _PyArray_FLAGS
#define PyArray_NDIM _PyArray_NDIM
#define PyArray_DIM _PyArray_DIM
diff --git a/pypy/module/cpyext/include/numpy/old_defines.h
b/pypy/module/cpyext/include/numpy/old_defines.h
--- a/pypy/module/cpyext/include/numpy/old_defines.h
+++ b/pypy/module/cpyext/include/numpy/old_defines.h
@@ -2,9 +2,11 @@
#ifndef OLD_DEFINES_H
#define OLD_DEFINES_H
+/*
#if defined(NPY_NO_DEPRECATED_API) && NPY_NO_DEPRECATED_API >=
NPY_1_7_API_VERSION
#error The header "old_defines.h" is deprecated as of NumPy 1.7.
#endif
+*/
#define NDARRAY_VERSION NPY_VERSION
diff --git a/pypy/module/cpyext/ndarrayobject.py
b/pypy/module/cpyext/ndarrayobject.py
--- a/pypy/module/cpyext/ndarrayobject.py
+++ b/pypy/module/cpyext/ndarrayobject.py
@@ -8,11 +8,38 @@
from pypy.module.cpyext.pyobject import PyObject
from pypy.module.micronumpy.interp_numarray import W_NDimArray,
convert_to_array, wrap_impl
from pypy.module.micronumpy.interp_dtype import get_dtype_cache
+from pypy.module.micronumpy.arrayimpl.concrete import ConcreteArray
from pypy.module.micronumpy.arrayimpl.scalar import Scalar
from rpython.rlib.rawstorage import RAW_STORAGE_PTR
-NPY_FORTRAN = 0x0002
-NPY_OWNDATA = 0x0004
+NPY_C_CONTIGUOUS = 0x0001
+NPY_F_CONTIGUOUS = 0x0002
+NPY_OWNDATA = 0x0004
+NPY_FORCECAST = 0x0010
+NPY_ENSURECOPY = 0x0020
+NPY_ENSUREARRAY = 0x0040
+NPY_ELEMENTSTRIDES = 0x0080
+NPY_ALIGNED = 0x0100
+NPY_NOTSWAPPED = 0x0200
+NPY_WRITEABLE = 0x0400
+NPY_UPDATEIFCOPY = 0x1000
+
+NPY_BEHAVED = NPY_ALIGNED | NPY_WRITEABLE
+NPY_BEHAVED_NS = NPY_ALIGNED | NPY_WRITEABLE | NPY_NOTSWAPPED
+NPY_CARRAY = NPY_C_CONTIGUOUS | NPY_BEHAVED
+NPY_CARRAY_RO = NPY_C_CONTIGUOUS | NPY_ALIGNED
+NPY_FARRAY = NPY_F_CONTIGUOUS | NPY_BEHAVED
+NPY_FARRAY_RO = NPY_F_CONTIGUOUS | NPY_ALIGNED
+NPY_DEFAULT = NPY_CARRAY
+NPY_IN = NPY_CARRAY_RO
+NPY_OUT = NPY_CARRAY
+NPY_INOUT = NPY_CARRAY | NPY_UPDATEIFCOPY
+NPY_IN_FARRAY = NPY_FARRAY_RO
+NPY_OUT_FARRAY = NPY_FARRAY
+NPY_INOUT_FARRAY = NPY_FARRAY | NPY_UPDATEIFCOPY
+NPY_CONTIGUOUS = NPY_C_CONTIGUOUS | NPY_F_CONTIGUOUS
+NPY_UPDATE_ALL = NPY_CONTIGUOUS | NPY_ALIGNED
+
# the asserts are needed, otherwise the translation fails
@@ -29,12 +56,19 @@
w_type = space.gettypeobject(W_NDimArray.typedef)
return space.is_w(w_obj_type, w_type)
-
@cpython_api([PyObject], rffi.INT_real, error=CANNOT_FAIL)
-def _PyArray_ISCONTIGUOUS(space, w_array):
+def _PyArray_FLAGS(space, w_array):
assert isinstance(w_array, W_NDimArray)
- return w_array.implementation.order == 'C'
-
+ flags = NPY_BEHAVED_NS
+ if isinstance(w_array.implementation, ConcreteArray):
+ flags |= NPY_OWNDATA
+ if len(w_array.get_shape()) < 2:
+ flags |= NPY_CONTIGUOUS
+ elif w_array.implementation.order == 'C':
+ flags |= NPY_C_CONTIGUOUS
+ else:
+ flags |= NPY_F_CONTIGUOUS
+ return flags
@cpython_api([PyObject], rffi.INT_real, error=CANNOT_FAIL)
def _PyArray_NDIM(space, w_array):
@@ -157,7 +191,7 @@
raise OperationError(space.w_NotImplementedError,
space.wrap("strides must be NULL"))
- order = 'F' if flags & NPY_FORTRAN else 'C'
+ order = 'C' if flags & NPY_C_CONTIGUOUS else 'F'
owning = True if flags & NPY_OWNDATA else False
w_subtype = None
diff --git a/pypy/module/cpyext/test/test_ndarrayobject.py
b/pypy/module/cpyext/test/test_ndarrayobject.py
--- a/pypy/module/cpyext/test/test_ndarrayobject.py
+++ b/pypy/module/cpyext/test/test_ndarrayobject.py
@@ -32,11 +32,16 @@
assert not api._PyArray_Check(x)
assert not api._PyArray_CheckExact(x)
- def test_ISCONTIGUOUS(self, space, api):
- a = array(space, [10, 5, 3], order='C')
+ def test_FLAGS(self, space, api):
+ s = array(space, [10])
+ c = array(space, [10, 5, 3], order='C')
f = array(space, [10, 5, 3], order='F')
- assert api._PyArray_ISCONTIGUOUS(a) == 1
- assert api._PyArray_ISCONTIGUOUS(f) == 0
+ assert api._PyArray_FLAGS(s) & 0x0001
+ assert api._PyArray_FLAGS(s) & 0x0002
+ assert api._PyArray_FLAGS(c) & 0x0001
+ assert api._PyArray_FLAGS(f) & 0x0002
+ assert not api._PyArray_FLAGS(c) & 0x0002
+ assert not api._PyArray_FLAGS(f) & 0x0001
def test_NDIM(self, space, api):
a = array(space, [10, 5, 3])
_______________________________________________
pypy-commit mailing list
[email protected]
http://mail.python.org/mailman/listinfo/pypy-commit