Skip to content

Commit

Permalink
BUG: core: consider both C and F order buffers as contiguous
Browse files Browse the repository at this point in the history
  • Loading branch information
pv authored and charris committed Sep 29, 2013
1 parent 52a8c07 commit 2d897e9
Show file tree
Hide file tree
Showing 2 changed files with 35 additions and 5 deletions.
33 changes: 28 additions & 5 deletions numpy/core/src/multiarray/conversion_utils.c
Expand Up @@ -146,30 +146,53 @@ PyArray_IntpConverter(PyObject *obj, PyArray_Dims *seq)
NPY_NO_EXPORT int
PyArray_BufferConverter(PyObject *obj, PyArray_Chunk *buf)
{
#if defined(NPY_PY3K)
Py_buffer view;
#else
Py_ssize_t buflen;
#endif

buf->ptr = NULL;
buf->flags = NPY_ARRAY_BEHAVED;
buf->base = NULL;
if (obj == Py_None) {
return NPY_SUCCEED;
}
if (PyObject_AsWriteBuffer(obj, &(buf->ptr), &buflen) < 0) {

#if defined(NPY_PY3K)
if (PyObject_GetBuffer(obj, &view, PyBUF_ANY_CONTIGUOUS|PyBUF_WRITABLE) != 0) {
PyErr_Clear();
buf->flags &= ~NPY_ARRAY_WRITEABLE;
if (PyObject_AsReadBuffer(obj, (const void **)&(buf->ptr),
&buflen) < 0) {
if (PyObject_GetBuffer(obj, &view, PyBUF_ANY_CONTIGUOUS) != 0) {
return NPY_FAIL;
}
}
buf->len = (npy_intp) buflen;

buf->ptr = view.buf;
buf->len = (npy_intp) view.len;

/*
* XXX: PyObject_AsWriteBuffer does also this, but it is unsafe, as there is
* no strict guarantee that the buffer sticks around after being released.
*/
PyBuffer_Release(&view);

/* Point to the base of the buffer object if present */
#if defined(NPY_PY3K)
if (PyMemoryView_Check(obj)) {
buf->base = PyMemoryView_GET_BASE(obj);
}
#else
if (PyObject_AsWriteBuffer(obj, &(buf->ptr), &buflen) < 0) {
PyErr_Clear();
buf->flags &= ~NPY_ARRAY_WRITEABLE;
if (PyObject_AsReadBuffer(obj, (const void **)&(buf->ptr),
&buflen) < 0) {
return NPY_FAIL;
}
}
buf->len = (npy_intp) buflen;

/* Point to the base of the buffer object if present */
if (PyBuffer_Check(obj)) {
buf->base = ((PyArray_Chunk *)obj)->base;
}
Expand Down
7 changes: 7 additions & 0 deletions numpy/core/tests/test_regression.py
Expand Up @@ -1912,6 +1912,13 @@ def test_copymodule_preserves_f_contiguity(self):
assert_(c.flags.fortran)
assert_(c.flags.f_contiguous)

def test_fortran_order_buffer(self):
import numpy as np
a = np.array([['Hello', 'Foob']], dtype='<U5', order='F')
arr = np.ndarray(shape=[1, 2, 5], dtype='<U1', buffer=a)
arr2 = np.array([[[sixu('H'), sixu('e'), sixu('l'), sixu('l'), sixu('o')],
[sixu('F'), sixu('o'), sixu('o'), sixu('b'), sixu('')]]])
assert_array_equal(arr, arr2)

if __name__ == "__main__":
run_module_suite()

0 comments on commit 2d897e9

Please sign in to comment.